2017-10-11 6 views
0

J'essaye d'écrire un test JUnit avec injection de dépendances de service.Test JUnit du serveur Ratpack avec injection de Guice

protected MainClassApplicationUnderTest aut = new MainClassApplicationUnderTest(App.class) { 
    @Override 
    protected void addImpositions(final ImpositionsSpec impositions) { 
     impositions.add(UserRegistryImposition.of(appRegistry -> { 
      // Allow modifying Injector in tests 
      return appRegistry.join(Guice.registry(injector)); 
     })); 
    } 
}; 

private Injector injector = com.google.inject.Guice.createInjector(new Module()); 

@Before 
public void setup() { 
    injector.injectMembers(this); 
} 

@After 
public void tearDown() { 
    aut.close(); 
} 

, puis en utilisant les services injectés dans mes classes de test:

@Inject 
private UserService userService; 

Cela fonctionnait très bien jusqu'à ce que je commencé à ajouter la persistance à mon application avec HikariModule. Maintenant, la création de registre Guice est un peu plus complexe:

.join(Guice.registry(b -> b 
     .module(HikariModule.class, hikariConfig -> { 
      final String dbUrl = System.getenv("JDBC_DATABASE_URL"); 
      hikariConfig.setJdbcUrl(dbUrl); 
     }) 
     .module(Module.class) 
     .bind(DbMigrator.class) 
    ).apply(r)) 

Parce que mon registre se compose maintenant de plusieurs modules si j'ai un service qui dépend de la classe DataSource provenant HikariModule injection de Guice échoue dans les tests.

Mon but est de permettre l'écriture de tests de la manière suivante:

@Inject // <- not required can be done in @Before method 
private UserService userService; // <- Inject it somehow from Application under test 

@Test 
public void testUser() { 
    final Result<User, String> userResult = userService.create(new User.Registration()); 
    final ReceivedResponse res = aut.getHttpClient().get("https://stackoverflow.com/users/" + user.userId); 
    assertEquals(200, res.getStatusCode()); 
} 

Quelle est la bonne approche de l'injection de dépendances de services dans les tests? Je préférerais de loin réutiliser des modules de guice de MainClassApplicationUnderTest plutôt que de créer le mien et les surcharger.

Répondre

0

Après un certain temps à lutter contre ce problème et l'aide de Ratpack mou, j'ai réussi à retirer ce problème.

Tout d'abord, nous devons capturer notre registre d'applications dans la variable locale.

private Registry appRegistry; 

protected MainClassApplicationUnderTest aut = new MainClassApplicationUnderTest(App.class) { 
    @Override 
    protected void addImpositions(final ImpositionsSpec impositions) { 
     impositions.add(UserRegistryImposition.of(r -> { 
      appRegistry = r; 
      return Registry.empty(); 
     })); 
    } 
}; 

Il s'avère qu'il existe une méthode astucieuse qui démarre l'application. Donc, lors de l'injection de la classe, nous saurons que Registry ne sera pas nul et nous pouvons injecter des classes. Ensuite, dans les classes de test, nous pouvons simplement injecter n'importe quelle classe qui est présente dans le registre

protected <T> T inject(final Class<T> classOf) { 
    aut.getAddress(); 
    return appRegistry.get(classOf); 
} 

final UserService userService = inject(UserService.class); 
// OR 
final DataSource dataSource = inject(DataSource.class);