2011-08-31 8 views
7

यदि मैं किसी ऑब्जेक्ट का एक नया उदाहरण वापस करने के लिए एक विधि का नकल करता हूं, तो मैं लौटा हुआ उदाहरण कैप्चर कैसे कर सकता हूं?मॉकिटो: क्या स्टब किए गए विधि के वापसी मूल्य को कैप्चर करने का कोई तरीका है?

उदा .:

when(mock.someMethod(anyString())).thenAnswer(new Answer() { 
    Object answer(InvocationOnMock invocation) { 
     Object[] args = invocation.getArguments(); 
     Object mock = invocation.getMock(); 
     return new Foo(args[0]) 
    } 
}); 

जाहिर है, मैं प्रकार फू के एक क्षेत्र हो सकता है और answer अंदर यह नया उदाहरण के लिए सेट है, लेकिन वहाँ एक अच्छा तरीका है? ArgumentCaptor की तरह कुछ?

उत्तर

6

ऐसा लगता है कि करने के लिए तो Answer उदाहरणों का निरीक्षण करने और notfications हर बार answer विधि कहा जाता है (जो एक नया Foo के निर्माण से चलाता है) प्राप्त करना चाहते हैं।

public abstract class ObservableAnswer implements Answer { 
    private Listener[] listeners; // to keep it very simple... 

    public ObservableAnswer(Listener...listeners) { 
    this.listeners = listeners; 
    } 

    @Override 
    public Object answer(InvocationOnMock invocation) { 
    Object answer = observedAnswer(invocation); 
    for (Listener listener:listeners) { 
     listener.send(answer); 
    } 
    return answer; 
    } 

    // we'll have to implement this method now 
    public abstract Object observedAnswer(InvocationOnMock invocation); 
} 

इरादे से उपयोग: तो क्यों एक ObservableAnswer वर्ग का आविष्कार नहीं

Listener[] myListenerns = getListeners(); // some magic (as usual) 
when(mock.someMethod(anyString())).thenAnswer(new ObservableAnswer(myListeners) { 
    Object observedAnswer(InvocationOnMock invocation) { 
     Object[] args = invocation.getArguments(); 
     Object mock = invocation.getMock(); 
     return new Foo(args[0]) 
    } 

}); 
9

मैं इसी तरह कुछ करना चाहता था, लेकिन एक नकली के बजाय एक जासूसी वस्तु के साथ। विशेष रूप से, एक जासूसी वस्तु दी गई, मैं वापसी मूल्य पर कब्जा करना चाहता हूं। Andreas_D के उत्तर के आधार पर, मैं यहां आया हूं।

public class ResultCaptor<T> implements Answer { 
    private T result = null; 
    public T getResult() { 
     return result; 
    } 

    @Override 
    public T answer(InvocationOnMock invocationOnMock) throws Throwable { 
     result = (T) invocationOnMock.callRealMethod(); 
     return result; 
    } 
} 

इरादे से उपयोग:

// spy our dao 
final Dao spiedDao = spy(dao); 
// instantiate a service that does some stuff, including a database find 
final Service service = new Service(spiedDao); 

// let's capture the return values from spiedDao.find() 
final ResultCaptor<QueryResult> resultCaptor = new ResultCaptor<>(); 
doAnswer(resultCaptor).when(spiedDao).find(any(User.class), any(Query.class)); 

// execute once 
service.run(); 
assertThat(resultCaptor.getResult()).isEqualTo(/* something */); 

/// change conditions /// 

// execute again 
service.run(); 
assertThat(resultCaptor.getResult()).isEqualTo(/* something different */);