java - Migrating to Hibernate 5 -
i migrating application hibernate 4.3 hibernate 5.0.1-final use implicitnamingstrategycomponentpathimpl
hibernate.implicit_naming_strategy
postgres 9.4.4 , company uses hibernate.hbm2ddl.auto = update
deployment ( know bad practice cant it)
while session factory initializes, throws below error. apparently generated alias long postgres. how go situation? have tried assigning @table(name=..)
annotation work around getting worse every relationship point gets screwd.
caused by: org.hibernate.tool.schema.spi.schemamanagementexception: unable execute schema management jdbc target [create table public.referencedocumentversion_referencedocumentsourcefilesstoredescriptor (referencedocumentversion_unid uuid not null, sourcefilesstore_filesdescriptormap_unid uuid not null, filesdescriptormap_key text not null, primary key (referencedocumentversion_unid, filesdescriptormap_key))] @ org.hibernate.tool.schema.internal.targetdatabaseimpl.accept(targetdatabaseimpl.java:59) @ org.hibernate.tool.schema.internal.schemamigratorimpl.applysqlstring(schemamigratorimpl.java:371) @ org.hibernate.tool.schema.internal.schemamigratorimpl.applysqlstrings(schemamigratorimpl.java:360) @ org.hibernate.tool.schema.internal.schemamigratorimpl.createtable(schemamigratorimpl.java:181) @ org.hibernate.tool.schema.internal.schemamigratorimpl.domigrationtotargets(schemamigratorimpl.java:134) @ org.hibernate.tool.schema.internal.schemamigratorimpl.domigration(schemamigratorimpl.java:59) @ org.hibernate.tool.hbm2ddl.schemaupdate.execute(schemaupdate.java:129) @ org.hibernate.tool.hbm2ddl.schemaupdate.execute(schemaupdate.java:97) @ org.hibernate.internal.sessionfactoryimpl.<init>(sessionfactoryimpl.java:481) @ org.hibernate.boot.internal.sessionfactorybuilderimpl.build(sessionfactorybuilderimpl.java:444) @ org.hibernate.jpa.boot.internal.entitymanagerfactorybuilderimpl.build(entitymanagerfactorybuilderimpl.java:802) ... 29 more caused by: org.postgresql.util.psqlexception: error: relation "referencedocumentversion_referencedocumentsourcefilesstoredescr" exists @ org.postgresql.core.v3.queryexecutorimpl.receiveerrorresponse(queryexecutorimpl.java:2182) @ org.postgresql.core.v3.queryexecutorimpl.processresults(queryexecutorimpl.java:1911) @ org.postgresql.core.v3.queryexecutorimpl.execute(queryexecutorimpl.java:173) @ org.postgresql.jdbc2.abstractjdbc2statement.execute(abstractjdbc2statement.java:618) @ org.postgresql.jdbc2.abstractjdbc2statement.executewithflags(abstractjdbc2statement.java:454) @ org.postgresql.jdbc2.abstractjdbc2statement.executeupdate(abstractjdbc2statement.java:382) @ org.apache.tomcat.dbcp.dbcp.delegatingstatement.executeupdate(delegatingstatement.java:228) @ org.apache.tomcat.dbcp.dbcp.delegatingstatement.executeupdate(delegatingstatement.java:228) @ sun.reflect.nativemethodaccessorimpl.invoke0(native method) @ sun.reflect.nativemethodaccessorimpl.invoke(nativemethodaccessorimpl.java:62) @ sun.reflect.delegatingmethodaccessorimpl.invoke(delegatingmethodaccessorimpl.java:43) @ java.lang.reflect.method.invoke(method.java:497) @ net.bull.javamelody.jdbcwrapper.doexecute(jdbcwrapper.java:404) @ net.bull.javamelody.jdbcwrapper$statementinvocationhandler.invoke(jdbcwrapper.java:129) @ net.bull.javamelody.jdbcwrapper$delegatinginvocationhandler.invoke(jdbcwrapper.java:286) @ com.sun.proxy.$proxy93.executeupdate(unknown source) @ org.hibernate.tool.schema.internal.targetdatabaseimpl.accept(targetdatabaseimpl.java:56) ... 39 more
i have addressed situation custom implicitnamingstrategy
truncates hibernate generated identifiers 64 chars (max length postgres).
previous versions of hibernate(4.x) have encountered same error ignores , proceeds initializing sessionfactory. however, hibernate 5.x has new boot strap api throws schemamanagementexception in such cases , aborts. hibernate logs test scenarios pasted below reference.
hibernate 4.x
info: hhh000396: updating schema oct 04, 2015 1:38:00 pm org.hibernate.tool.hbm2ddl.databasemetadata gettablemetadata info: hhh000262: table not found: referencedocumentversionentitywithareallyreallyreallylongnamebeyondpostgres oct 04, 2015 1:38:00 pm org.hibernate.tool.hbm2ddl.databasemetadata gettablemetadata info: hhh000262: table not found: referencedocumentversionentitywithareallyreallyreallylongnamebeyondpostgres oct 04, 2015 1:38:00 pm org.hibernate.tool.hbm2ddl.databasemetadata gettablemetadata info: hhh000262: table not found: referencedocumentversionentitywithareallyreallyreallylongnamebeyondpostgres oct 04, 2015 1:38:00 pm org.hibernate.tool.hbm2ddl.schemaupdate execute error: hhh000388: unsuccessful: create table referencedocumentversionentitywithareallyreallyreallylongnamebeyondpostgres (unid uuid not null, path text, primary key (unid)) oct 04, 2015 1:38:00 pm org.hibernate.tool.hbm2ddl.schemaupdate execute error: error: relation "referencedocumentversionentitywithareallyreallyreallylongnamebe" exists oct 04, 2015 1:38:00 pm org.hibernate.tool.hbm2ddl.schemaupdate execute info: hhh000232: schema update complete
hibernate 5.0.2.final
oct 04, 2015 1:39:16 pm org.hibernate.tool.hbm2ddl.schemaupdate execute info: hhh000228: running hbm2ddl schema update oct 04, 2015 1:39:16 pm org.hibernate.tool.schema.extract.internal.informationextractorjdbcdatabasemetadataimpl processgettableresults info: hhh000262: table not found: referencedocumentversionentitywithareallyreallyreallylongnamebeyondpostgres oct 04, 2015 1:39:16 pm org.hibernate.tool.schema.extract.internal.informationextractorjdbcdatabasemetadataimpl processgettableresults info: hhh000262: table not found: referencedocumentversionentitywithareallyreallyreallylongnamebeyondpostgres tests run: 1, failures: 0, errors: 1, skipped: 0, time elapsed: 0.813 sec <<< failure! testapp(org.foobar.apptest) time elapsed: 0.788 sec <<< error! javax.persistence.persistenceexception: [persistenceunit: org.foobar.persistence.default] unable build hibernate sessionfactory @ org.hibernate.jpa.boot.internal.entitymanagerfactorybuilderimpl.persistenceexception(entitymanagerfactorybuilderimpl.java:877) @ org.hibernate.jpa.boot.internal.entitymanagerfactorybuilderimpl.build(entitymanagerfactorybuilderimpl.java:805) @ org.hibernate.jpa.hibernatepersistenceprovider.createentitymanagerfactory(hibernatepersistenceprovider.java:58) @ javax.persistence.persistence.createentitymanagerfactory(persistence.java:55) @ javax.persistence.persistence.createentitymanagerfactory(persistence.java:39) @ org.foobar.apptest.testapp(apptest.java:18)
solution
custom implicitnamingstrategy
package org.foobar.persistence; import org.hibernate.boot.model.naming.identifier; import org.hibernate.boot.model.naming.implicitnamingstrategycomponentpathimpl; import org.hibernate.boot.spi.metadatabuildingcontext; public class pgconstrainedimplicitnamingstrategy extends implicitnamingstrategycomponentpathimpl { private static final int postgres_identifier_maxlength = 63; public static final pgconstrainedimplicitnamingstrategy instance = new pgconstrainedimplicitnamingstrategy(); public pgconstrainedimplicitnamingstrategy() { } @override protected identifier toidentifier(string stringform, metadatabuildingcontext buildingcontext) { return buildingcontext.getmetadatacollector() .getdatabase() .getjdbcenvironment() .getidentifierhelper() .toidentifier( stringform.substring( 0, math.min( postgres_identifier_maxlength, stringform.length() ) ) ); }}
persistence.xml
<properties> <property name="hibernate.implicit_naming_strategy" value="org.foobar.persistence.pgconstrainedimplicitnamingstrategy"/> </properties>
this not scalable solution @ helps keep show running. permanent solution explicitly supply identifiers hibernate not generate long identifiers.
Comments
Post a Comment