3 回答
TA贡献1824条经验 获得超6个赞
这不是直接支持的,即使有一个未解决的问题(stretchr/testify/issue 741 "assert mock calls in order")
更一般的问题684“断言调用顺序?” 包括反驳:
IMO 你应该检查函数的输出,而不是它在内部是如何工作的。它可能会导致很难维护的测试实现。
虽然,在同一个线程中:
IMO 有强制执行命令的情况。即如果你模拟一个互斥锁,你最好检查在解锁之前总是调用锁。
我们可以有一个简单的实现,其中模拟有一个“assertExpectationsInOrder
”真/假标志,可以在添加任何期望之前设置。
这可能会导致一些测试,例如cassandra-operator/cmd/operator/controller_test.go
哪些记录事件来测试他们的订单。
TA贡献1801条经验 获得超8个赞
IMO 有强制执行命令的情况。即如果你模拟一个互斥锁,你最好检查在解锁之前总是调用锁。
这是一个简单的单线程实现:
func TestOrderOfMocks(t *testing.T) {
order := 0
amock := new(AMock)
amock.On("Execute").Run(func(args mock.Arguments) {
if order++; order != 1 {
t.Fail()
}
})
bmock := new(BMock)
bmock.On("Execute").Run(func(args mock.Arguments) {
if order++; order != 2 {
t.Fail()
}
})
c := &Composition{amock, bmock}
err := c.Apply()
require.NoError(t, err)
}
PLAYGROUND
如果有原因,您可以使订单检查逻辑复杂化......
TA贡献1856条经验 获得超11个赞
正如其他人所说,这是一个内部细节,并且确实将您的测试与实现纠缠在一起。如果您确定订单很重要,这将毫无意义。在这里保持简洁是另一种使用最低限度测试订单的解决方案。
创建两个实现 InterfaceA 和 InterfaceB 的间谍。
type SpyA struct {
Calls *[]string
}
func (s *SpyA) Execute() {
*s.Calls = append(*s.Calls, "ExecuteA")
}
type SpyB struct {
Calls *[]string
}
func (s *SpyB) Execute() {
*s.Calls = append(*s.Calls, "ExecuteB")
}
然后像这样使用它们。
func TestApply(t *testing.T) {
got := []string{}
c := &Composition{
a: &SpyA{&got},
b: &SpyB{&got},
}
c.Apply()
expected := []string{"ExecuteA", "ExecuteB"}
if len(got) != len(expected) {
t.Fail()
}
for i := range got {
if got[i] != expected[i] {
t.Fail()
}
}
}
- 3 回答
- 0 关注
- 135 浏览
添加回答
举报