I'm developing an application using Hibernate 5.2.1.Final with SQLite (driver: Xerial 3.11.8.2) and Maven. The problem is, that Hibernate can't find my named queries (which are located in an entity provided with #Entity (javax.persistence.Entity) annotation. I've searched everywhere for a solution so far, but I couldn't make it work.
I've recently switched to Hibernate API instead of using a JPA one - I had no issues before and I haven't made any modifications to this named query. As far as I'm concerned, I can still use javax.persistence annotations.
Exception I'm getting:
Caused by: java.lang.IllegalArgumentException: No query defined for that name [SugerowanaPozycja.getByCategory]
at org.hibernate.internal.AbstractSharedSessionContract.getNamedQuery(AbstractSharedSessionContract.java:546)
at org.hibernate.internal.AbstractSharedSessionContract.getNamedQuery(AbstractSharedSessionContract.java:101)
at pl.nombritech.Menual.dao.SugerowanaPozycjaDAO.getByKategoria(SugerowanaPozycjaDAO.java:90)
at pl.nombritech.Menual.view.GlowneOknoController.uzupelnijSugerowanePozycje(GlowneOknoController.java:227)
at pl.nombritech.Menual.view.GlowneOknoController.initialize(GlowneOknoController.java:210)
... 22 more
Annotations in my entity class:
import javax.persistence.Entity;
import javax.persistence.NamedQueries;
import javax.persistence.NamedQuery;
#Entity
#NamedQueries({
#NamedQuery(name = "SugerowanaPozycja.getByCategory",
query = "SELECT e FROM SugerowanaPozycja e WHERE e.kategoria = :kategoria")
})
And it is where the exception happens:
public static ObservableList<SugerowanaPozycja> getByKategoria(String kategoria)
{
Session session = Main.SESSION_FACTORY.openSession();
Transaction transaction = session.beginTransaction();
Query<SugerowanaPozycja> query = session.getNamedQuery("SugerowanaPozycja.getByCategory"); // exception here
query.setParameter("kategoria", kategoria);
ObservableList<SugerowanaPozycja> list = FXCollections.observableArrayList(query.getResultList());
transaction.commit();
session.close();
return list;
}
My hibernate.cfg.xml:
<?xml version="1.0" encoding="utf-8"?>
<!DOCTYPE hibernate-configuration PUBLIC
"-//Hibernate/Hibernate Configuration DTD 3.0//EN"
"http://www.hibernate.org/dtd/hibernate-configuration-3.0.dtd">
<hibernate-configuration>
<session-factory>
<property name="hibernate.connection.driver_class">org.sqlite.JDBC</property>
<property name="hibernate.connection.url">jdbc:sqlite:menual_data/bazadb.db</property>
<property name="hibernate.connection.username"></property>
<property name="hibernate.connection.password"></property>
<property name="hibernate.dialect">pl.nombritech.Menual.util.SQLiteDialect</property>
<property name="show_sql">true</property>
<property name="format_sql">true</property>
<property name="hbm2ddl.auto">create</property>
<property name="hibernate.c3p0.min_size">1</property>
<property name="hibernate.c3p0.max_size">1</property>
</session-factory>
</hibernate-configuration>
And finally how I initialize Hibernate:
public static SessionFactory SESSION_FACTORY;
Configuration configuration = new Configuration().configure(Main.class.getResource("/hibernate.cfg.xml"));
StandardServiceRegistryBuilder serviceRegistryBuilder = new StandardServiceRegistryBuilder();
serviceRegistryBuilder.applySettings(configuration.getProperties());
ServiceRegistry serviceRegistry = serviceRegistryBuilder.build();
SESSION_FACTORY = configuration.buildSessionFactory(serviceRegistry);
I would be very grateful for any hints in this matter. I know there was a lot of such threads here, but it didn't help in my case.
The mapping of the class inside which your query resides should be present into the hibernate.cfg.xml. In this case since it it not present that's why you are getting this exception.
In order to resolve this issue, place the following tag inside hibernate.cfg.xml:
<mapping class="your.package.ClassName"/>
and re-run your program.
Related
I am new to Hibernate and I am learning myself. I've got a problem when I am executing a program. I have tried a lot to solve the error but got no luck. Here is my main and configuration file and hbm files.
package com.HibernateLearn;
import org.hibernate.Session;
import org.hibernate.SessionFactory;
import org.hibernate.Transaction;
import org.hibernate.cfg.Configuration;
public class Client {
public static void main(String[] args) {
// creating configuration object
Configuration cfg = new Configuration();
cfg.configure("hibernate.cfg.xml");// populates the data of the
// configuration file
// creating seession factory object
SessionFactory factory = cfg.buildSessionFactory();
// creating session object
Session session = factory.openSession();
// creating transaction object
Transaction t = session.beginTransaction();
Employee e1 = new Employee();
e1.setId(103);
e1.setF_name("Ahammed");
e1.setL_name("Naseer");
//e1.getId();
//e1.getF_name();
e1.getL_name();
session.persist(e1);// persisting the object
t.commit();// transaction is committed
session.close();
System.out.println("successfully saved");
}
}
my hibernate.cfg.xml
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE hibernate-configuration PUBLIC "-//Hibernate/Hibernate
Configuration DTD 3.0//EN" "http://hibernate.sourceforge.net/hibernate-
configuration-3.0.dtd">
<hibernate-configuration>
<session-factory>
<property name="show_sql">true</property>
<!-- <property name="hbm2ddl.auto">create-update</property> -->
<!--Below are other values for hbm2ddl.auto validate: validate the schema,
makes no changes to the database. update: update the schema. create: creates
the schema, destroying previous data. create-drop: drop the schema at the
end of the session. -->
<!--property name="hibernate.cache.use_query_cache">true</property -->
<property name="hibernate.dialect">org.hibernate.dialect.MySQLDialect</property>
<property name="hibernate.connection.driver_class">com.mysql.jdbc.Driver</property>
<property name="hibernate.connection.url">jdbc:mysql://localhost:3306/joctopusdb</property>
<property name="hibernate.connection.username">root</property>
<property name="hibernate.connection.password">abc123</property>
<mapping resource="hibernate.hbm.xml"/>
</session-factory>
</hibernate-configuration>
my hibernate.hbm.xml file
<?xml version='1.0' encoding='UTF-8'?>
<!DOCTYPE hibernate-mapping PUBLIC
"-//Hibernate/Hibernate Mapping DTD 3.0//EN"
"http://hibernate.sourceforge.net/hibernate-mapping-3.0.dtd">
<hibernate-mapping>
<class name="com.HibernateLearn.Employee" table="emp_table">
<id name="Id">
<generator class="increment"></generator>
</id>
<property name="F_name"></property>
<property name="L_name"></property>
</class>
</hibernate-mapping>
Error I am getting
Exception in thread "main" org.hibernate.PersistentObjectException: detached entity passed to persist: com.HibernateLearn.Employee
You do e1.setId(103); while the unique ids for new entities are generated for you:
<id name="Id">
<generator class="increment"></generator>
</id>
Hibernate is expecting your Employee instance is already in the database because it has its id set. In other words, Hibernate is expecting it is updating an existing instance that is attached to the session. Hence the detached error message.
So to fix this you should not set the id for new entities yourself.
I am new bee to Hibernate and trying out things.
One thing that seems to amuse all is how to connect to different databases?
I have two questions here:
If in the same web app I need to connect to MySQL and Oracle, how do I do it?
I am using MySQL and have two databases test1 and test2, how to connect and retrieve data?
I have read in a blog that we can create different configuration files and do it.
I tried it but was not sucessful.
Here's what I tried:
SessionFactory sf = (SessionFactory) new Configuration().configure(path);
Where path is the path of the config file.
Is this the right way?
Using annotation mappings as an example:
Configuration cfg1 = new AnnotationConfiguration();
cfg1.configure("/hibernate-oracle.cfg.xml");
cfg1.addAnnotatedClass(SomeClass.class); // mapped classes
cfg1.addAnnotatedClass(SomeOtherClass.class);
SessionFactory sf1 = cfg1.buildSessionFactory();
Configuration cfg2 = new AnnotationConfiguration();
cfg2.configure("/hibernate-mysql.cfg.xml");
cfg2.addAnnotatedClass(SomeClass.class); // could be the same or different than above
cfg2.addAnnotatedClass(SomeOtherClass.class);
SessionFactory sf2 = cfg2.buildSessionFactory();
Then use sf1 and sf2 to get the sessions for each database. For mapping files, you just use cfg.addClass instead of addAnnotatedClass. Put the cfg.xml files in the root package in this case. Those will have the Oracle or MySQL dialect and connection information.
It cannot be done using one hibernate configuration file. You need to have two configurations files for it.
To configure mysql database
hibernate-mysql.cfg.xml
To configure oracle database
hibernate-oracle.cfg.xml
In Details, mysql configuration file be like this.
<?xml version="1.0" encoding="utf-8"?>
<!DOCTYPE hibernate-configuration PUBLIC
"-//Hibernate/Hibernate Configuration DTD 3.0//EN"
"http://hibernate.sourceforge.net/hibernate-configuration-3.0.dtd">
<hibernate-configuration>
<session-factory>
<property name="hibernate.bytecode.use_reflection_optimizer">false</property>
<property name="hibernate.connection.driver_class">com.mysql.jdbc.Driver</property>
<property name="hibernate.connection.password">PASSWORD</property>
<property name="hibernate.connection.url">jdbc:mysql://localhost:3306/UR_DB_NAME</property>
<property name="hibernate.connection.username">USERNAME</property>
<property name="hibernate.dialect">org.hibernate.dialect.MySQLDialect</property>
<property name="show_sql">true</property>
<mapping class="domain.EmployeeMysql"></mapping>
</session-factory>
</hibernate-configuration>
In Details, oracle configuration file be like this.
<?xml version="1.0" encoding="utf-8"?>
<!DOCTYPE hibernate-configuration PUBLIC
"-//Hibernate/Hibernate Configuration DTD 3.0//EN"
"http://hibernate.sourceforge.net/hibernate-configuration-3.0.dtd">
<hibernate-configuration>
<session-factory>
<property name="hibernate.bytecode.use_reflection_optimizer">false</property>
<property name="hibernate.connection.driver_class">oracle.jdbc.driver.OracleDriver</property>
<property name="hibernate.connection.password">PASSWORD</property>
<property name="hibernate.connection.url">jdbc:oracle:thin:UR DB NAME</property>
<property name="hibernate.connection.username">USERNAME</property>
<property name="hibernate.dialect">org.hibernate.dialect.Oracle10gDialect</property>
<property name="show_sql">true</property>
<mapping class="domain.EmployeeOracleSql"></mapping>
</session-factory>
</hibernate-configuration>
And code should be like this.
mysql configuration
private static SessionFactory sessionAnnotationFactory;
sessionAnnotationFactory = new Configuration().configure("hibernate-mysql.cfg.xml").buildSessionFactory();
Session session = sessionAnnotationFactory.openSession();
oracle sql configuration
sessionAnnotationFactory = new Configuration().configure("hibernate-oracle.cfg.xml").buildSessionFactory();
Session session = sessionAnnotationFactory.openSession()
Ideally you should move to Distributed transaction type of system[using Java Transaction Analyzer org.hibernate.transaction.JTATransactionFactory] in this case. If you are running in JBoss App Server, you can do it by using "Distributed Transaction Managers". You can learn more about it here.
You can also use a catalog with the value of the other database
#Table(name = "foo", schema = "bar", catalog = "OtherDatabase")
You can also Add mapping class in configuration.xml file
Note : this is for annotations and for resources use resources keyword instead of class
<mapping class="packageName.classNmae1"/>
<mapping class="packageName.classNmae2"/>
You can connect two databases test1 and test2, retrieve data with only one hibernate with some tricks:
hibernate SQLQuery: just add database name with the table "select * from test1.table1", "select * from test2.table2"
hibernate persistence: using the key schema in the hibernate mapping xml
<class name="Table1Class" table="table1" schema="test1">
<class name="Table2Class" table="table2" schema="test2">
Hi i trying to write my first Hibernate program,
its giving an error while instantiating the session factory.
I'm using hibernate 5.0.4 & java 8 & eclipse Luna SR1 (4.4.1) & oracle 11g.
MainClass is:
public class MainMethod {
public static void main(String[] args) {
SampleClass s = new SampleClass();
s.setId(1);
s.setValue("Value_1");
SessionFactory sessionFactory = new Configuration().configure().buildSessionFactory();
Session session = sessionFactory.openSession();
session.beginTransaction();
session.save(s);
session.getTransaction().commit();
}
}
the hibernate.cfg.xml is
<?xml version="1.0" encoding="utf-8"?>
<!DOCTYPE hibernate-configuration PUBLIC
"-//Hibernate/Hibernate Configuration DTD 3.0//EN"
"http://hibernate.sourceforge.net/hibernate-configuration-3.0.dtd">
<hibernate-configuration>
<session-factory>
<property name="hibernate.connection.driver_class">oracle.jdbc.driver.OracleDriver</property>
<property name="hibernate.connection.url">jdbc:oracle:thin:#localhost:1521:mndb11g</property>
<property name="hibernate.connection.username">temp_p</property>
<property name="hibernate.connection.password">temp_p</property>
<property name="connection.pool_size">1</property>
<property name="hibernate.dialect">org.hibernate.dialect.Oracle10gDialect</property>
<property name="hibernate.default_schema">temp_p</property>
<property name="hbm2ddl.auto">create</property>
<property name="show_sql">true</property>
<mapping class="com.h.SampleClass.SampleClass"/>
</session-factory>
</hibernate-configuration>
Its giving an exception at
SessionFactory sessionFactory = new Configuration().configure().buildSessionFactory();
The exception stack trace is
Exception in thread "main" java.lang.NullPointerException
at org.hibernate.boot.registry.classloading.internal.ClassLoaderServiceImpl$AggregatedClassLoader.getResources(ClassLoaderServiceImpl.java:173)
at java.util.ServiceLoader$LazyIterator.hasNextService(ServiceLoader.java:348)
at java.util.ServiceLoader$LazyIterator.hasNext(ServiceLoader.java:393)
at java.util.ServiceLoader$1.hasNext(ServiceLoader.java:474)
at org.hibernate.boot.registry.classloading.internal.ClassLoaderServiceImpl.loadJavaServices(ClassLoaderServiceImpl.java:324)
at org.hibernate.integrator.internal.IntegratorServiceImpl.<init>(IntegratorServiceImpl.java:40)
at org.hibernate.boot.registry.BootstrapServiceRegistryBuilder.build(BootstrapServiceRegistryBuilder.java:213)
at org.hibernate.cfg.Configuration.<init>(Configuration.java:119)
at com.h.MainMethod.main(MainMethod.java:19)
Can anyone please help to solve this.
Thanks in advance.
This could happen due to several reasons.
May be the Entity cannot be found. In your hibernate.cfg.xml file the entity is mentioned as com.h.SampleClass.SampleClass
Please double check the class name and the package name.
Make sure that the hibernate libraries are added as user libraries. Not system libraries. More info
Hope this helps.
It sounds like hibernate.cfg.xml is not on your classpath when the code runs. If you are using maven put it in src/main/resources.
i am trying Hibernate 4 in Netbeans 8, the problem is that after the the committed is done the application still running.
Here is the code
public class TestHibernateAnotation {
/**
* #param args the command line arguments
*/
public static void main(String[] args) {
Users user = new Users();
Users user2 = new Users();
user2.setUser_name("Djalil");
user.setUser_name("Daniel");
Session session = HibernateUtil.getSessionFactory().openSession();
session.beginTransaction();
session.save(user);
session.save(user2);
session.getTransaction().commit();
session.close();
System.out.print("End of code");
}
}
My Hibernate Config
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE hibernate-configuration PUBLIC "-//Hibernate/Hibernate Configuration DTD 3.0//EN" "http://hibernate.sourceforge.net/hibernate- configuration-3.0.dtd">
<hibernate-configuration>
<session-factory>
<property name="hibernate.dialect">org.hibernate.dialect.PostgreSQLDialect</property>
<property name="hibernate.connection.driver_class">org.postgresql.Driver</property>
<property name="hibernate.connection.url">jdbc:postgresql://localhost:5432/SalesTest</property>
<property name="hibernate.connection.username">postgres</property>
<property name="hibernate.connection.password">admin</property>
<property name="hibernate.current_session_context_class">thread</property>
<property name="hibernate.hbm2ddl.auto">create</property>
<mapping class="testhibernateanotation.NewClass"/>
<mapping class="testhibernateanotation.Users"/>
any Idea about this issue
thank you,
You need to explicitly destroy the service registry after session.close();. This seems to be a bug in newer hibernate versions. So basically your code that cleans up at the end should look like :
sessionFactory.close();
StandardServiceRegistryBuilder.destroy(sessionFactory.getSessionFactoryOptions().getServiceRegistry());
Plug: I had posted an example here - including this issue.
I found the solution (in an other post),
it would be adding this to your config files:
<property name="hibernate.c3p0.acquire_increment">1</property>
<property name="hibernate.c3p0.idle_test_period">100</property>
<property name="hibernate.c3p0.max_size">10</property>
<property name="hibernate.c3p0.max_statements">10</property>
<property name="hibernate.c3p0.min_size">10</property>
<property name="hibernate.c3p0.timeout">100</property>
They said that it is bug in hibernate 4
you will have to close the SessionFactory object [ HibernateUtil.getSessionFactory().openSession() ]
The SessionFactory is a heavyweight object; it is usually created during application start up and kept for later use.The SessionFactory is a thread safe object and used by all the threads of an application.
We can create one SessionFactory implementation per database in any application. If your application is referring to multiple databases, then you need to create one SessionFactory per database.
its how hibernate SessionFactory was designed.
https://docs.jboss.org/hibernate/orm/3.5/api/org/hibernate/SessionFactory.html
I read almost all thread about How configure hibernate datasource but I can't find help. I mean in hibernate.cfg.xml element <property name="hibernate.connection.datasource"> ? </property> i know i have to set up with jndi. i try to google it but all articles are based on developing with jbossas, ejb, tomcat, weblogic and their jndi. But i need jndi of java SE. Correct me please if i am wrong.
I am new to Hibernate so I am using NetBeans, SE project with Hibernate 3.2.5 jars. (I am studying Hibernate from book Beginning Hibernate 2nd edition, apress and source code derive on the book...)
My hibernate.cfg.xml
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE hibernate-configuration PUBLIC "-//Hibernate/Hibernate Configuration DTD 3.0//EN"
"http://hibernate.sourceforge.net/hibernate-configuration-3.0.dtd">
<hibernate-configuration>
<property name="hibernate.connection.driver_class">
com.mysql.jdbc.Driver
</property>
<property name="hibernate.connection.url">
jdbc:mysql://127.0.0.1:3306/asd
</property>
<property name="hibernate.connection.username">root</property>
<!-- nastaveni dialektu -->
<property name="hibernate.dialect">
org.hibernate.dialect.MySQLInnoDBDialect
</property>
<!-- jndi nastaveni -->
<property name="hibernate.connection.datasource">
java:hibernate/SessionFactory
</property>
<property name="hibernate.connection.username">root</property>
<property name="cache.provider_class">
org.hibernate.cache.NoCacheProvider
</property>
<property name="hibernate.jndi.class">javax.naming.InitialContext</property>
</session-factory>
</hibernate-configuration>
And I have only one class FirstHibernate:
package firsthibernate;
import java.util.List;
import org.hibernate.Session;
import org.hibernate.SessionFactory;
import org.hibernate.cfg.AnnotationConfiguration;
public class FirstHibernate {
private static SessionFactory session = null;
private static Session s = null;
public static void main(String[] args) {
try {
session = new AnnotationConfiguration().configure().buildSessionFactory();
s = session.openSession();
s.beginTransaction();
// List l = s.createQuery("from query").list();
s.getTransaction().commit();
} catch (Exception ex) {
if (s.getTransaction() != null) {
//s.getTransaction().rollback();
}
System.out.println(ex.toString());
} finally {
s.close();
}
}
}
I obtain this message:
SEVERE: Could not obtain initial context javax.naming.NoInitialContextException: Cannot instantiate class: javax.naming.InitialContext [Root exception is java.lang.ClassCastException: javax.naming.InitialContext cannot be cast to javax.naming.spi.InitialContextFactory]
You don't need that complex setup for SE.
Hope this link helps
Hibernate Sample App
Check Hibernate Quick Start
From what i perceive you are configuring hibernate in a non managed environment . In Non managed environment hibernate handles the connections via simple connection pools .Its not possible to have a data source configured in the non managed mode . You can have a look at http://docs.jboss.org/hibernate/orm/3.3/reference/en/html/transactions.html#transactions-demarcation-nonmanaged for further details .