@SpringBootTest com @Sql: ordem de execução do script e inicialização do contexto

9

Eu tenho testes de integração que são executados no topo do banco de dados de inmemory. A assinatura de cada teste parece mais ou menos assim:

@RunWith(SpringRunner.class)
@SpringBootTest
@Sql("/clean-data-in-all-tables.sql")
public class SomeTest { 
    @Test
    public void shouldDoSomehting() {}
}

Durante a inicialização do contexto de teste, o esquema do banco de dados é recriado pelo Hibernate:

spring:
  jpa:
    hibernate:
      ddl-auto: create-drop

Espero que o script sql seja executado após a inicialização do contexto e após a geração do esquema do db. No entanto, em alguns casos clean-data-in-all-tables.sql é executado antes da geração do esquema e falha porque espera tabelas que ainda não foram criadas.

Eu tenho mais de 500 testes escritos da maneira que expliquei e todos eles estavam funcionando bem até que eu adicionei mais alguns testes semelhantes.

Os testes falham quando eu os executo juntos via Gradle ou IntelliJ. Observe que os testes com falha não são os testes que foram adicionados recentemente. Estes são os testes antigos totalmente não relacionados aos que eu adicionei. O que também é estranho é que os testes falhados funcionam bem se eu os executar um por um através do IntelliJ.

Parece um bug do spring-boot, mas eu ainda tento encontrar uma maneira de contornar isso. Ao mesmo tempo eu tentei inúmeras coisas para resolver o problema, mas nenhum deles foi útil.

Por favor, compartilhe suas ideias sobre o que poderia ajudar e o que poderia estar errado com o meu código.

ATUALIZAÇÃO: Encontrou a solução alternativa: alterar o spring.jpa.hibernate.ddl-auto de create-drop para create resolve o problema.

Mas a questão ainda está em aberto qual é a razão de tal comportamento estranho?

    
por Oleksandr Shpota 11.05.2017 в 13:42
fonte

1 resposta

2

Uma possível solução (não tenho certeza se você está aberto para usar o DBUnit) pode ser:

1) Criar Teste de Integração do Repositório Resumo:

@TestExecutionListeners({DbUnitTestExecutionListener.class})
@SpringApplicationConfiguration(classes = Application.class)
@DirtiesContext
public abstract class AbstractRepositoryIT extends AbstractTransactionalJUnit4SpringContextTests {
}

2) Crie um teste de integração "real":

@DatabaseSetup(SomeEntityRepositoryIT.DATASET)
@DatabaseTearDown(type = DatabaseOperation.DELETE_ALL, value = {"dataset.xml})
public class SomeEntityRepositoryIT extends AbstractRepositoryIT {
...
}

No arquivo dataset.xml você pode configurar o estado inicial para seus testes, etc ... Mais informações podem ser encontradas aqui

    
por nick79 11.05.2017 / 14:24
fonte