简体   繁体   中英

How to make FakeItEasy capture full argument state?

I have a piece of code like this (simplified):

await realApiClient.DoSomething(entity);
entity.Email = newEmail;
await realApiClient.DoSomethingElse(entity);

In my test I have created a fake and want to check that both DoSomething and DoSomethingElse were called. So I do it like this:

A.CallTo(() => fakeApiClient.DoSomething(A<Entity>
        .That.Matches(p => p.Email == "p123@okdomain.com"
    )))
    .MustHaveHappenedOnceExactly();

A.CallTo(() => fakeApiClient.DoSomethingElse(A<Entity>
        .That.Matches(p => p.Email != "p123@okdomain.com"
    )))
    .MustHaveHappenedOnceExactly();

The problem - the test for DoSomething fails because FakeItEasy seems to not capture the full state of the method call arguments. When I check the email in DoSomething call, FakeItEasy is checking against the value that was updated in entity.Email = newEmail; and not the original value before the update.

As soon as I comment out entity.Email = newEmail; then DoSomething test succeeds. But then, of course, DoSomethingElse rightfully fails because it expected the email to be changed.

What is the proper way to access the argument state as it actually was at the time when DoSomething was called?

FakeItEasy doesn't (and likely never will) store a snapshot of an object's state, for reasons discussed mostly in the accepted answer to MustHaveHappened fails when called twice on the same object and also in Verifying multiple method calls with reference parameters .

There are hints there about manually capturing important state to preserve it between calls.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM