mockito geri aramaları ve bağımsız değişken değerleri alma


89

Mockito'nun fonksiyon argüman değerlerini yakalaması için hiç şansım yok! Bir arama motoru dizini ile dalga geçiyorum ve bir dizin oluşturmak yerine sadece bir karma kullanıyorum.

// Fake index for solr
Hashmap<Integer,Document> fakeIndex;

// Add a document 666 to the fakeIndex
SolrIndexReader reader = Mockito.mock(SolrIndexReader.class);

// Give the reader access to the fake index
Mockito.when(reader.document(666)).thenReturn(document(fakeIndex(666))

Sorguların sonuçlarını (yani hangi belgeleri döndürdüklerini) test ettiğim için rastgele argümanlar kullanamıyorum. Aynı şekilde, her belge için belirli bir değer ve bir satır belirtmek istemiyorum!

Mockito.when(reader.document(0)).thenReturn(document(fakeIndex(0))
Mockito.when(reader.document(1)).thenReturn(document(fakeIndex(1))
....
Mockito.when(reader.document(n)).thenReturn(document(fakeIndex(n))

Mockito Kullanma sayfasındaki geri aramalar bölümüne baktım . Ne yazık ki Java değil ve Java'da çalışmak için kendi yorumumu bulamadım.

DÜZENLEME (açıklama için): Mockito'nun bir X argümanını yakalayıp işlevime aktarmasını nasıl sağlayabilirim? X'in tam değerini (veya ref) işleve geçirilmesini istiyorum.

Tüm vakaları numaralandırmak istemiyorum ve keyfi argüman işe yaramayacak çünkü farklı sorgular için farklı sonuçlar test ediyorum.

Mockito sayfası diyor ki

val mockedList = mock[List[String]]
mockedList.get(anyInt) answers { i => "The parameter is " + i.toString } 

Bu java değil ve java'ya nasıl tercüme edeceğimi ya da olanı bir işleve nasıl geçireceğimi bilmiyorum.


Senin için neyin başarısız olduğunu tam olarak anladığımdan emin değilim. Çağrınız Mockito.when(reader.document(666)).thenReturn(document(fakeIndex(666))sizin için sahte nesneyi ayarlamalıdır. Aradığınızda ne olur reader.document(666)?
kafeinli

666 iyi çalışıyor. Ancak, belirli bir X sayısını geçebilmek ve fakeIndex (X) sonucunu almak istiyorum. Sorguları test etmek için çok sayıda potansiyel dokümanım var ve hepsini girmek istemiyorum.
nflacco

Yanıtlar:


104

Mockito'yu hiç kullanmadım ama öğrenmek istiyorum, işte burada. Benden daha az ipucu olmayan biri cevap verirse, önce cevabını deneyin!

Mockito.when(reader.document(anyInt())).thenAnswer(new Answer() {
 public Object answer(InvocationOnMock invocation) {
     Object[] args = invocation.getArguments();
     Object mock = invocation.getMock();
     return document(fakeIndex((int)(Integer)args[0]));
     }
 });

2
Mockito'nun sağ tarafındaki bağlantıyı fark ettim : Bir yöntemin kendisine iletilen bir argüman döndürmesini sağlama . Görünüşe göre yakın değildim.
Ed Staub

güçlü kullanıcı itibarı (666) ile orijinal soru korelasyonu! Bu çok iyi çalıştı. Eşyaları derlemek için yaptığım tek değişiklik, Object cevabının (InvocationOnMock çağrısı) önüne getirildi ....
nflacco

54

ArgumentCaptors'a göz atın:

https://site.mockito.org/javadoc/current/org/mockito/ArgumentCaptor.html

ArgumentCaptor<Integer> argument = ArgumentCaptor.forClass(Integer.class);
Mockito.when(reader.document(argument.capture())).thenAnswer(
  new Answer() {
    Object answer(InvocationOnMock invocation) {
      return document(argument.getValue());
    }
  });

3
Vay canına, ArgumentCaptorsaplama için s kullanabileceğini bilmiyordum . Yine de bu bağlantıda bununla ilgili büyük bir uyarı var. Dikkatle ilerle.
einnocent

3
Evet, haklısın. Ele geçirenler yalnızca doğrulamalarla kullanılmalıdır.
qualidafial

41

Testte yürütmeyi sağlamak için ArgumentCaptor ile birlikte doğrulamak () ve argümanları değerlendirmek için ArgumentCaptor kullanmak isteyebilirsiniz:

ArgumentCaptor<Document> argument = ArgumentCaptor.forClass(Document.class);
verify(reader).document(argument.capture());
assertEquals(*expected value here*, argument.getValue());

Argümanın değerine argument.getValue () aracılığıyla daha fazla manipülasyon / kontrol veya yapmak istediğiniz her şey için açıkça erişilebilir.


2
en iyi cevap: doğrudan, anlaşılması kolay
Radu Cugut

Soruya cevap vermiyor. Soru Mockito ile ilgili. Ne zaman ve doğrulama değil.
seBaka28

@ seBaka28 argümanlar elde etmenin en iyi çözümü argümanı kapmaktır. ArgumentCaptors'ın Mockito'nun yazarları tarafından doğrulama ile kullanılması şiddetle tavsiye edilir, bu nedenle tam bir perspektif cevap vermek istedim. kendiniz için bunları kullanmamayı seçerseniz, bu sizin seçiminizdir, ancak tavsiye edilmez. DÜZENLEME: Bunun bir olumsuz oyu nasıl haklı çıkardığını anlamıyorum, ama bu aynı zamanda sizin seçiminiz.
fl0w

1
Çünkü soruya cevap vermiyor. Evet, ArgumentCaptor, argümanı yakalamak istediğinizde harikadır, ancak onu when (...) ile birlikte kullanamazsınız. ThenReturn () ki bu OP'nin yapmaya çalıştığı şeydir: Belirli bir parametreye dayalı, alay konusu bir hizmet belirli bir nesneyi döndürmesi gerekiyor.
seBaka28

1
@YuraHoy, doğrula kullandığınızda standart bir hata mesajıdır ve nesne veya yöntem doğrulamayı beklediğinizden daha sık çağrılır. Beklenti sayısını, times (n) argümanını aşağıdaki gibi ekleyerek değiştirebilirsiniz: doğrulama (okuyucu, times (5)) - bu 5 etkileşim beklenir. Referans için lütfen bakınız: baeldung.com/mockito-verify
fl0w

14

Java 8 ile bu şöyle bir şey olabilir:

Mockito.when(reader.document(anyInt())).thenAnswer(
  (InvocationOnMock invocation) -> document(invocation.getArguments()[0]));

Bunun documentbir harita olduğunu varsayıyorum .

Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.