org.hibernate.QueryException: query must……的解决方案

本文介绍了解决使用Hibernate的Query进行update操作时遇到的错误:org.hibernate.QueryException:querymustbeginwithSELECTorFROM。通过调整hibernate配置文件中的特定属性,可以启用对更新语句的支持。

 在使用hibernate的query进行update时,如果提示
org.hibernate.QueryException: query must begin with SELECT or FROM,不表示hibernate版本的query不支持更新,检查hibernate的配置文件会发现有个属性设置为
  <property name="hibernateProperties">
   <props>
    <prop key="hibernate.query.factory_class">org.hibernate.hql.classic.ClassicQueryTranslatorFactory</prop>
    <prop key="hibernate.show_sql">false</prop>
   </props>    
  </property>

这个属性会使得hibernate不支持更新语句,如果使用executeUpdate执行更新语句就会报错。设置这个属性的是指定hibernate的hql解析器。

你遇到的异常: ``` org.springframework.orm.hibernate.HibernateQueryException: query must begin with SELECT or FROM: UPDATE ... ``` 是因为你在使用 `HibernateTemplate.find(sql)` 方法时传入了一条 **UPDATE 语句**,而 `find()` 方法只能用于 **查询(SELECT)语句**,不能用于执行更新操作。 --- ## ✅ 正确做法:使用 HibernateTemplate 执行 HQL 更新语句 要执行类似 `UPDATE` 这样的写操作,你需要使用 `HibernateTemplate.execute()` 方法,并在其中使用 `createQuery()` 创建一个更新语句。 --- ### ✅ 修改后的代码如下: ```java String sql = "UPDATE PayMes SET actualAmount = " + createPay.getActualAmount() + " WHERE transactionSerialNo = " + createPay.getTransactionSerialNo(); this.getHibernateTemplate().execute(new HibernateCallback<Integer>() { @Override public Integer doInHibernate(Session session) throws HibernateException { Query query = session.createQuery(sql); return query.executeUpdate(); // 返回影响的行数 } }); ``` --- ## ✅ 更安全的做法:使用参数化 SQL 防止注入 直接拼接字符串容易导致 **HQL 注入问题**,建议使用参数化方式: ```java final BigDecimal actualAmount = createPay.getActualAmount(); final Long serialNo = createPay.getTransactionSerialNo(); String hql = "UPDATE PayMes SET actualAmount = :amount WHERE transactionSerialNo = :serialNo"; this.getHibernateTemplate().execute(new HibernateCallback<Integer>() { @Override public Integer doInHibernate(Session session) throws HibernateException { Query query = session.createQuery(hql); query.setParameter("amount", actualAmount); query.setParameter("serialNo", serialNo); return query.executeUpdate(); } }); ``` --- ## ✅ 补充说明 | 方法 | 是否支持更新 | 用途 | |------|---------------|------| | `hibernateTemplate.find()` | ❌ 否 | 只能用于 SELECT 查询 | | `hibernateTemplate.execute()` | ✅ 是 | 可以执行任意 HQL 操作(包括 UPDATE、DELETE 等) | --- ## ✅ 建议升级到现代 Spring + Hibernate / JPA 方式 如果你正在使用较新的 Spring Boot 或 Spring Data JPA,推荐使用以下方式替代 `HibernateTemplate`: ```java @Autowired private SessionFactory sessionFactory; public int updatePayMes(Pay createPay) { String hql = "UPDATE PayMes SET actualAmount = :amount WHERE transactionSerialNo = :serialNo"; Session session = sessionFactory.getCurrentSession(); return session.createQuery(hql) .setParameter("amount", createPay.getActualAmount()) .setParameter("serialNo", createPay.getTransactionSerialNo()) .executeUpdate(); } ``` ---
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值