開篇
?這篇文章的目的是講解RM Executor模塊當(dāng)中一些通用的方法,這些方法在各個(gè)Executor的父類當(dāng)中實(shí)現(xiàn)的挑宠,各個(gè)子類Executor模塊都會(huì)復(fù)用疮装,因此抽取出來統(tǒng)一的進(jìn)行講解。
?個(gè)人是認(rèn)為抽取通用的內(nèi)容放在一篇文章講解完后可以針對(duì)每類Executor講解特有的功能统倒,這樣能夠有更好的理解的猛。這篇文章講解Executor的實(shí)現(xiàn)類DeleteExecutor耀盗。
類依賴圖
說明:
- 著重講解DeleteExecutor實(shí)現(xiàn)類。
DeleteExecutor方法介紹
public class DeleteExecutor<T, S extends Statement> extends AbstractDMLBaseExecutor<T, S> {
public DeleteExecutor(StatementProxy statementProxy, StatementCallback statementCallback, SQLRecognizer sqlRecognizer) {
super(statementProxy, statementCallback, sqlRecognizer);
}
@Override
protected TableRecords beforeImage() throws SQLException {
SQLDeleteRecognizer visitor = (SQLDeleteRecognizer) sqlRecognizer;
// 獲取表的所有的列
TableMeta tmeta = getTableMeta(visitor.getTableName());
List<String> columns = new ArrayList<>();
for (String column : tmeta.getAllColumns().keySet()) {
columns.add(column);
}
// 拼接SELECT的SQL語句
StringBuffer selectSQLAppender = new StringBuffer("SELECT ");
for (int i = 0; i < columns.size(); i++) {
selectSQLAppender.append(getColumnNameInSQL(columns.get(i)));
if (i < (columns.size() - 1)) {
selectSQLAppender.append(", ");
}
}
String whereCondition = null;
// 解析并獲取where條件
ArrayList<Object> paramAppender = new ArrayList<>();
if (statementProxy instanceof ParametersHolder) {
whereCondition = visitor.getWhereCondition((ParametersHolder) statementProxy, paramAppender);
} else {
whereCondition = visitor.getWhereCondition();
}
// 拼接SQL的where條件
selectSQLAppender.append(" FROM " + getFromTableInSQL() + " WHERE " + whereCondition + " FOR UPDATE");
String selectSQL = selectSQLAppender.toString();
// 根據(jù)拼接的SQL查詢數(shù)據(jù)表獲取刪除前的數(shù)據(jù)
TableRecords beforeImage = null;
PreparedStatement ps = null;
Statement st = null;
ResultSet rs = null;
try {
if (paramAppender.isEmpty()) {
st = statementProxy.getConnection().createStatement();
rs = st.executeQuery(selectSQL);
} else {
ps = statementProxy.getConnection().prepareStatement(selectSQL);
for (int i = 0; i< paramAppender.size(); i++) {
ps.setObject(i + 1, paramAppender.get(i));
}
rs = ps.executeQuery();
}
beforeImage = TableRecords.buildRecords(tmeta, rs);
} finally {
if (rs != null) {
rs.close();
}
if (st != null) {
st.close();
}
if (ps != null) {
ps.close();
}
}
return beforeImage;
}
}
說明:
- DeleteExecutor需要保存SQL執(zhí)行前的鏡像卦尊。
- 執(zhí)行前鏡像的準(zhǔn)備整體思路是按照按照刪除條件逆向拼接正向查詢SQL叛拷。
- 查詢的SQL的select的字段直接從查詢表的元數(shù)據(jù)的列值。
- 查詢的SQL的條件通過解析delete的條件生成猫牡。
- 執(zhí)行根據(jù)delete操作生成的正向select語句查詢刪除前的數(shù)據(jù)胡诗。
- 根據(jù)TableRecords.buildRecords生成執(zhí)行前鏡像邓线。
public class DeleteExecutor<T, S extends Statement> extends AbstractDMLBaseExecutor<T, S> {
public DeleteExecutor(StatementProxy statementProxy, StatementCallback statementCallback, SQLRecognizer sqlRecognizer) {
super(statementProxy, statementCallback, sqlRecognizer);
}
@Override
protected TableRecords afterImage(TableRecords beforeImage) throws SQLException {
return TableRecords.empty(getTableMeta());
}
}
說明:
- DeleteExecutor保存的執(zhí)行后的鏡像就是生產(chǎn)空白進(jìn)行而已淌友。
- TableRecords.empty()方法返回空白鏡像煌恢。
期待
?DeleteExecutor生成執(zhí)行前后鏡像的過程分析完后,會(huì)接著分析UpdateExecutor震庭。