W.Del
W.Del

Reputation: 21

Spring Boot 2.0.4 - H2 Database - @SpringBootTest - Failing on Caused by: org.h2.jdbc.JdbcSQLException: Schema "classpath:db/schema.sql" not found

I have built an application with Spring Boot 2.0.4 and integrated with JPA.

Now I want to run some tests with h2 database, but I am unable to execute the Spring Boot tests with h2.

The exceptions are shown below:

Caused by: org.springframework.jdbc.datasource.init.UncategorizedScriptException: Failed to execute database script; nested exception is org.springframework.jdbc.CannotGetJdbcConnectionException: Failed to obtain JDBC Connection; nested exception is org.h2.jdbc.JdbcSQLException: Schema "classpath:db/schema.sql" not found [90079-197]
    at org.springframework.jdbc.datasource.init.DatabasePopulatorUtils.execute(DatabasePopulatorUtils.java:58)
    at org.springframework.boot.autoconfigure.jdbc.DataSourceInitializer.runScripts(DataSourceInitializer.java:210)
    at org.springframework.boot.autoconfigure.jdbc.DataSourceInitializer.createSchema(DataSourceInitializer.java:104)
    at org.springframework.boot.autoconfigure.jdbc.DataSourceInitializerInvoker.afterPropertiesSet(DataSourceInitializerInvoker.java:64)
    at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.invokeInitMethods(AbstractAutowireCapableBeanFactory.java:1758)
    at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.initializeBean(AbstractAutowireCapableBeanFactory.java:1695)
    ... 74 more
Caused by: org.springframework.jdbc.CannotGetJdbcConnectionException: Failed to obtain JDBC Connection; nested exception is org.h2.jdbc.JdbcSQLException: Schema "classpath:db/schema.sql" not found [90079-197]
    at org.springframework.jdbc.datasource.DataSourceUtils.getConnection(DataSourceUtils.java:81)
    at org.springframework.jdbc.datasource.init.DatabasePopulatorUtils.execute(DatabasePopulatorUtils.java:46)
    ... 79 more
Caused by: org.h2.jdbc.JdbcSQLException: Schema "classpath:db/schema.sql" not found [90079-197]
    at org.h2.message.DbException.getJdbcSQLException(DbException.java:357)
    at org.h2.message.DbException.get(DbException.java:179)
    at org.h2.message.DbException.get(DbException.java:155)
    at org.h2.engine.Database.getSchema(Database.java:1808)
    at org.h2.engine.Session.setCurrentSchemaName(Session.java:1317)
    at org.h2.jdbc.JdbcConnection.setSchema(JdbcConnection.java:1989)
    at com.zaxxer.hikari.pool.PoolBase.setupConnection(PoolBase.java:423)
    at com.zaxxer.hikari.pool.PoolBase.newConnection(PoolBase.java:370)
    at com.zaxxer.hikari.pool.PoolBase.newPoolEntry(PoolBase.java:194)
    at com.zaxxer.hikari.pool.HikariPool.createPoolEntry(HikariPool.java:460)
    at com.zaxxer.hikari.pool.HikariPool.checkFailFast(HikariPool.java:534)
    at com.zaxxer.hikari.pool.HikariPool.<init>(HikariPool.java:115)
    at com.zaxxer.hikari.HikariDataSource.getConnection(HikariDataSource.java:112)
    at org.springframework.jdbc.datasource.DataSourceUtils.fetchConnection(DataSourceUtils.java:151)
    at org.springframework.jdbc.datasource.DataSourceUtils.doGetConnection(DataSourceUtils.java:115)
    at org.springframework.jdbc.datasource.DataSourceUtils.getConnection(DataSourceUtils.java:78)
    ... 80 more

And my application-test.properties is:

spring.datasource.driver-class-name=org.h2.Driver
spring.datasource.jdbc-url=jdbc:h2:mem:test
spring.datasource.schema=classpath:db/schema.sql
spring.datasource.data=classpath:db/data.sql
spring.datasource.initialization-mode=always


spring.jpa.show-sql=true
spring.jpa.hibernate.ddl-auto=none
logging.level.org.hibernate.SQL=debug
spring.jpa.database-platform=org.hibernate.dialect.H2Dialect

These exceptions happened when I executed schema.sql, but h2 want to execute this script in schema named "classpath:schema.sql" which is specified in spring.datasource.schema.

Upvotes: 2

Views: 4554

Answers (3)

Nikhil Singh
Nikhil Singh

Reputation: 1

Set spring.jpa.defer-datasource-initialization = true in your application.properties file.

Upvotes: 0

Wilder Valera
Wilder Valera

Reputation: 1019

Your property should looks like this:

spring.datasource.schema=db/schema.sql

In the class DataSourceInitializer you can see how it is used

public boolean createSchema() {
    List<Resource> scripts = getScripts("spring.datasource.schema",
            this.properties.getSchema(), "schema");
    if (!scripts.isEmpty()) {
        if (!isEnabled()) {
            logger.debug("Initialization disabled (not running DDL scripts)");
            return false;
        }
        String username = this.properties.getSchemaUsername();
        String password = this.properties.getSchemaPassword();
        runScripts(scripts, username, password);
    }
    return !scripts.isEmpty();
}

the method getScripts add the classpath String:

private List<Resource> getScripts(String propertyName, List<String> resources,
        String fallback) {
    if (resources != null) {
        return getResources(propertyName, resources, true);
    }
    String platform = this.properties.getPlatform();
    List<String> fallbackResources = new ArrayList<>();
    fallbackResources.add("classpath*:" + fallback + "-" + platform + ".sql");
    fallbackResources.add("classpath*:" + fallback + ".sql");
    return getResources(propertyName, fallbackResources, false);
}

So you don't have to set it.

Upvotes: 1

Alien
Alien

Reputation: 15878

It is pretty clear by the exception Not Found that Spring boot is not able to find the schema.sql file.

Simply copy the src/main/resources/db/schema.sql to src/test/resources/db/schema.sql.

Upvotes: 1

Related Questions