In my database code I use some Hibernate native SQL queries (inserts, deletion, updates). I understand that when I use HQL and the cache is on than the state of the DB is stable whenever I call the DB with the HQL. However, I wonder what happens if I use native SQL queries, e.g. I insert some data (but do not commit it) and than I try to fetch some data with a HQL query. Will I get the inserted data too?
Any hints?
I would say, that it depends on underlying database and transactions setting. But even HQL is translated to native SQL and executed. As long as you stay in same transaction, you will be able to load changes made with native SQL via HQL. But keep in mind, that HQL queries interat with caches, proxies and other hibernate stuff - there could be some weird issues, because natiev SQL completely bypasses this ( this is purpose of native queries - fast lane around all the hibernate stuff )
Adding to Konstantin Pribluda's answer I can say that in the reverse situation : adding data through Hibernate(even with session.save()) and then fetching data with native SQL resulted in the native SQL-query not fetching the added data.
So when using different types of query's in the DAO, I always flush the session first before I use a native SQL query... Never know which method's get mixed in the Service layer.
Yes, you will get it because all of your DAO queries will executed one by one whether its HQL or SQL. So if insert query is first in order then you will get inserted records.
Related
I use Spring Data JPA (hibernate) generated queries for fetching data from my Sqlserver. Now i am getting performance related issues in my system.
Load findByLoadId(Integer loadId);
This is the query i am using to get data. This query returns 25 cell data but i only use 5 data from that.
can i use direct native query like
select id,date,createdBy,createdOn,loadName from Load where
loadId=:loadId
but if native query is suggestable then I am having question like Does ORM frameWork reduce performence by getting unneeded data from Database?
By "data cell" I assume that you are referring to database table columns, and not to records. The answer to your question is that yes, ORM frameworks might tend to just do a SELECT * under the hood, which can result in unwanted information being sent across the network to your application. If the JPA repository interface is behaving this way, you may switch to either an explicit JPA query (e.g. using the #Query annotation), or even a native query. Then, just select the columns you want. The issue here is that ORM frameworks map object templates (e.g. classes) to entire database tables. So, the concept of entity implicitly includes every database column. If you go with the option of selecting only certain columns, you may need to do some juggling on the Java side. Note that if the use a JPA query, your code would still, in theory, be database independent.
I'm using Java with Hibernate. I want to:
Save my data to the database
Run sql to verify the result
If the result is valid, then commit, otherwise rollback
So, is it possible to save the result to the database without commit, so that I can use sql / hql to verify data and rollback if needed?
My actual scenario is quite complicated, the simplified version is:
PERSON joins PERSON_CAR joins CAR joins CAR_SEAT joins SEAT
Make changes and commit everything
If any PERSON has more than 10 SEATs, I want to show errors
If I could save everything to the database first, then I can write SQL with GROUP BY and HAVING statement to aggregate the data and only return the ones that exceed.
Yes, there is session.flush() function, which could be used for that purpose.
I have to insert ~40K records in 2 tables(say table1 & table2) in the database.
The insert in table2 is conditional. A record should be inserted in table2 if and only if a record is inserted in table1 successfully.
Can this be done in batch? I'm using JDBC driver. I'm using Oracle 10g XE.
What is the best approach to do this? Should I go for db pooling with multi-threading?
The executeUpdate method will return the number of rows affected by your statement. Could use this as a comparison to check it had executed successfully.
My suggestion is perform the business logic for the operation as close to the data as possible. This will mean having a PL/SQL procedure to act as an API for the functionality you wish to perform.
This will make your code trivial; a simple call to the database procedure which will return something giving you the result.
All the logic applied to the data is performed by code designed almost exclusively to manipulate data. Unlike Java which can manipulate data but not as well as PL/SQL. Incidentally it is also likely to be much faster.(this presentation on Youtube is very informative, if a little long - https://www.youtube.com/watch?v=8jiJDflpw4Y )
With SQL I can copy data from one table to another mirror table. (e.g. insert into TABLE_EXAMPLE_COPY select * from TABLE_EXAMPLE; .
How can I do the same thing using Hibernate org.hibernate.Criteria or org.hibernate.Query or org.hibernate.SQLQuery?
If you want to perform that action from within the boundaries of JPA or Hibernate, the best way to accomplish that is to use a Native SQL statement.
session
.createNativeQuery( "INSERT INTO table_copy SELECT * FROM table" ).
.executeUpdate();
The other options involve reading the source table into a POJO and then transforming that into the POJO representation for the copy table and saving those rows. The problem with these is that you also introduce network latency and JVM overhead just to create an in-memory object, transform it, and then push it back over the network to the database.
The presented above solution avoids all those drawbacks and allows the database to handle all that in the best performing way it knows how.
I was reading the Hibernate HQL tutorial and found that HQL doesn't support INSERT INTO..VALUES.. but INSERT INTO..SELECT.. i.e. HQL only support insert from another table.
Suppose I want to insert same values in one table and that data is not from any other table i.e. the values are not in any other table.Then how can I do that in HQL?
Also, would like to know the rational behind such restrictions in HQL?
You don't need to use hql to insert if the data is from another table.
Simply get a reference to your entity, get a hold of a Hibernate session, and call save().
According to http://docs.jboss.org/hibernate/orm/4.0/devguide/en-US/html/ch04.html#d0e2116
Pseudo-syntax for INSERT statements
INSERT INTO EntityName properties_list select_statement
Only the INSERT INTO ... SELECT ... form is supported. You cannot specify explicit values to insert.
Hibernate is an ORM framework (Object-Relational Mapping).
Its job is that you give objects (Entities) to it and he manages the storage (through Session.save(), IIRC).
So, you do not use the HQL to insert new records, but use the ORM methods.
And (this is a guess) on the other hand, since loading entities from a table, copying them to other entities and storing them one by one is slow, HQL provides a shortcut to the SQL in the DB just for that specific operation for performance purposes.
You can use session.save(object) to insert data into tables.