2

I'm doing an integration test in spring and in this example I testing a service layer.

I have a problem where during the addition test in the service, rollback not working, and always add an item to the base ,but not delete it.

I put annotation @ Transactional and @ TestPropertySource on test class, also have application-test.properties and the test is successful but the rollback is not executed and a new item is always added to the test database.

My test class and test method for add address(last one):

@RunWith(SpringRunner.class)
@SpringBootTest(classes = TicketServiceApplication.class)
@Transactional
@TestPropertySource("classpath:application-test.properties")
public class AddressServiceIntegrationTest {


@Autowired
private AddressService addressService;

@Autowired
private AddressRepository addressRepository;

@Test
public void findAllSuccessTest(){
    List<Address> result = addressService.finfAllAddress();

    assertNotNull(result);
    assertFalse(result.isEmpty());
    assertEquals(2, result.size());
}

@Test
public void findOneAddressExistTest_thenReturnAddress(){
    Long id = AddressConst.VALID_ID_ADDRESS;
    Address a = addressService.findOneAddress(id);
    assertEquals(id, a.getId());
}

@Test(expected = EntityNotFoundException.class)
public void findOneAddressNotExistTest_thenThrowException(){
    Long id = AddressConst.NOT_VALID_ID_ADDRESS;
    Address a = addressService.findOneAddress(id);
}

@Test
public void addAddressSuccessTest(){

    int sizeBeforeAdd = addressRepository.findAll().size();

    Address address = AddressConst.newAddressToAdd();
    Address result = addressService.addAddress(address);

    int sizeAfterAdd  = addressRepository.findAll().size();

    assertNotNull(result);
    assertEquals(sizeBeforeAdd+1, sizeAfterAdd);
    assertEquals(address.getCity(), result.getCity());
    assertEquals(address.getState(), result.getState());
    assertEquals(address.getNumber(), result.getNumber());
    assertEquals(address.getLatitude(), result.getLatitude());
    assertEquals(address.getLongitude(), result.getLongitude());
    assertEquals(address.getStreet(), result.getStreet());
}
}

My application-test.properties :

spring.datasource.url= jdbc:mysql://localhost:3306/kts_test&useSSL=false&
useUnicode=true&characterEncoding=utf8
spring.datasource.username = root
spring.datasource.password = root
spring.jpa.show-sql = true
spring.datasource.driver-class-name=com.mysql.cj.jdbc.Driver

And when execute add address test, every time in my kts_test data base ( db used for testing) is added new item and not rollback.

This is a log from the console where you can see that the rollback was called but did not execute, because when I refresh the database after the test the new item was left, it was not deleted.

INFO 10216 --- [           main] o.s.t.c.transaction.TransactionContext   : Rolled back transaction for test: [DefaultTestContext@3e58a80e testClass = AddressServiceIntegrationTest, testInstance = com.ftn.services.address.AddressServiceIntegrationTest@4678ec43, testMethod = addAddressSuccessTest@AddressServiceIntegrationTest, testException = [null],...

Lastly, to write that I tried @Transactional above methods, I also tried @ Rollback above methods or @ Rollback (true), tried changing application-test.properties and I no longer know what the error might be.

If anyone can help I would be grateful. Thank you.

jovanKg
  • 35
  • 7

1 Answers1

2

Hibernate is by default creating tables with MyISAM storage engine - this engine does not support transactions. You need to have InnoDB tables:

  • Either manage your DB migrations manually with a tool like Flyway (imho preferred option so you can have a complete control) and turn off recreating database in tests.
  • Or set the correct engine in configuration:
spring.jpa.properties.hibernate.dialect.storage_engine=innodb

OR (deprecated)

spring.jpa.properties.hibernate.dialect=org.hibernate.dialect.MySQL5InnoDBDialect
Josef Cech
  • 2,115
  • 16
  • 17
  • will there be problems with the application if i change the engine to innodb in both data base and the application base and the test base? – jovanKg Mar 07 '20 at 19:59
  • What problems do you have in mind? If you are concerned about a different behavior / capabilities there are some answered questions about this: https://stackoverflow.com/questions/12614541/whats-the-difference-between-myisam-and-innodb Hopefully it will help. .) – Josef Cech Mar 07 '20 at 20:12