如何使用FakeItEasy断言方法没有被调用

时间:2013-07-29 21:43:40

标签: c# .net unit-testing xunit fakeiteasy

我想断言没有派遣,a.k.a。 _dispatcher.Dispatch未被调用

interface被伪造/嘲笑:

interface IDispatcher
{
    void Dispatch<T>(T command, 
                     Stuff stuff = null,
                     TimeSpan? timeout = null,
                     int? retries = null) where T : Command;
}

在测试机构中:

_dispatcher = A.Fake<IDispatcher>();

// do stuff

A.CallTo(() => _dispatcher.Dispatch(A<Command>.Ignored,
                                    A<Stuff>.Ignored,
                                    A<TimeSpan?>.Ignored,
                                    A<int?>.Ignored)).MustNotHaveHappened();

测试通过 调度

有什么想法吗?我错误地使用了FakeItEasy吗?

1 个答案:

答案 0 :(得分:1)

@Scoobie

您调用调度方法的实际类型是否真的Command?或者它是派生类型?如果它是派生类型,可能会导致您观察到的行为。

请参阅以下示例:     var dispatcher = A.Fake();

dispatcher.Dispatch(new Command(), new Stuff());

A.CallTo(() => dispatcher.Dispatch(A<Command>.Ignored,
                                    A<Stuff>.Ignored,
                                    A<TimeSpan?>.Ignored,
                                    A<int?>.Ignored)).MustNotHaveHappened();

此测试将失败,如预期的那样。

但如果你有这样的事情:

public class NewCommand : Command
{
}

以下测试

var dispatcher = A.Fake<IDispatcher>();

dispatcher.Dispatch(new NewCommand(), new Stuff());

A.CallTo(() => dispatcher.Dispatch(A<Command>.Ignored,
                                    A<Stuff>.Ignored,
                                    A<TimeSpan?>.Ignored,
                                    A<int?>.Ignored)).MustNotHaveHappened();

虽然你预计会失败,但会成功。

但这就是FakeItEasy的工作原理。如果你想讨论它是否应该以这种方式工作,请转到https://github.com/FakeItEasy/FakeItEasy并提出问题。

现在为您解决问题。我假设您要确保永远不会调用IDispatcher.Dispatch方法,无论泛型参数具有哪种类型。 你有几个选择:

由于Dispatch方法是IDispatcher上的唯一方法,我只想写下以下内容

A.CallTo(dispatcher).MustNotHaveHappened();

当调用dispatcher实例上的任何方法(或属性)时,此操作失败。

A.CallTo(dispatcher).Where(_ => _.Method.Name == "Dispatch")
    .MustNotHaveHappened();

只有在调用Dispatch时才会失败,但这种用法是重构杀手。

如果可能,我希望第一种替代方案。