Una delle ragioni per cui la primavera è descritta come "test-friendly" è perché potrebbe essere facile solo il nuovo o roba finta nel test dell'unità.
In alternativa abbiamo usato la seguente configurazione con grande successo, e penso che è abbastanza vicino a quello che si vuole, vorrei fortemente raccomando:
Per tutti i fagioli che necessitano di diverse implementazioni in contesti diversi, passare al cablaggio basato sull'annotazione. Puoi lasciare gli altri così come sono.
Implementare la seguente serie di annotazioni
<context:component-scan base-package="com.foobar">
<context:include-filter type="annotation" expression="com.foobar.annotations.StubRepository"/>
<context:include-filter type="annotation" expression="com.foobar.annotations.TestScopedComponent"/>
<context:exclude-filter type="annotation" expression="org.springframework.stereotype.Repository"/>
</context:component-scan>
Poi di annotare le vivo implementazioni con @Repository, il vostro stub implementazioni con @StubRepository, qualsiasi codice che dovrebbe essere presente nel dispositivo di unità di test SOLO con @TestScopedComponent. Potresti incorrere in un paio di ulteriori annotazioni, ma sono un ottimo inizio.
Se hai un sacco di spring.xml, probabilmente avrai bisogno di creare alcuni nuovi file xml primaverili che fondamentalmente contengono solo le definizioni di scansione dei componenti. Normalmente dovresti semplicemente aggiungere questi file al tuo normale elenco @ContextConfiguration. La ragione di ciò è dovuta al fatto che spesso si ottengono configurazioni diverse delle scansioni del contesto (fiducia in me, corrisponderà a almeno 1 altra annotazione se esegui test web, che rende 4 combinazioni pertinenti)
quindi si utilizza fondamentalmente la
@ContextConfiguration(locations = { "classpath:/path/to/root-config.xml" })
@RunWith(SpringJUnit4ClassRunner.class)
si noti che questa impostazione non non consentono di avere alternati combinazioni di dati stub/live. L'abbiamo provato, e penso che ciò abbia provocato un casino che non consiglierei a nessuno;) o colleghiamo il set completo di stub o il set completo di servizi live.
Principalmente usiamo le dipendenze di stub auto-cablate quando testiamo gui vicino a cose in cui le dipendenze sono in genere piuttosto consistenti. Nelle aree più pulite del codice utilizziamo test unitari più regolari.
Nel nostro sistema abbiamo i seguenti file XML per il componente-scan:
- per la produzione di web regolare
- per iniziare web con mozziconi solo
- per i test di integrazione (in JUnit)
- per i test unitari (in junit)
- per prove web selenio (a) junit
Ciò significa che abbiamo totalmente 5 diverse configurazioni a livello di sistema con cui possiamo avviare l'applicazione. Poiché usiamo solo annotazioni, la molla è abbastanza veloce da rendere autowire anche quei test unitari che vogliamo cablati. So che non è tradizionale, ma è davvero grandioso.
Out test di integrazione gestita con piena messa a punto dal vivo, e una o due volte ho deciso di ottenere davvero pragmatico e vogliono avere un 5 cablaggi live e un singolo finto:
public class HybridTest {
@Autowired
MyTestSubject myTestSubject;
@Test
public void testWith5LiveServicesAndOneMock(){
MyServiceLive service = myTestSubject.getMyService();
try {
MyService mock = EasyMock.create(...)
myTestSubject.setMyService(mock);
.. do funky test with lots of live but one mock object
} finally {
myTestSubject.setMyService(service);
}
}
}
So che il test i puristi mi staranno addosso per questo. Ma a volte è solo una soluzione molto pragmatica che risulta essere molto elegante quando l'alternativa sarebbe davvero brutta. Di nuovo è di solito in quelle zone spericolate.
La primavera rende semplice il test dell'unità. Questa è la parte che ti manca: stai facendo un test di integrazione e non un test unitario. In un vero Unit Test, qualsiasi bean dipendente dovrebbe essere un mock, perché si sta solo testando un'unità e non un intero sistema. – bpapa
Come * unit test * un'applicazione primaverile: http://confessionsofanagilecoach.blogspot.com/2016/05/unit-testing-spring-applications.html –