Exception in JPA Persistance - java

I have question...I Have two JAR file, which have similar code, and one is in English and second for Deutch...I have two DB (for EN a DE), but I want to have same table names. If I start this, I have two definitions for same table...I want to keep the table same for the JAR, which will change. But it's enough for me to load one of this two. How can I do it? My app is bigger...
I don't want the modification of one table definition to be written to both tables.
Some advice? In persistance you can see some solve? Thanks
<jar-file>FA_DE-MLA-1.0.jar</jar-file>
<jar-file>FA_EN-MLA-1.0.jar</jar-file>
<exclude-unlisted-classes>false</exclude-unlisted-classes>
<properties>
<property name="hibernate.enable_lazy_load_no_trans" value="true"/>
<property name="javax.persistence.validation.mode" value="none" />
<property name="hibernate.hbm2ddl.auto" value="update"/>
<property name="hibernate.dialect" value="org.hibernate.dialect.MySQL5Dialect"/>
<property name="hibernate.show_sql" value="false"/>
<property name="hibernate.format_sql" value="false"/>
<property name="hibernate.create_empty_composites.enabled" value="true"/>
</properties>

Related

JPA / Hibernate : schema generation with multiple persistence units

I have an application that uses a set of JPA entities that are located in 2 different databases. I configured it with multiple persistence units.
The problem is that I want to auto-generate the schema using schema-generation, and all the entities are created in both databases.
I have in both PUs:
<property name="javax.persistence.schema-generation.database.action" value="drop-and-create"/>
<property name="javax.persistence.schema-generation.create-source" value="metadata"/>
<property name="javax.persistence.schema-generation.drop-source" value="metadata"/>
And, yes, I want to use the metadata to get the entities automatically. I do not want to provide a manual script, because I would need to keep it up to date with the entities.
Is there a way to mark which entity to be generated by which PU?
-edit: please be aware that adding "schema" property on #Table does not resolve the problem, because each PU will try to create the same entity in the right schema, and there will be errors because the tables will already exist.
Yes, you can do that. You need to list the entities under each persistant unit, and also DISABLE the auto discovery of the unlisted entities explicitly with <exclude-unlisted-classes>true</exclude-unlisted-classes>.
<!-- Unit 1 -->
<persistence-unit name="Unit1" transaction-type="RESOURCE_LOCAL">
<provider>org.hibernate.ejb.HibernatePersistence</provider>
<class>com.your.class.A</class>
<exclude-unlisted-classes>true</exclude-unlisted-classes>
<properties>
<property name="javax.persistence.jdbc.username" value=""/>
<property name="javax.persistence.jdbc.password" value=""/>
<property name="hibernate.hbm2ddl.auto" value="update"/>
<property name="javax.persistence.schema-generation.database.action" value="drop-and-create"/>
<property name="javax.persistence.schema-generation.create-source" value="metadata"/>
<property name="javax.persistence.schema-generation.drop-source" value="metadata"/>
</properties>
</persistence-unit>
<!-- Unit 2 -->
<persistence-unit name="Unit2" transaction-type="RESOURCE_LOCAL">
<provider>org.hibernate.ejb.HibernatePersistence</provider>
<class>com.your.class.B</class>
<exclude-unlisted-classes>true</exclude-unlisted-classes>
<properties>
<property name="javax.persistence.jdbc.username" value=""/>
<property name="javax.persistence.jdbc.password" value=""/>
<property name="hibernate.hbm2ddl.auto" value="update"/>
<property name="javax.persistence.schema-generation.database.action" value="drop-and-create"/>
<property name="javax.persistence.schema-generation.create-source" value="metadata"/>
<property name="javax.persistence.schema-generation.drop-source" value="metadata"/>
</properties>
</persistence-unit>
Edit
If you are using annotations configuration, then
LocalContainerEntityManagerFactoryBean lef = new LocalContainerEntityManagerFactoryBean();
lef.setPackagesToScan("com.A");
And another factory for another entity manager with a different package name.
I found a way: I will use "schema" property in #Table annotation for each entity and then I would enable only one PU to auto generate the tables.

How to qualify sequence names in Hibernate?

I'm having troubles when generating sequences for an oracle databese running under the same instance than other one, with the same data structure. Here is a fragment of my persistence.xml where I define different schemas according to the persistence unit:
<persistence-unit name="oracle_development" transaction-type="RESOURCE_LOCAL">
<provider>org.hibernate.ejb.HibernatePersistence</provider>
<properties>
<property name="hibernate.archive.autodetection" value="class" />
<property name="hibernate.dialect" value="org.hibernate.dialect.Oracle10gDialect" />
<property name="hibernate.hbm2ddl.auto" value="update" />
<property name="hibernate.ejb.naming_strategy" value="org.hibernate.cfg.ImprovedNamingStrategy" />
<property name="hibernate.connection.charSet" value="UTF-8" />
<property name="hibernate.show_sql" value="false" />
<property name="hibernate.format_sql" value="false" />
<property name="hibernate.connection.autocommit" value="false" />
<property name="hibernate.ejb.entitymanager_factory_name"
value="o11g" />
<property name="hibernate.default_schema" value="devdatabase"/>
</properties>
</persistence-unit>
<persistence-unit name="oracle_production" transaction-type="RESOURCE_LOCAL">
<provider>org.hibernate.ejb.HibernatePersistence</provider>
<properties>
<property name="hibernate.archive.autodetection" value="class" />
<property name="hibernate.dialect" value="org.hibernate.dialect.Oracle10gDialect" />
<property name="hibernate.hbm2ddl.auto" value="update" />
<property name="hibernate.ejb.naming_strategy" value="org.hibernate.cfg.ImprovedNamingStrategy" />
<property name="hibernate.connection.charSet" value="UTF-8" />
<property name="hibernate.show_sql" value="false" />
<property name="hibernate.format_sql" value="false" />
<property name="hibernate.connection.autocommit" value="false" />
<property name="hibernate.ejb.entitymanager_factory_name"
value="o11g" />
<property name="hibernate.default_schema" value="proddatabase"/>
</properties>
</persistence-unit>
Well, the tables are generated perfectly, once the table names in creating commands include the default schema as qualifier. But sequences are not generated in the 'proddatabase' if they're already created on 'devdatabase', in example... Any help?
The hibernate.hbm2ddl.auto=”update” is convenient but less flexible if you plan on adding functions or executing some custom scripts.
So, the most flexible approach is to generate the DDL scripts with "org.hibernate.tool.ant.HibernateToolTask" and then use a component to execute the scripts on context startup. The destroy scripts are called when the Spring context is closed.
The second approach is much more flexible, especially if you want to mix JPA Entity Model with jOOQ Table Model.
Needless to say that this is only an Integration testing concern since for the production environment we use Flyway. So, you shouldn't rely on Hibernate for managing your database schema, because it's riskier, less flexible and it doesn't play well with CI and CD.

Best way to create schema in embedded HSQL database

I'm currently using the following setup to create a schema in an embedded database before running my tests against it
In my application context
<jdbc:embedded-database id="dataSource" type="HSQL">
<jdbc:script location="classpath:createSchema.sql" />
</jdbc:embedded-database>
createSchema.sql
create schema ST_TEST AUTHORIZATION DBA;
hibernate properties
<properties>
<property name="hibernate.dialect" value="org.hibernate.dialect.HSQLDialect" />
<property name="hibernate.default_schema" value="ST_TEST"/>
<property name="hibernate.hbm2ddl.auto" value="create-drop" />
<property name="hibernate.show_sql" value="true" />
<property name="hibernate.use_sql_comments" value="true" />
<property name="hibernate.cache.use_second_level_cache" value="false" />
</properties>
My question is is this the best way to do this. Or can i use a different schema name in my properties? or set the schema name in the jdbc:embedded-database element
By default HSQL creates a schema called PUBLIC. source: HSQL documentation
Seeing as the schema name is never seen in the tests (named queries/entity manager to do the interactions) you can change the hibernate properties to use this PUBLIC schema
<properties>
<property name="hibernate.dialect" value="org.hibernate.dialect.HSQLDialect" />
<property name="hibernate.default_schema" value="PUBLIC"/>
<property name="hibernate.hbm2ddl.auto" value="create-drop" />
</properties>
OR
just leave out the default_schema from the properties list and it uses PUBLIC anyway
<properties>
<property name="hibernate.dialect" value="org.hibernate.dialect.HSQLDialect" />
<property name="hibernate.hbm2ddl.auto" value="create-drop" />
</properties>
You can use this code in your Base Testing class, and call it using #BeforeClass annotation (for Junit). I do it like this.
EmbeddedDatabaseBuilder builder = new EmbeddedDatabaseBuilder();
builder = builder.setType(EmbeddedDatabaseType.HSQL).addScript(
"createSchema.sql");
builder.setName("MyDatabase");
EmbeddedDatabase db = builder.build();

C3P0 Configurations! Where and How?

We are implementing a Web App using JPA2.0 and Hibernate3.0. Connection pool configurations are set in persistence.xml located in META-INF folder.
persistence.xml:
<persistence xmlns="http://java.sun.com/xml/ns/persistence" version="2.0">
<persistence-unit name="MyPU" transaction-type="RESOURCE_LOCAL">
<!-- Entity Classes-->
<properties>
<property name="hibernate.connection.driver_class" value="com.mysql.jdbc.Driver"/>
<property name="hibernate.dialect" value="org.hibernate.dialect.MySQL5InnoDBDialect"/>
<property name="hibernate.show_sql" value="true"/>
<property name="bytecode.provider" value="org.hibernate.bytecode.javassist.BytecodeProviderImpl"/>
<property name="hibernate.connection.username" value="{username}"/>
<property name="hibernate.connection.password" value="{password}"/>
<property name="hibernate.hbm2ddl.auto" value="update"/>
<property name="hibernate.format_sql" value="true"/>
<property name="hibernate.connection.url" value="{jdbc url}"/>
<property name="hibernate.c3p0.min_size" value="1"/>
<property name="hibernate.c3p0.timeout" value="1000"/>
<property name="hibernate.c3p0.acquire_increment" value="1"/>
<property name="hibernate.c3p0.idle_test_periods" value="600"/>
<property name="hibernate.c3p0.testConnectionOnCheckin" value="true"/>
<property name="hibernate.c3p0.preferredTestQuery" value="SELECT 1;"/>
</properties>
</persistence-unit>
</persistence>
We have a problem with connection pool configurations. It seems the configurations have no effect and the connection will be broken after 8 hours.
Do we need another configuration file like hibernate.cfg.xml or hibernate.properties?
I had this same problem with the proprieties that I put in persistence.xml didn't affect c3p0.
Looking into http://www.mchange.com/projects/c3p0/index.html#configuration_files I tried to put an xml file named c3p0-config.xml and put it in WEB-INF/classes and it work perfectly.
Here is an example of a c3p0-config.xml file:
<c3p0-config>
<default-config>
<property name="automaticTestTable">con_test</property>
<property name="checkoutTimeout">30000</property>
<property name="idleConnectionTestPeriod">30</property>
<property name="initialPoolSize">10</property>
<property name="maxIdleTime">30</property>
<property name="maxPoolSize">100</property>
<property name="minPoolSize">10</property>
<property name="maxStatements">200</property>
<user-overrides user="test-user">
<property name="maxPoolSize">10</property>
<property name="minPoolSize">1</property>
<property name="maxStatements">0</property>
</user-overrides>
</default-config>
</c3p0-config>
Good question, bad title. :) I think I answered this question on your re-post: Best configuration of c3p0
I had the same exact issue, my problem was that my web application container (Tomcat) was managing my database connections. I had to move the c3p0 configuration from my persistence.xml file to Tomcat's context.xml. The link Domenic D provided is a great place to start if that's your problem.
There is a typo in your settings, it should be idle_test_period not idle_test_periods.
See this post for information about the setting: The use of c3p0.idle_test_period.

Persistence unit is not persistent

I need persistence unit that creates embedded database which stays persistent after closing EntityManager.
This is my PU:
<persistence-unit name="hello-jpa" transaction-type="RESOURCE_LOCAL">
<class>hello.jpa.User</class>
<properties>
<property name="hibernate.show_sql" value="true"/>
<property name="hibernate.format_sql" value="true"/>
<property name="hibernate.dialect" value="org.hibernate.dialect.HSQLDialect"/>
<property name="hibernate.connection.driver_class" value="org.hsqldb.jdbcDriver"/>
<property name="hibernate.connection.username" value="sa"/>
<property name="hibernate.connection.password" value=""/>
<property name="hibernate.connection.url" value="jdbc:hsqldb:target/hsql.db"/>
<property name="hibernate.hbm2ddl.auto" value="update"/>
</properties>
</persistence-unit>
And it deletes data after closing application.
My understanding of the documentation is that the "old" URL jdbc:hsqldb:. creates or connects to the same database as the new form for the URL jdbc:hsqldb:mem:. (i.e. in memory).
So try with the following URL instead: jdbc:hsqldb:file:target/hsql.db.

Categories