我有一组请求处理程序,如下所示:
func GetProductsHandler(w http.ResponseWriter, req *http.Request) {
defer req.Body.Close()
products := db.GetProducts()
// ...
// return products as JSON array
}
如何以正确的方式测试它们?我应该将模拟ResponseWriter和Request对象发送到函数并查看结果吗?
是否有工具在Go中模拟请求和响应对象以简化流程而无需在测试之前启动服务器?
答案 0 :(得分:8)
Go提供了一个模拟编写器,用于测试处理程序。 standard library documentation提供了一个示例:
package main
import (
"fmt"
"net/http"
"net/http/httptest"
)
func main() {
handler := func(w http.ResponseWriter, r *http.Request) {
http.Error(w, "something failed", http.StatusInternalServerError)
}
req := httptest.NewRequest("GET", "http://example.com/foo", nil)
w := httptest.NewRecorder()
handler(w, req)
fmt.Printf("%d - %s", w.Code, w.Body.String())
}
我认为拥有全局依赖关系(db
)会对完整的单元测试产生影响。使用go你的测试可以重新分配值,屏蔽,db
的全局值。
另一个策略(我的首选)是将处理程序打包在一个结构中,该结构具有db
属性..
type Handlers struct {
db DB_INTERFACE
}
func (hs *Handlers) GetProductsHandler(w http.ResponseWriter, req *http.Request) {...}
这样,您的测试可以使用存根Handlers
对象实例化db
,这将允许您创建无IO单元测试。