如何处理Spring Data JPA中的一系列ID批量删除?

JSO*_*JSO 12 hibernate spring-mvc spring-data spring-data-jpa

现在我有一个类User,我arrayjsp或获得了一个请求数据html.

列出这个 Integer[] arr=[5,6,9,10,62,52,21]

然后我使用两种方法来完成膨胀删除操作.

@Transactional
@Override
public void deleteUser(Integer id) {

    oneRepository.delete(id);
}


@Transactional
@Override
public void deleteSomeUser(Integer[] ids) {

    for (Integer id : ids) {

        deleteUser(id);

    }

}
Run Code Online (Sandbox Code Playgroud)

我想知道如果这是一种更有效的方法来完成这个动作.

你可以看到我的日志:它似乎不太好!

[94, 95, 91, 92, 93]
Hibernate: 
    delete 
    from
        sshh_user 
    where
        ID=?


Hibernate: 
    delete 
    from
        sshh_user 
    where
        ID=?



Hibernate: 
    delete 
    from
        sshh_user 
    where
        ID=?



Hibernate: 
    delete 
    from
        sshh_user 
    where
        ID=?



Hibernate: 
    delete 
    from
        sshh_user 
    where
        ID=?



Hibernate: 
    select
        count(practice0_.ID) as col_0_0_ 
    from
        sshh_user practice0_
Run Code Online (Sandbox Code Playgroud)

Laz*_*het 24

只需将以下内容添加到用户存储库界面即可

void deleteByIdIn(List<Integer> ids);
Run Code Online (Sandbox Code Playgroud)

Spring将通过方法名称派生自动生成相应的查询.

https://docs.spring.io/spring-data/jpa/docs/current/reference/html/#jpa.query-methods

编辑:关于此的更多详细信息

使用Springs Repository接口之类的CrudRepository,JpaRespository带来了基本的数据库操作集,如创建,读取,更新,删除,分页,排序等.

要手动添加一些简单的查询,例如搜索用户名或邮件地址,弹簧提供了良好的机制,而没有注释任何基于字符串的HQL查询或类似问题.

Spring只会分析您的方法名称,搜索关键字.阅读上面提供关键字的文档链接.

a的示例方法CrudRepository<User>:

Iterable<User> findByNameLike(String search) 解决了 select * from user where name like '<search>'

void deleteByIdIn(List<Integer> ids) 解决了 delete from user where id in ([ids])

  • 这在2.0.5.RELEASE版本中不起作用。deleteByIdIn生成与您提供的ID数量一样多的删除查询。 (2认同)
  • 尝试了deleteByIdIn()并查看了Hibernate调试日志,看起来该方法被转换为多个删除查询,而不是上面提到的单个查询。我最终按照接受的答案中的概述编写了自定义查询。 (2认同)

Ali*_*ani 14

假设你有一个UserRepository喜欢:

public interface UserRepository extends JpaRepository<User, Integer> {}
Run Code Online (Sandbox Code Playgroud)

然后,您可以将以下修改查询方法添加到您的UserRepository:

/**
 * Delete all user with ids specified in {@code ids} parameter
 * 
 * @param ids List of user ids
 */
@Modifying
@Query("delete from User u where u.id in ?1")
void deleteUsersWithIds(List<Integer> ids);
Run Code Online (Sandbox Code Playgroud)

最后,您可以更改批量删除服务,如下所示:

@Transactional
@Override
public void deleteSomeUser(Integer[] ids) {
    oneRepository.deleteUsersWithIds(Arrays.asList(ids));
}
Run Code Online (Sandbox Code Playgroud)

这将生成一个删除查询,如:

Hibernate: delete from users where id in (? , ? , ?)
Run Code Online (Sandbox Code Playgroud)

当您从另一个方法调用一个建议方法时,也要注意自我调用问题public.