Update one single column in database using JPQL - java

How to write a JPQL query to update a single column in MySql DB :
Regular SQL update query :
Update NATAddress SET ordinal = ? WHERE ordinal = ? AND natId = ?
JPQL update query :
UPDATE NATAddress na SET na.ordinal = ?1 WHERE na.ordinal = ?2 AND na.networkDomain.natId =?3
Eclipse shows following error for above JPQL update query
Input parameters can only be used in the WHERE clause or HAVING clause of a query.
Looks like JPA specifications doesn't allow to set input parameters in update columns.
Is there any other way to update other than updating the whole JPA Entity using merge() method?

Update your query to be like this I assume this is the Class name and this is the name of its attributes
UPDATE NATAddress na SET na.ordinal = ? WHERE na.ordinal = ? AND na.networkDomain.natId =?

try this
String query = "Update NATAddress SET ordinal = '"+Parameter1+"' WHERE ordinal = '"+Parameter2+"' AND natId = '"+Parameter3+"'";

Related

How to force Hibernate use AND in update query?

I am trying to update a raw by composite primary key by using hibernate.
Hibernate uses the next style for such updates:
update mytable set mycolumn=321 where (left_pk, right_pk) = (123, 456);
Is it possible to force hibernate to use the next style?:
update mytable set mycolumn=321 where left_pk = 123 and right_pk = 456;
Both queries work but with a huge difference (at least in MariaDB).
If we use repeatable read transaction then the first query locks the whole table for updates and the second query locks only the single row for updates.
I would prefer to lock only a single row, so I need to use the second query.
You can go for NamedQueries approach in Hibernate,
For example:
//Create Query
#NamedQueries({ #NamedQuery(name = " YOUR QUERY NAME",
query = "from DeptEmployee where department = :department and emp = :emp") })
// set multiple parameters
query.setParameter("department",department)
.setParameter("emp", emp)
Try giving this a shot.

hibernate hql - return updated rows id list after execute update query

I'm using Hibernate Query Language(HQL) with Oracle database in my Java spring MVC application. I have write an HQL update query in this way:
String hql = "update " + MyModel.class.getName() + " e set e.field = " + value + " where ..."
//Acquiring session
...
Query query = session.createQuery(hql);
int result = query.executeUpdate();
The executeUpdate() method returns number of updated rows. But I want to get a list of the ids of updated rows after executing the update query. Is there any way of doing this in HQL?
As far as I know there is no such functionality in JPA/Hibernate. But you can create native query and use native SQL. I do not know oracle, but in PostgreSQL I would write :
String sql = "update table set field = :values where ... returning id";
Query query = session.createNativeQuery(sql);
query.setParameter("value", value);
List ids = query.list();
May be oracle have similar functional and this will help you.
Blaze-Persistence, a library that works on top of JPA/Hibernate, adds support for this.
Here some more information about that: https://persistence.blazebit.com/documentation/core/manual/en_US/index.html#returning-from-update-statement

Need column names and column values from update sql before executing

I need to know the list of the column and values from the update sql using java. Code is to read a update query and take backup of the actual column values before executing the update sql. For this is need to know the column names. Please advise!
sql = update testenv.employee set gender = '2',StudentInd = '112233' where empID in (987987);
String criteriaQuery = resultset.getString("query"); // this is the update statement which is not constant and varies everytime.
String schema = StringUtils.substringBetween(criteriaQuery.toUpperCase(), "UPDATE ", ".").trim();
String table = StringUtils.substringBetween(criteriaQuery.toUpperCase(), ".", "SET").trim();
String columnName = StringUtils.substringBetween(criteriaQuery.toUpperCase(), "SET", "=").trim();
But columnName will not get the correct columns. Need to optimise the code such that i can get the entire column names from the update query.
If you're using JDBC, you can use the following:
ResultSetMetaData md = rs.getMetaData();
after getting the result set of your select statement.
http://www.roseindia.net/jdbc/jdbc-mysql/DiscriptionTable.shtml
Provides a clear example, the same applies for SQLServer databases and Oracle.

Hibernate 2 with MSSQL for ORDER BY

I have been working with Oracle and Postgre and recently switched to MS SQL 2012.
I use hibernate in my application and wherever I have used the Order by Criteria:
(criteria.addOrder(Order.asc("applicationId")));
It causes an error saying:
aggregate functions dont work.
Once I comment that line out my program works and data can be retrieved.
I'm using Hibernate 3.
Is there any way to order it through hibernate without this error?
edit..
This is one error I get,
Column "SKY.tcrent.RENTNO" is invalid in the ORDER BY clause because
it is not contained in either an aggregate function or the GROUP BY
clause.
Edit 2..
MY query
Query tcSchaduleQ = getSession().createQuery("SELECT SUM(tcs.dueAmount) FROM TrialCalculationSchedule tcs WHERE tcs.facilityId=:facilityId AND tcs.rentalNumber>:rentalNumber AND tcs.dueDate>:dueDate AND dueTypeId IN(:dueTypeId) ORDER BY tcs.rentalNumber ").setInteger("rentalNumber", facility.getPeriod() - noOfprePayments).setInteger("facilityId",facility.getFacilityId()).setDate("dueDate", date).setParameterList("dueTypeId", plist);
Number tcsAmt = (Number) tcSchaduleQ.uniqueResult();
and this is what hibernate generates in HQL
SELECT
SUM(tcs.dueAmount)
FROM
TrialCalculationSchedule tcs
WHERE
tcs.facilityId=:facilityId
AND tcs.rentalNumber>:rentalNumber
AND tcs.dueDate>:dueDate
AND dueTypeId IN(
:dueTypeId
)
ORDER BY
tcs.rentalNumber
and this is the SQL
select
SUM(trialcalcu0_.DUEAMT) as col_0_0_
from
SKYBANKSLFHP.tcrent trialcalcu0_
where
trialcalcu0_.FACID=?
and trialcalcu0_.RENTNO>?
and trialcalcu0_.DUEDATE>?
and (
trialcalcu0_.DUETYPEID in (
? , ?
)
)
order by
trialcalcu0_.RENTNO
Look Like you mix aggregate and non-aggregate expressions .If you are using any aggregate function like AVG() in Select query with some other non-aggregate then you must use Group By ..
Try something like this
createQuery("SELECT SUM(tcs.dueAmount) As DueAmount ...
If you are using Criteria then it should be like this
Criteria crit = sess.createCriteria(Insurance.class);
ProjectionList proList = Projections.projectionList();
proList.add(Projections.sum("investementAmount"));
crit.setProjection(proList);
List sumResult = crit.list();

java.lang.String cannot be cast HQL

Updated
Error says:
ava.lang.String cannot be cast to com.test.test.classes.TblTaxType
what is happening is when I add the tag select distinct taxtcode error is appearing. But when I removed the select tag like FROM tblTaxType tbl_tax_type WHERE bfnsCode = ? everything is fine. What is the cause? this is my code:
String hql = "SELECT DISTINCT TAXT_CODE FROM tbl_tax_type WHERE BFNS_CODE = ?";
try {
setSession(HibernateUtil.getSession());
#SuppressWarnings("unchecked")
List <TblTaxType> resultList = getSession().createSQLQuery(hql)
.setString(0, bfnsCode)
.list();
Your entity is probably named TblTaxType, not tblTaxType. Case matters.
Side note: don't name sql an HQL query. SQL and HQL are different languages.
Solved it using GROUP BY instead by using DISTINCT.
String hql = "FROM TblTaxType tbl_tax_type WHERE bfnsCode = ? GROUP BY taxtCode";
Your query returns TAXT_CODE, this field is a property of your TblTaxType entity, so you can't cast one property (string) in your main entity. This is the reason of your error.
If you need complete entity you must change your query but DISTINCT is not useful in this case because if you extract complete entity, there's ID field (different for each row). If you want a first element, you can add in your query ORDER BY clause with LIMIT 1 (is MySql).
A solution with GROUP BY works only if you use MySql as DBMS because if you have Sql Server the correct behaviour of field list / group by is: a field in field list must be in GROUP BY cluse or must be in aggregate function.

Categories