DataAccessException при использовании DAO в Jooq - PullRequest
0 голосов
/ 25 октября 2019

Я хочу добавить сгенерированный Pojo в базу данных, используя DAO. Но я получаю исключение и понятия не имею, как его решить.

Я пытался добавить Public.Troop перед каждой таблицей.

Вставка отряда в использование DAO:

TroopDao dao = new TroopDao(new DefaultConfiguration().set(SQLDialect.SQLITE).set(database.getConnection()));
Troop initial = new Troop(1, 100, 120, 120.2, 11.2, 12.0, 13.0, 6245.0, 1534.0, 1364.0, 121235.3, 125.3, 51.3);
dao.insert(initial);

Используемый файл базы данных:

CREATE TABLE IF NOT EXISTS TROOP(
    id INTEGER PRIMARY KEY AUTOINCREMENT,
    current_health INTEGER NOT NULL,
    max_health INTEGER NOT NULL,
    pos_x DOUBLE NOT NULL,
    pos_y DOUBLE NOT NULL,
    normal_speed DOUBLE NOT NULL,
    street_speed DOUBLE NOT NULL,
    difficult_terrain_speed DOUBLE NOT NULL,
    close_combat_range DOUBLE NOT NULL,
    ranged_combat_range DOUBLE NOT NULL,
    normal_view_distance DOUBLE NOT NULL,
    disadvantaged_view_distance DOUBLE NOT NULL,
    advantaged_view_distance DOUBLE NOT NULL
);

CREATE TABLE IF NOT EXISTS ARMY(
    id INTEGER,
    hq INTEGER,
    troop INTEGER,
    FOREIGN KEY(hq) REFERENCES TROOP(id),
    FOREIGN KEY(troop) REFERENCES TROOP(id),
    UNIQUE(hq, troop),
    PRIMARY KEY (id, hq, troop)
);

Поколение JOOQ, я также попытался unqualifiedSchema = main:

        Configuration configuration = new Configuration()
                .withGenerator(new Generator()
                        .withDatabase(new Database()
                                .withName("org.jooq.meta.extensions.ddl.DDLDatabase")
                                .withIncludes("ARMY | TROOP")
                                .withOutputSchemaToDefault(Boolean.TRUE)
                                .withProperties(new Property()
                                                .withKey("unqualifiedSchema")
                                                .withValue("none"),
                                        new Property()
                                                .withKey("scripts")
                                                .withValue("/db/schema.sql")))
                        .withGenerate(new Generate()
                                .withPojos(Boolean.TRUE)
                                .withDeprecationOnUnknownTypes(Boolean.FALSE)
                                .withImmutableInterfaces(Boolean.TRUE)
                                .withDaos(Boolean.TRUE))
                        .withTarget(new Target()
                                .withPackageName("me.leslie.generals.server.persistence.jooq")
                                .withDirectory("Generals-Server/src/main/java")));

        GenerationTool.generate(configuration);

Класс базы данных просто синглтон, который возвращает основное соединение с базой данных:

@EqualsAndHashCode
@ToString
@Getter
public class Database {
    public static final String DEFAULT_DB_URL = "jdbc:sqlite:";
    @NonNull
    private final String url;
    private final Connection connection;

    private static Database instance;

    public static Database get() {
        if(instance == null){
            instance = new Database(DEFAULT_DB_URL);
        }
        return instance;
    }

    private Database(String url) {
        try {
            this.connection = DriverManager.getConnection(url);
        } catch (SQLException e) {
            throw new InitializationException("Could not get Database connection", e);
        }
        initialize();
        this.url = url;
    }


    private void initialize() {
        final String troopSchema = "CREATE TABLE IF NOT EXISTS TROOP(" +
                "id INTEGER PRIMARY KEY AUTOINCREMENT," +
                "current_health INTEGER NOT NULL," +
                "max_health INTEGER NOT NULL," +
                "pos_x DOUBLE NOT NULL," +
                "pos_y DOUBLE NOT NULL," +
                "normal_speed DOUBLE NOT NULL," +
                "street_speed DOUBLE NOT NULL," +
                "difficult_terrain_speed DOUBLE NOT NULL," +
                "close_combat_range DOUBLE NOT NULL," +
                "ranged_combat_range DOUBLE NOT NULL," +
                "normal_view_distance DOUBLE NOT NULL," +
                "disadvantaged_view_distance DOUBLE NOT NULL," +
                "advantaged_view_distance DOUBLE NOT NULL" +
                ");";


        final String armySchema = "CREATE TABLE IF NOT EXISTS ARMY(" +
                "id INTEGER," +
                "hq INTEGER," +
                "troop INTEGER," +
                "FOREIGN KEY(hq) REFERENCES TROOP(id)," +
                "FOREIGN KEY(troop) REFERENCES TROOP(id)," +
                "UNIQUE(hq, troop)," +
                "PRIMARY KEY (id, hq, troop)" +
                ");";

        try (PreparedStatement sql = connection.prepareStatement(troopSchema)) {
            sql.execute();


        } catch (SQLException e) {
            throw new InitializationException("Could not initialize Troops", e);
        }

        try (PreparedStatement sql = connection.prepareStatement(armySchema)) {
            sql.execute();
        } catch (SQLException e) {
            throw new InitializationException("Could not initialize Armies", e);
        }
    }
}

Ошибка, когда я использую БД на основе файлов и получаю к ней доступ, кажется, что там есть необходимые таблицы:

WARNING: An illegal reflective access operation has occurred
WARNING: Illegal reflective access by org.jooq.tools.reflect.Reflect (file:/home/leslie/.m2/repository/org/jooq/jooq/3.11.11/jooq-3.11.11.jar) to constructor java.lang.invoke.MethodHandles$Lookup(java.lang.Class)
WARNING: Please consider reporting this to the maintainers of org.jooq.tools.reflect.Reflect
WARNING: Use --illegal-access=warn to enable warnings of further illegal reflective access operations
WARNING: All illegal access operations will be denied in a future release
23:32:56.084 [main] INFO org.jooq.Constants - 

@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@
@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@
@@@@@@@@@@@@@@@@  @@        @@@@@@@@@@
@@@@@@@@@@@@@@@@@@@@        @@@@@@@@@@
@@@@@@@@@@@@@@@@  @@  @@    @@@@@@@@@@
@@@@@@@@@@  @@@@  @@  @@    @@@@@@@@@@
@@@@@@@@@@        @@        @@@@@@@@@@
@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@
@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@
@@@@@@@@@@        @@        @@@@@@@@@@
@@@@@@@@@@    @@  @@  @@@@  @@@@@@@@@@
@@@@@@@@@@    @@  @@  @@@@  @@@@@@@@@@
@@@@@@@@@@        @@  @  @  @@@@@@@@@@
@@@@@@@@@@        @@        @@@@@@@@@@
@@@@@@@@@@@@@@@@@@@@@@@  @@@@@@@@@@@@@
@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@
@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@  Thank you for using jOOQ 3.11.11

23:32:56.093 [main] DEBUG org.jooq.tools.LoggerListener - Executing query          : select PUBLIC.TROOP.ID from PUBLIC.TROOP
23:32:56.099 [main] DEBUG org.jooq.tools.LoggerListener - Exception                
org.jooq.exception.DataAccessException: SQL [select PUBLIC.TROOP.ID from PUBLIC.TROOP]; [SQLITE_ERROR] SQL error or missing database (no such table: PUBLIC.TROOP)
    at org.jooq_3.11.11.SQLITE.debug(Unknown Source)
    at org.jooq.impl.Tools.translate(Tools.java:2430)
    at org.jooq.impl.DefaultExecuteContext.sqlException(DefaultExecuteContext.java:832)
    at org.jooq.impl.AbstractQuery.execute(AbstractQuery.java:364)
    at org.jooq.impl.AbstractResultQuery.fetch(AbstractResultQuery.java:323)
    at org.jooq.impl.SelectImpl.fetch(SelectImpl.java:2700)
    at me.leslie.generals.server.repository.TroopJooqRepository.nextID(TroopJooqRepository.java:47)
    at me.leslie.generals.server.repository.TroopJooqRepository.create(TroopJooqRepository.java:60)
    at java.base/java.util.stream.ReferencePipeline$3$1.accept(ReferencePipeline.java:195)
    at java.base/java.util.Spliterators$ArraySpliterator.forEachRemaining(Spliterators.java:948)
    at java.base/java.util.stream.AbstractPipeline.copyInto(AbstractPipeline.java:484)
    at java.base/java.util.stream.AbstractPipeline.wrapAndCopyInto(AbstractPipeline.java:474)
    at java.base/java.util.stream.ReduceOps$ReduceOp.evaluateSequential(ReduceOps.java:913)
    at java.base/java.util.stream.AbstractPipeline.evaluate(AbstractPipeline.java:234)
    at java.base/java.util.stream.ReferencePipeline.collect(ReferencePipeline.java:578)
    at org.jooq.lambda.SeqImpl.collect(SeqImpl.java:190)
    at me.leslie.generals.server.repository.TroopJooqRepositoryTest.initializeTroops(TroopJooqRepositoryTest.java:38)
    at me.leslie.generals.server.repository.TroopJooqRepositoryTest.getSomeTroops(TroopJooqRepositoryTest.java:152)
    at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
    at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
    at java.base/jdk.internal.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
    at java.base/java.lang.reflect.Method.invoke(Method.java:567)
    at org.junit.platform.commons.util.ReflectionUtils.invokeMethod(ReflectionUtils.java:675)
    at org.junit.jupiter.engine.execution.MethodInvocation.proceed(MethodInvocation.java:60)
    at org.junit.jupiter.engine.execution.InvocationInterceptorChain$ValidatingInvocation.proceed(InvocationInterceptorChain.java:125)
    at org.junit.jupiter.engine.extension.TimeoutExtension.intercept(TimeoutExtension.java:132)
    at org.junit.jupiter.engine.extension.TimeoutExtension.interceptTestableMethod(TimeoutExtension.java:124)
    at org.junit.jupiter.engine.extension.TimeoutExtension.interceptTestMethod(TimeoutExtension.java:74)
    at org.junit.jupiter.engine.execution.ExecutableInvoker$ReflectiveInterceptorCall.lambda$ofVoidMethod$0(ExecutableInvoker.java:115)
    at org.junit.jupiter.engine.execution.ExecutableInvoker.lambda$invoke$0(ExecutableInvoker.java:105)
    at org.junit.jupiter.engine.execution.InvocationInterceptorChain$InterceptedInvocation.proceed(InvocationInterceptorChain.java:104)
    at org.junit.jupiter.engine.execution.InvocationInterceptorChain.proceed(InvocationInterceptorChain.java:62)
    at org.junit.jupiter.engine.execution.InvocationInterceptorChain.chainAndInvoke(InvocationInterceptorChain.java:43)
    at org.junit.jupiter.engine.execution.InvocationInterceptorChain.invoke(InvocationInterceptorChain.java:35)
    at org.junit.jupiter.engine.execution.ExecutableInvoker.invoke(ExecutableInvoker.java:104)
    at org.junit.jupiter.engine.execution.ExecutableInvoker.invoke(ExecutableInvoker.java:98)
    at org.junit.jupiter.engine.descriptor.TestMethodTestDescriptor.lambda$invokeTestMethod$6(TestMethodTestDescriptor.java:202)
    at org.junit.platform.engine.support.hierarchical.ThrowableCollector.execute(ThrowableCollector.java:73)
    at org.junit.jupiter.engine.descriptor.TestMethodTestDescriptor.invokeTestMethod(TestMethodTestDescriptor.java:198)
    at org.junit.jupiter.engine.descriptor.TestMethodTestDescriptor.execute(TestMethodTestDescriptor.java:135)
    at org.junit.jupiter.engine.descriptor.TestMethodTestDescriptor.execute(TestMethodTestDescriptor.java:69)
    at org.junit.platform.engine.support.hierarchical.NodeTestTask.lambda$executeRecursively$5(NodeTestTask.java:135)
    at org.junit.platform.engine.support.hierarchical.ThrowableCollector.execute(ThrowableCollector.java:73)
    at org.junit.platform.engine.support.hierarchical.NodeTestTask.lambda$executeRecursively$7(NodeTestTask.java:125)
    at org.junit.platform.engine.support.hierarchical.Node.around(Node.java:135)
    at org.junit.platform.engine.support.hierarchical.NodeTestTask.lambda$executeRecursively$8(NodeTestTask.java:123)
    at org.junit.platform.engine.support.hierarchical.ThrowableCollector.execute(ThrowableCollector.java:73)
    at org.junit.platform.engine.support.hierarchical.NodeTestTask.executeRecursively(NodeTestTask.java:122)
    at org.junit.platform.engine.support.hierarchical.NodeTestTask.execute(NodeTestTask.java:80)
    at java.base/java.util.ArrayList.forEach(ArrayList.java:1507)
    at org.junit.platform.engine.support.hierarchical.SameThreadHierarchicalTestExecutorService.invokeAll(SameThreadHierarchicalTestExecutorService.java:38)
    at org.junit.platform.engine.support.hierarchical.NodeTestTask.lambda$executeRecursively$5(NodeTestTask.java:139)
    at org.junit.platform.engine.support.hierarchical.ThrowableCollector.execute(ThrowableCollector.java:73)
    at org.junit.platform.engine.support.hierarchical.NodeTestTask.lambda$executeRecursively$7(NodeTestTask.java:125)
    at org.junit.platform.engine.support.hierarchical.Node.around(Node.java:135)
    at org.junit.platform.engine.support.hierarchical.NodeTestTask.lambda$executeRecursively$8(NodeTestTask.java:123)
    at org.junit.platform.engine.support.hierarchical.ThrowableCollector.execute(ThrowableCollector.java:73)
    at org.junit.platform.engine.support.hierarchical.NodeTestTask.executeRecursively(NodeTestTask.java:122)
    at org.junit.platform.engine.support.hierarchical.NodeTestTask.execute(NodeTestTask.java:80)
    at java.base/java.util.ArrayList.forEach(ArrayList.java:1507)
    at org.junit.platform.engine.support.hierarchical.SameThreadHierarchicalTestExecutorService.invokeAll(SameThreadHierarchicalTestExecutorService.java:38)
    at org.junit.platform.engine.support.hierarchical.NodeTestTask.lambda$executeRecursively$5(NodeTestTask.java:139)
    at org.junit.platform.engine.support.hierarchical.ThrowableCollector.execute(ThrowableCollector.java:73)
    at org.junit.platform.engine.support.hierarchical.NodeTestTask.lambda$executeRecursively$7(NodeTestTask.java:125)
    at org.junit.platform.engine.support.hierarchical.Node.around(Node.java:135)
    at org.junit.platform.engine.support.hierarchical.NodeTestTask.lambda$executeRecursively$8(NodeTestTask.java:123)
    at org.junit.platform.engine.support.hierarchical.ThrowableCollector.execute(ThrowableCollector.java:73)
    at org.junit.platform.engine.support.hierarchical.NodeTestTask.executeRecursively(NodeTestTask.java:122)
    at org.junit.platform.engine.support.hierarchical.NodeTestTask.execute(NodeTestTask.java:80)
    at org.junit.platform.engine.support.hierarchical.SameThreadHierarchicalTestExecutorService.submit(SameThreadHierarchicalTestExecutorService.java:32)
    at org.junit.platform.engine.support.hierarchical.HierarchicalTestExecutor.execute(HierarchicalTestExecutor.java:57)
    at org.junit.platform.engine.support.hierarchical.HierarchicalTestEngine.execute(HierarchicalTestEngine.java:51)
    at org.junit.platform.launcher.core.DefaultLauncher.execute(DefaultLauncher.java:229)
    at org.junit.platform.launcher.core.DefaultLauncher.lambda$execute$6(DefaultLauncher.java:197)
    at org.junit.platform.launcher.core.DefaultLauncher.withInterceptedStreams(DefaultLauncher.java:211)
    at org.junit.platform.launcher.core.DefaultLauncher.execute(DefaultLauncher.java:191)
    at org.junit.platform.launcher.core.DefaultLauncher.execute(DefaultLauncher.java:128)
    at com.intellij.junit5.JUnit5IdeaTestRunner.startRunnerWithArgs(JUnit5IdeaTestRunner.java:69)
    at com.intellij.rt.execution.junit.IdeaTestRunner$Repeater.startRunnerWithArgs(IdeaTestRunner.java:47)
    at com.intellij.rt.execution.junit.JUnitStarter.prepareStreamsAndStart(JUnitStarter.java:242)
    at com.intellij.rt.execution.junit.JUnitStarter.main(JUnitStarter.java:70)
Caused by: org.sqlite.SQLiteException: [SQLITE_ERROR] SQL error or missing database (no such table: PUBLIC.TROOP)
    at org.sqlite.core.DB.newSQLException(DB.java:941)
    at org.sqlite.core.DB.newSQLException(DB.java:953)
    at org.sqlite.core.DB.throwex(DB.java:918)
    at org.sqlite.core.NativeDB.prepare_utf8(Native Method)
    at org.sqlite.core.NativeDB.prepare(NativeDB.java:134)
    at org.sqlite.core.DB.prepare(DB.java:257)
    at org.sqlite.core.CorePreparedStatement.<init>(CorePreparedStatement.java:47)
    at org.sqlite.jdbc3.JDBC3PreparedStatement.<init>(JDBC3PreparedStatement.java:30)
    at org.sqlite.jdbc4.JDBC4PreparedStatement.<init>(JDBC4PreparedStatement.java:19)
    at org.sqlite.jdbc4.JDBC4Connection.prepareStatement(JDBC4Connection.java:35)
    at org.sqlite.jdbc3.JDBC3Connection.prepareStatement(JDBC3Connection.java:241)
    at org.sqlite.jdbc3.JDBC3Connection.prepareStatement(JDBC3Connection.java:205)
    at org.jooq.impl.ProviderEnabledConnection.prepareStatement(ProviderEnabledConnection.java:109)
    at org.jooq.impl.SettingsEnabledConnection.prepareStatement(SettingsEnabledConnection.java:73)
    at org.jooq.impl.AbstractResultQuery.prepare(AbstractResultQuery.java:239)
    at org.jooq.impl.AbstractQuery.execute(AbstractQuery.java:322)
    ... 77 common frames omitted

1 Ответ

1 голос
/ 25 октября 2019

В соответствии с jOOQ 3.12, DDLDatabase анализирует ваши SQL-скрипты, переводит их в H2 и запускает их в базе данных H2 в памяти, которая использует PUBLIC в качестве схемы по умолчанию, где все ваши таблицы теперь расположены източка зрения генератора кода.

Такая схема не существует в SQLite, поэтому вы получаете ошибки, которые вы видели. В jOOQ 3.12 это исправлено путем поддержки нового свойства unqualifiedSchema, которое позволяет указывать подразумеваемую схему всех неквалифицированных таблиц в сценариях DDL. По умолчанию, учитывая, что это соответствует PUBLIC в H2, PUBLIC принимается как «схема по умолчанию». Итак, чтобы это исправить, просто обновитесь до jOOQ 3.12. Подробнее см. Здесь: https://www.jooq.org/doc/latest/manual/code-generation/codegen-ddl

Примечание. Этот флаг уже используется, но вы не используете jOOQ 3.12. В 3.11.11 он еще не был доступен.

...