Hibernate and testcontainers

Viewed 519

I need to run my tests in docker containers. I have Testcontainers lib for this. Besides that I use hibernate. Also, I use Flyway to run some initial SQL scripts. I'm new in Testcontainers and Hibernate and don't understand why I get "Relation not found exception". This is how my app organized:

Abstract test for initializing container:

@ActiveProfiles("test")
@SpringBootTest(webEnvironment = SpringBootTest.WebEnvironment.RANDOM_PORT)
@AutoConfigureTestDatabase(replace = AutoConfigureTestDatabase.Replace.NONE)
@ContextConfiguration(initializers = AbstractIT.DockerPostgreDataSourceInitializer.class)
@Testcontainers
public class AbstractIT {

    public static PostgreSQLContainer<?> postgreDBContainer = new PostgreSQLContainer<> 
    ("postgres:12.2");

    static {
        postgreDBContainer.start();
    }

    public static class DockerPostgreDataSourceInitializer implements 
        ApplicationContextInitializer<ConfigurableApplicationContext> {

        @Override
        public void initialize(ConfigurableApplicationContext applicationContext) {

            TestPropertySourceUtils.addInlinedPropertiesToEnvironment(
                    applicationContext,
                    "spring.datasource.url=" + postgreDBContainer.getJdbcUrl(),
                    "spring.datasource.username=" + postgreDBContainer.getUsername(),
                    "spring.datasource.password=" + postgreDBContainer.getPassword()
            );
        }
    }
}

My test for "create" function that extends abstract AbstractIT:

@SpringBootTest
class JdbcGroupDaoTest extends AbstractIT {
    @Autowired
    private JdbcGroupDao jdbcGroupDao;

    @Test
    void create() throws Exception {
        jdbcGroupDao.setFactory(Persistence.createEntityManagerFactory("university-test"));
        Group group = new Group("Test group");
        Group expected = new Group(1L, "Test group");
        Group actual = jdbcGroupDao.save(group);
        assertEquals(expected, actual);
    }
}

Class under test:

@Component
public class JdbcGroupDao extends JdbcAbstractDao<Group, Long> implements GroupDao {
    private EntityManagerFactory factory ;
    private static final Logger LOGGER = LoggerFactory.getLogger(JdbcGroupDao.class);

@Override
public void setFactory(EntityManagerFactory factory){
    this.factory = factory;
}

@Override
protected Group create(Group group) {
    if(factory==null){
        factory=Persistence.createEntityManagerFactory("university");
    }
    EntityManager entityManager = factory.createEntityManager();
    entityManager.getTransaction().begin();
    entityManager.persist(group);
    entityManager.getTransaction().commit();
    entityManager.close();
    entityManager.flush();
    factory.close();
    return group;
}

My config file for Hibernate:

<persistence version="2.1" xmlns="http://xmlns.jcp.org/xml/ns/persistence"
         xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
         xsi:schemaLocation="http://xmlns.jcp.org/xml/ns/persistence
    http://xmlns.jcp.org/xml/ns/persistence/persistence_2_1.xsd">
<persistence-unit name="university">
    <properties>
        <property name="javax.persistence.jdbc.url" 
value="jdbc:postgresql://localhost:5432/university" />
        <property name="javax.persistence.jdbc.user" value="admin" />
        <property name="javax.persistence.jdbc.password" value="admin" />
        <property name="javax.persistence.jdbc.driver" value="org.postgresql.Driver" />
        <property name="hibernate.show_sql" value="true" />
        <property name="hibernate.format_sql" value="true" />
    </properties>
</persistence-unit>

<persistence-unit name="university-test">
    <properties>
        <property name="javax.persistence.jdbc.driver" 
value="org.testcontainers.jdbc.ContainerDatabaseDriver"/>
        <property name="javax.persistence.jdbc.url" value="jdbc:tc:postgresql:9.6.8:///university"/>
        <property name="javax.persistence.jdbc.user" value="admin" />
        <property name="javax.persistence.jdbc.password" value="admin" />
    </properties>
</persistence-unit>

</persistence>

The error message:

Caused by: org.postgresql.util.PSQLException: ERROR: relation "groups" does not exist

I have two persistence units here because this is the only way I found to prevent hibernate from altering data in real DB. I believe this is the main reason why I got my error. Though I don't know how to fix it. If you need more info about my code, feel free to ask, I will add whatever you need into my post. Thanks in advance.

EDIT: Flyway init. sql file. (added code related to "groups" only):

create table groups
(
    id    serial
        constraint groups_pkey
            primary key,
    title varchar(100)
);
alter table groups
    add constraint uq_groups_title UNIQUE
        (
         title
            );
0 Answers
Related