使用 spring 数据和 JDBC 模板进行交易处理
Transaction handling with spring data and JDBC Template
我想在不先为每个对象创建 Select 的情况下进行批量删除。我没有找到使用 spring 数据 jpa 和实体管理器来执行 this.For 的方法,因此我尝试了 JDBC 模板。
但是,我遇到了可分页的问题。
这段代码工作正常,所有删除都是通过批处理执行的。不幸的是,每个实体都有一个不必要的 select。
@Transactional
public void deleteFoos() {
Page<Foo> page = repository.findAll(PageRequest.of(0,50);
Pageable pageable = null;
do {
if ( pageable != null ) {
page = repository.findAll( pageable );
}
repository.deleteAll( page.getContent() );
} while ( (pageable = page.nextPageable()) != Pageable.unpaged() );
}
我现在尝试的是直接用 JDBC 模板实现整个事情。
@Transactional
public void deleteFoos() {
Page<Foo> page = repository.findAll(PageRequest.of(0,50);
Pageable pageable = null;
do {
if ( pageable != null ) {
page = repository.findAll( pageable );
}
//repository.deleteAll( page.getContent() );
jdbcTemplate.batchUpdate(
"DELETE FROM foo WHERE (id = ?)",
page.getContent(),
page.getTotalItems(),
( preparedStatement, argument ) -> {
preparedStatement.setObject( 1, argument.getId() );
} );
} while ( (pageable = page.nextPageable()) != Pageable.unpaged() );
}
但是,第三页和第四页始终是空的。似乎直接执行了删除。自动提交已关闭,还有什么问题吗?
编辑:Jens 的解决方案工作正常:“您可以简单地重复请求第一页并将其删除。”
JdbcTemplate
只是执行 SQL 语句,所以是的,它们会立即执行。与 JPA 操作一样,不涉及缓存。
但即使是 JPA 操作也会在执行查询之前刷新到数据库中,所以差别并不大。
您可以简单地重复请求第一页并删除它。
但是使用带删除的分页没有多大意义,您可以只删除 table 中的所有行并在一次往返数据库中完成:
DELETE FROM foo
如果您想批量删除,您仍然可以在不加载任何应用程序的情况下执行此操作。详细信息可能取决于数据库,但与此类似的东西应该可以很好地工作:
DELETE FROM foo
LIMIT 100;
我想在不先为每个对象创建 Select 的情况下进行批量删除。我没有找到使用 spring 数据 jpa 和实体管理器来执行 this.For 的方法,因此我尝试了 JDBC 模板。 但是,我遇到了可分页的问题。 这段代码工作正常,所有删除都是通过批处理执行的。不幸的是,每个实体都有一个不必要的 select。
@Transactional
public void deleteFoos() {
Page<Foo> page = repository.findAll(PageRequest.of(0,50);
Pageable pageable = null;
do {
if ( pageable != null ) {
page = repository.findAll( pageable );
}
repository.deleteAll( page.getContent() );
} while ( (pageable = page.nextPageable()) != Pageable.unpaged() );
}
我现在尝试的是直接用 JDBC 模板实现整个事情。
@Transactional
public void deleteFoos() {
Page<Foo> page = repository.findAll(PageRequest.of(0,50);
Pageable pageable = null;
do {
if ( pageable != null ) {
page = repository.findAll( pageable );
}
//repository.deleteAll( page.getContent() );
jdbcTemplate.batchUpdate(
"DELETE FROM foo WHERE (id = ?)",
page.getContent(),
page.getTotalItems(),
( preparedStatement, argument ) -> {
preparedStatement.setObject( 1, argument.getId() );
} );
} while ( (pageable = page.nextPageable()) != Pageable.unpaged() );
}
但是,第三页和第四页始终是空的。似乎直接执行了删除。自动提交已关闭,还有什么问题吗?
编辑:Jens 的解决方案工作正常:“您可以简单地重复请求第一页并将其删除。”
JdbcTemplate
只是执行 SQL 语句,所以是的,它们会立即执行。与 JPA 操作一样,不涉及缓存。
但即使是 JPA 操作也会在执行查询之前刷新到数据库中,所以差别并不大。
您可以简单地重复请求第一页并删除它。
但是使用带删除的分页没有多大意义,您可以只删除 table 中的所有行并在一次往返数据库中完成:
DELETE FROM foo
如果您想批量删除,您仍然可以在不加载任何应用程序的情况下执行此操作。详细信息可能取决于数据库,但与此类似的东西应该可以很好地工作:
DELETE FROM foo
LIMIT 100;