测试 http.Pusher 和 golang 中的推送功能

Testing http.Pusher and the push function in golang

我正在尝试为 http.Pusher 编写单元测试。我尝试将 httptest.NewRecorder() 用作 http.ResponseWriter 但类型转换失败。我还能如何编写测试?

    //My function 
    func push(w http.ResponseWriter, resource string) error {
        pusher, ok := w.(http.Pusher)
        if ok {
            return pusher.Push(resource, nil)
        }
        return fmt.Errorf("Pusher not supported")
    }

    //My test 
    func TestPush(t *testing.T) {
        resource := "static/css/main.css"
        response := httptest.NewRecorder()
        got := push(response, resource)

        if got != nil {
            t.Errorf("Error : %v", got)
        }
    }

输出是 "Pusher not supported",我假设 w.(http.Pusher) 失败了。

您可以创建一个模拟 http.ResponseWriter that also implements http.Pusher,并在测试期间通过它。

这是一个适合您的可测试函数的简单实现:

type pusher struct {
    http.ResponseWriter
    err    error // err to return from Push()
    target string
    opts   *http.PushOptions
}

func (p *pusher) Push(target string, opts *http.PushOptions) error {
    // record passed arguments for later inspection
    p.target = target
    p.opts = opts
    return p.err
}

示例测试函数:

func TestPush(t *testing.T) {
    resource := "static/css/main.css"
    p := &pusher{}
    err := push(p, resource)

    if err != p.err {
        t.Errorf("Expected: %v, got: %v", p.err, err)
    }
    if resource != p.target {
        t.Errorf("Expected: %v, got: %v", p.target, resource)
    }
}

请注意,这个简单的 pusher 嵌入了 http.ResponseWriter 类型,这将使​​它本身成为一个 http.ResponseWriter(它将使 pusher 实现 http.ResponseWriter)。在测试期间,我们离开了这个字段 nil 因为可测试的 push() 函数没有使用它的任何东西。如果您的真实函数会调用它的方法,例如 ResponseWriter.Header(),那当然会导致运行时恐慌。在这种情况下,您还必须提供有效的 http.ResponseWriter,例如:

p := &pusher{ResponseWriter: httptest.NewRecorder()}