testing - go中接口(interface)模拟的方法

标签 testing go mocking

如果我有一个如下所示的 handlerfunc。 “模拟”或注入(inject)包装某些对象以进行测试的接口(interface)的最佳方法是什么?

func GetOrCreateUser(w http.ResponseWriter, r *http.Request) {
    user := GetUserFromContext(r.Context())
    if created :=user.GetOrCreate(); created {
        smtp.SendEmail(...)
        return
    } else {
        w.Write([]byte("Hello User!"))
    }
}

我遇到的唯一方法似乎是这样做:

type Mailer interface { SendMail() }

func HandlerWithMailer(m Mailer) http.handlerFunc {
    return func(w http.ResponseWriter, r *http.Request) {
        user := GetUserFromContext(r.Context())
        if created := user.GetOrCreate(); created {
            m.SendEmail(...)
            return
        } else {                
            w.Write([]byte("Hello User!"))
        }
    }
}

然后在路由器中像这样调用邮件程序(使用 httprouter):

m := mailer.New() // assuming this returns a new mailer
r := httprouter.New()
r.GET("/mailer", HandlerWithMailer(m))

然后可以通过制作一个实现接口(interface)并返回我想要的任何东西的结构来测试它,它可以在测试中调用。我知道这行得通,但我想知道这是否是 Go 中首选的测试方法,以及是否有任何其他方法可以实现此目的。

最佳答案

我会从这样的结构中调用我的处理程序:

type Handlers struct {
    mailer *Mailer
}

func(h *Handlers) GetOrCreateUser(w http.ResponseWriter, r *http.Request) {
    user := GetUserFromContext(r.Context())
    if created :=user.GetOrCreate(); created {
        h.mailer.SendEmail(...)
        return
    } else {
        w.Write([]byte("Hello User!"))
    }
}

通过这种方式,您可以使用要使用的 Mailer 的实现来实例化结构。

m := mailer.New() // assuming this returns a new mailer
h := Handlers{&m}

r := httprouter.New()
r.GET("/mailer", h.HandlerWithMailer)

在你的测试中

m := mockMailer.New() // assuming this returns a new mailer
h := Handlers{&m}

r := httprouter.New()
r.GET("/mailer", h.HandlerWithMailer)

关于testing - go中接口(interface)模拟的方法,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/42775292/

相关文章:

unit-testing - 分支覆盖与决策覆盖相同吗?

parsing - 如何在 Go 中解码和编码 YAML,同时保留空白?

与文件系统中的二进制文件交互的方法的java单元测试

c++ - 在 gTest 中模拟 FreeRTOS 函数

ruby - 如何使用 minitest stub 多次调用同一函数以获得不同的返回

asp.net-mvc-2 - 使用带有 MSpecMVC、RedirectToAction 和 ViewData 测试条件问题的 MSpec 设置测试

android - 如何在不破坏手机的情况下测试我的自定义内核?

iOS:测试特定屏幕而不通过整个应用程序流程

post - 如何在 golang 中编码 POST 策略 - 基于浏览器的上传到 amazon S3?

go - Flanneld:错误注册网络:找不到具有管理 IP 的网络