我有一个具有“解释器 SQL”功能的网络应用程序。用户可以编写一些命令并执行它。
例如,用户想要执行3x操作:
1. ALTER TABLE "aaab".WHATEVER RENAME TO "Something";
2. ALTER TABLE "aaab".RESOURCES RENAME TO "SomethingElse";
3. ALTER TABLE "aaab".EXAMCATEGORIES MODIFY NAME NUMBER;
<小时/>
我想要实现的目标:
- 如果操作 1、2、3 成功,则
提交
所有 3x 操作 - 如果操作 1、2 成功,但操作 3 未成功,则
回滚
所有 3x 操作
通常,如果列表中的任何操作不成功,那么我想回滚
所有操作。
这是我的翻译:
public ArrayList<String> executeSQL(String[] queryRows) {
ArrayList<String> listException = new ArrayList<String>();
for (int i = 0; i < queryRows.length; ++i) {
String query = queryRows[i];
if(query.trim().length() > 5 && query.trim().substring(0, 6).toUpperCase().equals("SELECT")){
try{
mapList = jdbcTemplate.queryForList(query);
int rows = mapList.size();
listException.add("Success! { affected rows --> [" + rows + "] }");
updateFlag = true;
}catch (DataAccessException exceptionSelect){
listException.add(exceptionSelect.getCause().getMessage());
updateFlag = false;
break;
}
}
else if(whatKindOfStatementIsThat(query,"DDL")){
try{
jdbcTemplate.execute(query);
listException.add("Success!");
updateFlag = true;
}catch (DataAccessException exceptionDDL){
listException.add(exceptionDDL.getCause().getMessage());
updateFlag = false;
break;
}
}
else if (whatKindOfStatementIsThat(query,"DML")){
try {
int rows = jdbcTemplate.update(query);
listException.add("Success! { zaafektowane wiersze --> [" + rows + "] }");
updateFlag = true;
}catch (DataAccessException exceptionDML){
listException.add(exceptionDML.getCause().getMessage());
updateFlag = false;
break;
}
}
else{
try{
jdbcTemplate.execute(query);
listException.add("Success!");
updateFlag = true;
}catch (Exception exception){
listException.add(exception.getCause().getMessage());
updateFlag = false;
break;
}
}
}
return listException;
}
其实很简单,首先检查输入的是什么类型的语句。
1.如果语句是select
,那么我需要结果列表mapList = jdbcTemplate.queryForList(query);
2.如果语句是DDL
,那么我不需要任何东西jdbcTemplate.execute(query);
3.如果语句是DML
,那么我需要受影响的行数int rows = jdbcTemplate.update(query);
4.其他一切,只需执行 native 查询jdbcTemplate.execute(query);
我将语句保存在 ArrayList 中,它们在循环中一个接一个地执行。
例如,如果我有那个循环:
public void executeSQL (String[] queryRows){
for(int i = 0; i < queryRows.length; ++i){
// statements are executed there one after another.
}
}
<小时/>
我怎样才能实现这样的目标?
public void executeSQL(String[] queryRows){
...begin()
for(int i = 0; i < queryRows.length; ++i){
// statements are executed there one after another.
}
if(myCondition)
...commit()
else
...rollback()
}
<小时/>
最佳答案
使用 @Transactional 注释您的方法,并且只有当您从类外部调用它时所有操作都成功,它才会提交
Describes a transaction attribute on an individual method or on a class
了解更多信息Understanding the Spring Framework’s declarative transaction implementation
It is not sufficient to tell you simply to annotate your classes with the
@Transactional
annotation, add@EnableTransactionManagement
to your configuration, and then expect you to understand how it all works
关于java - 使用 jdbcTemplate 时如何手动处理事务?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/60088866/