{"record":{"id":"cfc6fcb8e0528155","repo":"flowable/flowable-engine","slug":"couldn-t-operation-db-schema-exceptionsqlsta","errorCode":null,"errorMessage":"couldn't ${operation} db schema: ${exceptionSqlStatement}","messagePattern":"couldn't (.+?) db schema: (.+?)","errorType":"exception","errorClass":"FlowableException","httpStatus":null,"severity":"critical","filePath":"modules/flowable-engine-common/src/main/java/org/flowable/common/engine/impl/db/AbstractSqlScriptBasedDbSchemaManager.java","lineNumber":348,"sourceCode":"                            sqlStatement = null;\n                        }\n                        \n                    } else {\n                        sqlStatement = addSqlStatementPiece(sqlStatement, line);\n                    }\n                }\n\n                line = readNextTrimmedLine(reader);\n            }\n\n            if (exception != null) {\n                throw exception;\n            }\n\n            logger.debug(\"flowable db schema {} for component {} successful\", operation, component);\n\n        } catch (Exception e) {\n            throw new FlowableException(\"couldn't \" + operation + \" db schema: \" + exceptionSqlStatement, e);\n        }\n    }\n\n    /**\n     * MySQL is funny when it comes to timestamps and dates.\n     * \n     * More specifically, for a DDL statement like 'MYCOLUMN timestamp(3)': - MySQL 5.6.4+ has support for timestamps/dates with millisecond (or smaller) precision. The DDL above works and the data in\n     * the table will have millisecond precision - MySQL before 5.5.3 allows the DDL statement, but ignores it. The DDL above works but the data won't have millisecond precision - \n     * MySQL 5.5.3 before [version] after 5.6.4 gives and exception when using the DDL above.\n     * \n     * Also, the 5.5 and 5.6 branches of MySQL are both actively developed and patched.\n     * \n     * Hence, when doing auto-upgrade/creation of the Flowable tables, the default MySQL DDL file is used and all timestamps/datetimes are converted to not use the millisecond precision by string\n     * replacement done in the method below.\n     * \n     * If using the DDL files directly (which is a sane choice in production env.), there is a distinction between MySQL version before 5.6.\n     */\n    protected String updateDdlForMySqlVersionLowerThan56(String ddlStatements) {","sourceCodeStart":330,"sourceCodeEnd":366,"githubUrl":"https://github.com/flowable/flowable-engine/blob/d6d39ce1c69ff244f2d9dc6af756a9b95e865586/modules/flowable-engine-common/src/main/java/org/flowable/common/engine/impl/db/AbstractSqlScriptBasedDbSchemaManager.java#L330-L366","documentation":"executeSchemaResource's outer catch wraps any exception raised while executing a schema SQL statement into FlowableException('couldn't <operation> db schema: <failing statement>'). The message includes the exact SQL statement that failed, so the error names both the operation (create/upgrade/drop) and the offending DDL/DML.","triggerScenarios":"Any SQL statement in a schema create/upgrade/drop script failing — object already exists, insufficient privileges, syntax unsupported by the database, table in use — during dbSchemaCreate, dbSchemaUpgrade, or dbSchemaDrop.","commonSituations":"Re-running schema creation on a partially populated database; DB user lacking CREATE/ALTER privileges; database type auto-detection mismatching the actual DB (Oracle script run on PostgreSQL); rerunning an interrupted upgrade that already applied some statements.","solutions":["Read the failing SQL statement in the message and the chained SQLException to identify the concrete database error.","Restore from a backup (or drop/recreate the schema) and run the schema operation once against a clean state.","Grant the DB user the required DDL privileges (CREATE TABLE, ALTER, DROP, INDEX).","Verify databaseType detection matches the actual database so the correct vendor scripts are used."],"exampleFix":"// before: rerunning create on a half-created schema\nengineConfig.setDatabaseSchemaUpdate(\"create\");\n// after\nengineConfig.setDatabaseSchemaUpdate(\"true\"); // checks what exists and upgrades/creates only what is missing","handlingStrategy":"try-catch","validationCode":"// preflight: run schema scripts on a scratch database copy to catch failing DDL early\nboolean ok = scratchDb.apply(flowableSchemaScripts);","typeGuard":null,"tryCatchPattern":"try { engineCfg.buildProcessEngine(); } catch (FlowableException e) { if (e.getMessage().startsWith(\"couldn't \")) { log.error(\"Failed schema op, failing statement: {} cause: {}\", e.getMessage(), e.getCause(), e.getCause()); } throw e; }","preventionTips":["Read the failing SQL statement embedded in the message to identify the exact problem","Use databaseSchemaUpdate=true (idempotent) instead of re-running 'create'","Grant the DB user sufficient DDL privileges","Verify databaseType/databaseVendor detection matches the actual database","Back up before upgrades; restore to clean state after failed partial schema runs"],"tags":["database","sql","schema","ddl"],"backgroundTag":"sql-query-failed","analyzedSha":"d6d39ce1c69ff244f2d9dc6af756a9b95e865586","analyzedAt":"2026-09-11T06:41:19.413Z","contentChangedAt":"2026-09-11T06:41:19.413Z","schemaVersion":2},"datasetVersion":"2026-09-14T05:17:10.506Z"}