我正在通过编写一个小型个人项目来学习Go。尽管体积很小,但我还是决定进行严格的单元测试,以便从一开始就学习Go的良好习惯。
琐碎的单元测试都很好,很花哨,但是现在我对依赖项感到困惑;我希望能够用模拟函数替换一些函数调用。这是我的代码片段:
func get_page(url string) string {
get_dl_slot(url)
defer free_dl_slot(url)
resp, err := http.Get(url)
if err != nil { return "" }
defer resp.Body.Close()
contents, err := ioutil.ReadAll(resp.Body)
if err != nil { return "" }
return string(contents)
}
func downloader() {
dl_slots = make(chan bool, DL_SLOT_AMOUNT) // Init the download slot semaphore
content := get_page(BASE_URL)
links_regexp := regexp.MustCompile(LIST_LINK_REGEXP)
matches := links_regexp.FindAllStringSubmatch(content, -1)
for _, match := range matches{
go serie_dl(match[1], match[2])
}
}
我希望能够测试downloader()而无需通过http实际获取页面-即通过模拟get_page(更轻松,因为它仅以字符串形式返回页面内容)或http.Get()。
我找到了这个线程:https : //groups.google.com/forum/#!topic/golang- nuts/ 6AN1E2CJOxI,这似乎与一个类似的问题有关。朱利安·菲利普斯(Julian Phillips)提出了他的图书馆Withmock(http://github.com/qur/withmock)作为解决方案,但我无法使其正常工作。老实说,这是我的测试代码的相关部分,对我来说,这基本上是对货物的崇拜代码:
import (
"testing"
"net/http" // mock
"code.google.com/p/gomock"
)
...
func TestDownloader (t *testing.T) {
ctrl := gomock.NewController()
defer ctrl.Finish()
http.MOCK().SetController(ctrl)
http.EXPECT().Get(BASE_URL)
downloader()
// The rest to be written
}
测试输出如下:
ERROR: Failed to install '_et/http': exit status 1
output:
can't load package: package _et/http: found packages http (chunked.go) and main (main_mock.go) in /var/folders/z9/ql_yn5h550s6shtb9c5sggj40000gn/T/withmock570825607/path/src/_et/http
Withmock是否可以解决我的测试问题?我应该怎么做才能使其正常工作?