使用简单的UPDATE查询时,不支持DML操作。

38

当我使用以下HQL时,出现错误不支持DML操作...

@Query("UPDATE WorkstationEntity w SET w.lastActivity = :timestamp WHERE w.uuid = :uuid")
void updateLastActivity(@Param("uuid") String uuid, @Param("timestamp") Timestamp timestamp);

可能是什么原因导致这个问题?考虑到我在谷歌上只找到了少数几个结果,它似乎不是常见的错误。


你能提供完整的代码清单和堆栈跟踪吗? - Ajay Bhojak
看看这个被接受的解决方案 https://dev59.com/7mkv5IYBdhLWcg3w91hG#12426144 看起来很相似。 - fn.
2
+1 对于“@Modifying”的建议是很不错的。因为这个问题似乎是关于Spring JPA Repository的,所以您应该将其添加为默认答案,并继续提出问题。 - minni
5个回答

39

4
我只需通过添加修改注释就解决了相同的问题。另一个提示:函数返回类型必须为void,因为我将函数从普通查询函数复制过来,所以返回类型是List<SomeModelClass>,即使我添加了修改注释后仍然会出现相同的错误。 - cn123h
@cn123h遇到了同样的问题,复制粘贴时返回类型为List<T>而不是void。 - Vishnoo Rath

15

我也遇到过注释的同样问题。在搜索并尝试了一些技巧后,我成功地解决了它。

  1. 在使用JPA的DML操作时,请验证以下步骤:

    在所需的方法上使用注解 @Modifying(org.springframework.data.jpa.repository.Modifying)@Transactional(org.springframework.transaction.annotation.Transactional)

  2. 使用 void 作为方法返回类型。

例如:

@Modifying
@Query("UPDATE ProcedureDTO o SET o.isSelectedByUser =?1")
@Transactional
public void getListOfProcedureBasedOnSelection(Boolean isSelected);```

2
我遇到了完全相同的问题,我的情况只需要添加@Modifying注释。根据文档:
指示查询方法应被视为修改查询,因为这改变了执行它的方式。仅当在通过Query注释定义的查询方法上使用时,才考虑此注释。它不适用于自定义实现方法或从方法名称派生的查询,因为它们已经控制了底层数据访问API或通过名称指定是否修改。
需要@Modifying注释的查询包括INSERT、UPDATE、DELETE和DDL语句。

1

请确保调用 updateLastActivity 的服务类方法具有 @Transactional(org.springframework.transaction.annotation.Transactional) 注释。并将存储库方法修改为以下内容:

import org.springframework.data.jpa.repository.Modifying;
import org.springframework.data.jpa.repository.Query;
...
@Modifying
@Query("UPDATE WorkstationEntity w SET w.lastActivity = :timestamp WHERE w.uuid = :uuid")
void updateLastActivity(@Param("uuid") String uuid, @Param("timestamp") Timestamp timestamp);

欲了解更多信息,请使用此答案


0

我也遇到了同样的问题,因为q是一个Query类的对象,所以不能使用q.list()进行更新或删除操作,而应该使用q.executeUpdate()。


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接