JPARepository - 使用与派生查询的日期比较进行删除

JPARepository - delete using date comparison with derived query

我正在尝试在 Spring 引导中使用 JPARepository 删除小于特定日期的记录,对于给定的用户 ID

应该是这样的Delete * from [table] where expiration_date < [date] and userid = [userid]

我想我应该可以使用其中一种自动生成的方法

    int deleteByExpiryDateBeforeAndUser(Date date, User user);

但这是生成 Select 而不是删除。我做错了什么?

更新

实体class

@Getter
@Setter
@ToString
@Entity(name = "refresh_token")
public class RefreshToken {
    @Id
    @GeneratedValue(strategy = GenerationType.AUTO)
    private long id;

    @OneToOne
    @JoinColumn(name = "user_id", referencedColumnName = "id")
    private User user;

    @Column(nullable = false, unique = true)
    private String token;

    @Column(nullable = false)
    private Date expiryDate;

    public RefreshToken() {
    }
}

存储库class

@Repository
public interface RefreshTokenRepository extends JpaRepository<RefreshToken, Long> {
    Optional<RefreshToken> findByToken(String token);

     @Modifying
    void deleteByUserIdAndExpiryDateBefore(Long userId, Date expiryDate);

    int deleteByUser(User user);
}

我是这样称呼它的

 @Transactional
 public void deleteExpiredTokens(User user) {
        refreshTokenRepository.deleteByUserIdAndExpiryDateBefore(user.getId(), new Date());
    }

您会看到 select 语句,因为 Spring 数据首先按条件加载实体。

然后一旦实体变为 'managed' Spring 数据就会为找到的每个实体发出删除查询。

如果您想避免冗余 SQL 查询 - 您必须考虑 @Query 注释。

那么您的代码将如下所示:

@Repository
public interface RefreshTokenRepository extends JpaRepository<RefreshToken, Long> {
    // ...
  
    @Query(value = "DELETE FROM refresh_token WHERE user_id =:userId AND expiry_date < :expiryDate", nativeQuery = true)
    @Modifying
    void deleteByUserIdAndExpiryDateBefore(Long userId, Date expiryDate);

    //...
}