2009-04-08 14 views
49

Mam wyśmiewany obiekt, który jest przekazywany jako argument konstruktora do innego obiektu.Rhino Mocks AssertWasCalled (wiele razy) na geterze właściwości za pomocą AAA

Jak mogę sprawdzić, czy wywołano właściwość obiektu wyszydzanego? Jest to kod używam obecnie:

INewContactAttributes newContact = MockRepository.GenerateMock<INewContactAttributes>(); 
newContact.Stub(x => x.Forenames).Return("One Two Three"); 
someobject.ConsumeContact(newContact); 
newContact.AssertWasCalled(x => { var dummy = x.Forenames; }); 

To działa z wyjątkiem, gdy w ramach „someObject” getter na imiona własności jest używany wielokrotnie. To kiedy się "Rhino.Mocks.Exceptions.ExpectationViolationException: INewContactAttributes.get_Forenames(); Oczekiwany # 1, # 2 Rzeczywista .."

prostu za pomocą

newContact.AssertWasCalled(x => { var dummy = x.Forenames; }, options => options.Repeat.Any()); 

nie działa i daje poniższy błąd :

"Oczekiwanie zostało usunięte z listy oczekiwań oczekujących, czy zadzwoniłeś do funkcji Repeat.Any()? To nie jest obsługiwane w AssertWasCalled()."

Jak więc obsłużyć wiele połączeń?

+1

Kliknij ✓ poniżej jednej z odpowiedzi na to zaakceptować. – lockstock

Odpowiedz

70

newContact.AssertWasCalled(x => { var dummy = x.Forenames; }, options => options.Repeat.AtLeastOnce());

Repeat.Any nie działa z AssertWasCalled ponieważ 0 liczy jak każdy .. więc jeśli NIE BYŁO wywoływane, AsserWasCalled zwróciło PRAWDA, nawet jeśli nie zostało wywołane.

+3

Dzięki, zaoszczędziło mi to czas. Powinna być najlepszą odpowiedzią na pytanie (IMO) – Thies

2

Jaka jest Twoja motywacja sprawdzania, ile razy jest ona wywoływana? Czy jest to szczególnie droga operacja? Jeśli tak, sugerowałbym, aby umieścić go za metodą zamiast, ponieważ, mówiąc semantycznie, właściwości powinny być niedrogie połączenia.

Również sprawdzanie, ile razy właściwość jest wywoływana, nie jest ciągiem testów jednostkowych (nie martw się, częstym błędem jest testowanie za dużo, wszyscy byliśmy tam). To, co naprawdę powinieneś testować, to to, że biorąc pod uwagę stan twojego symulowanego obiektu, metoda generuje oczekiwany wynik. Liczba razy, gdy metoda jest wywoływana, aby to zrobić, tak naprawdę nie ma znaczenia (chyba że jest to usługa wysłania wiadomości e-mail lub coś podobnego). Jest to szczegół implementacji, którego normalnie nie testowałbyś, ponieważ prosty refaktor złamałby twoje testy, ponieważ byłyby zbyt szczegółowe.

+0

Dzięki Garry. Właściwie nie chcę sprawdzać, ile razy był nazywany getter, tylko że został wywołany. Tak się składa, że ​​"someobject" używa go wewnętrznie dwa razy. To jest przyczyna problemu; wydaje się, że nie ma możliwości użycia .Repeat.Any() z AssertWasCalled. – Confused

+0

Ale ogólnie sprawdzenie, czy dane wyjściowe są prawidłowe, weryfikuje, czy właściwość została wywołana. Jak dane wyjściowe byłyby prawidłowe, gdyby właściwość nie została wywołana? –

+0

Garry, twoje komentarze są poprawne, ale musisz też powiedzieć, że istnieją zasadniczo dwie szkoły próbnego testowania: oparte na stanie i oparte na interakcjach. Sprawdzanie, ile razy metoda jest wywoływana, jest całkowicie poprawne w testach opartych na interakcjach. A czasami państwo się nie zmienia. –

0

newContact.Expect (c => c.ForeNames) .Return (...) .Repeat.Any()

2

W zależności od wersji Rhino używasz, można użyć:

// Call to mock object here 
LastCall.IgnoreArguments().Repeat.Never(); 
26

zgadzam się z Chrisem odpowiedź

newContact.AssertWasCalled(x => { var dummy = x.Forenames; }, options => options.Repeat.AtLeastOnce()); 

Dodatkowo Jeśli wiesz dokładnie, ile razy nieruchomość będzie nazywany możesz wykonać:

gdzie n jest int.

0

Od Here:

mock.AssertWasCalled(x => x.Name ="Bob"); 

lub

mock.AssertWasCalled(x => x.Name =Arg.Is("Bob")); 

lub

mock.AssertWasCalled(x => x.Name =Arg<string>.Is.NotNull); 
+1

Ta odpowiedź nie zadziała, ponieważ utkniesz w twierdzeniu, że metoda jest wywoływana raz. Pytanie dotyczy potwierdzenia, że ​​metoda została wywołana wiele razy. – Peter