1

我使用testify(v1.6.1)并且需要测试接口的方法是否以正确的顺序调用。我检查了文档并试图在互联网上找到任何信息,但没有找到任何关于模拟订单检查的信息。

例子:

type InterfaceA interface {
    Execute()
}

type InterfaceB interface {
    Execute()
}
type Composition struct {
    a InterfaceA
    b InterfaceB
}

func (c * Composition) Apply() error {
    //How to check that "a" execute before "b"?
    c.a.Execute()
    c.b.Execute()
    return nil
}
4

3 回答 3

1

这不是直接支持的,即使有一个未解决的问题(stretchr/testify/issue 741 "assert mock calls in order"

更一般的问题684“断言调用顺序?” 包括反驳:

IMO 你应该检查函数的输出,而不是它在内部是如何工作的。它可能会导致很难维护的测试实现。

虽然,在同一个线程中:

IMO 有强制执行命令的情况。即如果你模拟一个互斥锁,你最好检查在解锁之前总是调用锁。
我们可以有一个简单的实现,其中模拟有一个“ assertExpectationsInOrder”真/假标志,可以在添加任何期望之前设置。

这可能会导致一些测试,例如cassandra-operator/cmd/operator/controller_test.go哪些记录事件来测试他们的订单。

于 2020-08-05T04:26:33.167 回答
1

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

如果有原因,您可以使订单检查逻辑复杂化......

于 2020-08-05T04:31:47.383 回答
0

正如其他人所说,这是一个内部细节,并且确实将您的测试与实现纠缠在一起。如果您确定订单很重要,这将毫无意义。在这里保持简洁是另一种使用最低限度测试订单的解决方案。

创建两个实现 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()
        }
    }
}

操场

于 2020-08-06T16:06:59.180 回答