1
mirror of https://github.com/CarmJos/EasySQL.git synced 2026-06-04 15:28:20 +08:00

chore(sql): 提供当前事务实现思路

This commit is contained in:
2022-12-21 21:21:01 +08:00
parent 934f9d841e
commit b6871b1000
19 changed files with 183 additions and 123 deletions
@@ -1,26 +1,52 @@
package cc.carm.lib.easysql.api;
import cc.carm.lib.easysql.api.action.PreparedSQLUpdateAction;
import cc.carm.lib.easysql.api.action.PreparedSQLUpdateBatchAction;
import cc.carm.lib.easysql.api.transaction.SQLTransaction;
import cc.carm.lib.easysql.api.builder.*;
import cc.carm.lib.easysql.api.builder.TableAlterBuilder;
import cc.carm.lib.easysql.api.builder.TableCreateBuilder;
import cc.carm.lib.easysql.api.builder.TableMetadataBuilder;
import cc.carm.lib.easysql.api.enums.IsolationLevel;
import cc.carm.lib.easysql.api.function.SQLBiFunction;
import cc.carm.lib.easysql.api.function.SQLFunction;
import cc.carm.lib.easysql.api.transaction.SQLTransaction;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;
import java.sql.Connection;
import java.sql.DatabaseMetaData;
import java.sql.ResultSet;
import java.util.concurrent.CompletableFuture;
public interface NewSQLManager {
public interface NewSQLManager extends SQLSource, SQLOperator {
default @NotNull SQLTransaction createTransaction() {
return createTransaction(null);
}
@NotNull SQLTransaction createTransaction(@Nullable IsolationLevel level);
/**
* 得到用于该管理器的 {@link SQLSource}
* 在库中创建一个表。
*
* @return {@link SQLSource}
* @param tableName 表名
* @return {@link TableCreateBuilder}
*/
@NotNull SQLSource getSource();
@NotNull TableCreateBuilder createTable(@NotNull String tableName);
/**
* 对库中的某个表执行更改。
*
* @param tableName 表名
* @return {@link TableAlterBuilder}
*/
@NotNull TableAlterBuilder alterTable(@NotNull String tableName);
/**
* 快速获取表的部分元数据。
* <br> 当需要获取其他元数据时,请使用 {@link #fetchMetadata(SQLFunction, SQLFunction)} 方法。
*
* @param tablePattern 表名通配符
* @return {@link TableMetadataBuilder}
*/
@NotNull TableMetadataBuilder fetchTableMetadata(@NotNull String tablePattern);
/**
* 获取并操作 {@link DatabaseMetaData} 以得到需要的数据库消息。
@@ -70,86 +96,4 @@ public interface NewSQLManager {
<R> CompletableFuture<R> fetchMetadata(@NotNull SQLBiFunction<DatabaseMetaData, Connection, ResultSet> supplier,
@NotNull SQLFunction<@NotNull ResultSet, R> reader);
/**
* 在库中创建一个表。
*
* @param tableName 表名
* @return {@link TableCreateBuilder}
*/
@NotNull TableCreateBuilder createTable(@NotNull String tableName);
/**
* 对库中的某个表执行更改。
*
* @param tableName 表名
* @return {@link TableAlterBuilder}
*/
@NotNull TableAlterBuilder alterTable(@NotNull String tableName);
/**
* 快速获取表的部分元数据。
* <br> 当需要获取其他元数据时,请使用 {@link #fetchMetadata(SQLFunction, SQLFunction)} 方法。
*
* @param tablePattern 表名通配符
* @return {@link TableMetadataBuilder}
*/
@NotNull TableMetadataBuilder fetchTableMetadata(@NotNull String tablePattern);
/**
* 新建一个查询。
*
* @return {@link QueryBuilder}
*/
@NotNull QueryBuilder createQuery();
@NotNull SQLTransaction createTransaction();
/**
* 创建一条插入操作。
*
* @param tableName 目标表名
* @return {@link InsertBuilder}
*/
@NotNull InsertBuilder<PreparedSQLUpdateAction<Integer>> insertInto(@NotNull String tableName);
/**
* 创建支持多组数据的插入操作。
*
* @param tableName 目标表名
* @return {@link InsertBuilder}
*/
@NotNull InsertBuilder<PreparedSQLUpdateBatchAction<Integer>> insertBatchInto(@NotNull String tableName);
/**
* 创建一条替换操作。
*
* @param tableName 目标表名
* @return {@link ReplaceBuilder}
*/
@NotNull ReplaceBuilder<PreparedSQLUpdateAction<Integer>> replaceInto(@NotNull String tableName);
/**
* 创建支持多组数据的替换操作。
*
* @param tableName 目标表名
* @return {@link ReplaceBuilder}
*/
@NotNull ReplaceBuilder<PreparedSQLUpdateBatchAction<Integer>> replaceBatchInto(@NotNull String tableName);
/**
* 创建更新操作。
*
* @param tableName 目标表名
* @return {@link UpdateBuilder}
*/
@NotNull UpdateBuilder updateInto(@NotNull String tableName);
/**
* 创建删除操作。
*
* @param tableName 目标表名
* @return {@link DeleteBuilder}
*/
@NotNull DeleteBuilder deleteFrom(@NotNull String tableName);
}
@@ -269,7 +269,7 @@ public interface SQLManager {
* @param tableName 目标表名
* @return {@link InsertBuilder}
*/
InsertBuilder<PreparedSQLUpdateAction<Integer>> createInsert(@NotNull String tableName);
InsertBuilder<PreparedSQLUpdateAction<Integer>> insertInto(@NotNull String tableName);
/**
* 创建支持多组数据的插入操作。
@@ -0,0 +1,65 @@
package cc.carm.lib.easysql.api;
import cc.carm.lib.easysql.api.action.PreparedSQLUpdateAction;
import cc.carm.lib.easysql.api.action.PreparedSQLUpdateBatchAction;
import cc.carm.lib.easysql.api.builder.*;
import org.jetbrains.annotations.NotNull;
public interface SQLOperator {
/**
* 新建一个查询。
*
* @return {@link QueryBuilder}
*/
@NotNull QueryBuilder createQuery();
/**
* 创建一条插入操作。
*
* @param tableName 目标表名
* @return {@link InsertBuilder}
*/
@NotNull InsertBuilder<PreparedSQLUpdateAction<Integer>> insertInto(@NotNull String tableName);
/**
* 创建支持多组数据的插入操作。
*
* @param tableName 目标表名
* @return {@link InsertBuilder}
*/
@NotNull InsertBuilder<PreparedSQLUpdateBatchAction<Integer>> insertBatchInto(@NotNull String tableName);
/**
* 创建一条替换操作。
*
* @param tableName 目标表名
* @return {@link ReplaceBuilder}
*/
@NotNull ReplaceBuilder<PreparedSQLUpdateAction<Integer>> replaceInto(@NotNull String tableName);
/**
* 创建支持多组数据的替换操作。
*
* @param tableName 目标表名
* @return {@link ReplaceBuilder}
*/
@NotNull ReplaceBuilder<PreparedSQLUpdateBatchAction<Integer>> replaceBatchInto(@NotNull String tableName);
/**
* 创建更新操作。
*
* @param tableName 目标表名
* @return {@link UpdateBuilder}
*/
@NotNull UpdateBuilder updateInto(@NotNull String tableName);
/**
* 创建删除操作。
*
* @param tableName 目标表名
* @return {@link DeleteBuilder}
*/
@NotNull DeleteBuilder deleteFrom(@NotNull String tableName);
}
@@ -9,18 +9,18 @@ public interface PreparedSQLUpdateBatchAction<T extends Number> extends SQLActio
/**
* 设定多组SQL语句中所有 ? 对应的参数
*
* @param allParams 所有参数内容
* @param allValues 所有参数内容
* @return {@link PreparedSQLUpdateBatchAction}
*/
PreparedSQLUpdateBatchAction<T> setAllParams(Iterable<Object[]> allParams);
PreparedSQLUpdateBatchAction<T> allValues(Iterable<Object[]> allValues);
/**
* 添加一组SQL语句中所有 ? 对应的参数
*
* @param params 参数内容
* @param values 参数内容
* @return {@link PreparedSQLUpdateBatchAction}
*/
PreparedSQLUpdateBatchAction<T> addParamsBatch(Object... params);
PreparedSQLUpdateBatchAction<T> values(Object... values);
/**
* 设定该操作返回自增键序列。
@@ -49,7 +49,7 @@ public interface TableCreateBuilder extends SQLBuilder {
* @param columns 列的相关信息 (包括列设定)
* @return {@link TableCreateBuilder}
*/
TableCreateBuilder columns(@NotNull String... columns);
TableCreateBuilder setColumns(@NotNull String... columns);
/**
* 为该表添加一个列
@@ -0,0 +1,27 @@
package cc.carm.lib.easysql.api.enums;
/**
* 事务隔离级别。
* 部分Javadoc来自文章 <a href="https://cloud.tencent.com/developer/article/1865041">《理解事务的4种隔离级别》</a> 。
*/
public enum IsolationLevel {
/**
* 读未提交。即一个事务可以读取另一个未提交事务的数据。
*/
READ_UNCOMMITTED,
/**
* 读提交。即一个事务要等另一个事务提交后才能读取数据。
*/
READ_COMMITTED,
/**
* 重复读。即在开始读取数据(事务开启)时,不再允许修改操作。
*/
REPEATED_READ,
/**
* 序列化读取。此为最高隔离等级。在该级别下,事务串行化顺序执行,可以避免脏读、不可重复读与幻读。
* <br>注意: 这种事务隔离级别效率低下,比较耗数据库性能,一般不使用。
*/
SERIALIZABLE;
}
@@ -1,7 +1,6 @@
package cc.carm.lib.easysql.api.table;
import cc.carm.lib.easysql.api.SQLManager;
import cc.carm.lib.easysql.api.SQLTable;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;
@@ -16,7 +15,7 @@ public abstract class NamedSQLTable implements SQLTable {
protected @Nullable SQLManager manager;
/**
* 请调用 {@link NamedSQLTable} 下的静态方法进行对象的初始化。
* 请调用 {@link SQLTable} 下的静态方法进行对象的初始化。
*
* @param tableName 该表的名称
*/
@@ -1,5 +1,6 @@
package cc.carm.lib.easysql.api;
package cc.carm.lib.easysql.api.table;
import cc.carm.lib.easysql.api.SQLManager;
import cc.carm.lib.easysql.api.action.PreparedSQLUpdateAction;
import cc.carm.lib.easysql.api.action.PreparedSQLUpdateBatchAction;
import cc.carm.lib.easysql.api.builder.*;
@@ -45,7 +46,7 @@ public interface SQLTable {
static @NotNull NamedSQLTable of(@NotNull String tableName,
@NotNull String[] columns, @Nullable String tableSettings) {
return of(tableName, builder -> {
builder.columns(columns);
builder.setColumns(columns);
if (tableSettings != null) builder.setTableSettings(tableSettings);
});
}
@@ -106,7 +107,7 @@ public interface SQLTable {
}
default @NotNull InsertBuilder<PreparedSQLUpdateAction<Integer>> createInsert(@NotNull SQLManager sqlManager) {
return sqlManager.createInsert(getTableName());
return sqlManager.insertInto(getTableName());
}
default @NotNull InsertBuilder<PreparedSQLUpdateBatchAction<Integer>> createInsertBatch() {
@@ -12,5 +12,4 @@ public interface SQLSavepoint {
boolean isReleased();
}
@@ -1,18 +1,44 @@
package cc.carm.lib.easysql.api.transaction;
import cc.carm.lib.easysql.api.NewSQLManager;
import cc.carm.lib.easysql.api.SQLOperator;
import cc.carm.lib.easysql.api.enums.IsolationLevel;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;
public interface SQLTransaction extends NewSQLManager, AutoCloseable {
public interface SQLTransaction extends SQLOperator, AutoCloseable {
/**
* 得到本次事务的隔离级别
*
* @return {@link IsolationLevel} 隔离级别
*/
@NotNull IsolationLevel getIsolationLevel();
/**
* 提交已有操作
*/
void commit();
SQLSavepoint savepoint(String name);
/**
* 设定一个记录点
*
* @param name 记录点名称
* @return {@link SQLSavepoint} 事务记录点
*/
@NotNull SQLSavepoint savepoint(@NotNull String name);
/**
* 回退全部操作
*/
default void rollback() {
rollback(null);
}
/**
* 回退操作到某个记录点或回退整个事务操作。
*
* @param savepoint 记录点,若记录点为NULL则回退整个事务的操作。
*/
void rollback(@Nullable SQLSavepoint savepoint);
}
+1 -1
View File
@@ -1,5 +1,5 @@
import cc.carm.lib.easysql.api.SQLManager;
import cc.carm.lib.easysql.api.SQLTable;
import cc.carm.lib.easysql.api.table.SQLTable;
import cc.carm.lib.easysql.api.enums.IndexType;
import cc.carm.lib.easysql.api.enums.NumberType;
import cc.carm.lib.easysql.api.table.NamedSQLTable;
+1 -1
View File
@@ -1,5 +1,5 @@
import cc.carm.lib.easysql.api.SQLManager;
import cc.carm.lib.easysql.api.SQLTable;
import cc.carm.lib.easysql.api.table.SQLTable;
import cc.carm.lib.easysql.api.builder.TableCreateBuilder;
import cc.carm.lib.easysql.api.enums.IndexType;
import cc.carm.lib.easysql.api.enums.NumberType;
+4 -4
View File
@@ -1,6 +1,6 @@
import cc.carm.lib.easysql.api.SQLManager;
import cc.carm.lib.easysql.api.SQLQuery;
import cc.carm.lib.easysql.api.SQLTable;
import cc.carm.lib.easysql.api.table.SQLTable;
import cc.carm.lib.easysql.api.enums.ForeignKeyRule;
import cc.carm.lib.easysql.api.enums.IndexType;
import cc.carm.lib.easysql.api.enums.NumberType;
@@ -136,7 +136,7 @@ public class EasySQLDemo {
public void sqlInsert(SQLManager sqlManager) {
// 同步SQL插入 (不使用try-catch的情况下,返回的数值可能为空。)
int id = sqlManager.createInsert("users")
int id = sqlManager.insertInto("users")
.columns("username", "phone", "email", "registerTime")
.values("CarmJos", "18888888888", "carm@carm.cc", TimeDateUtils.getCurrentTime())
.returnGeneratedKey() // 设定在后续返回自增主键
@@ -147,10 +147,10 @@ public class EasySQLDemo {
});
try {
int userID = sqlManager.createInsert("users")
long userID = sqlManager.insertInto("users")
.columns("username", "phone", "email", "registerTime")
.values("CarmJos", "18888888888", "carm@carm.cc", TimeDateUtils.getCurrentTime())
.returnGeneratedKey().execute();
.returnGeneratedKey(Long.class).execute();
System.out.println("新用户的ID为 " + userID);
@@ -27,10 +27,9 @@ public class TransactionTest {
transaction.commit(); // 提交
} catch (Exception ex) {
transaction.rollback(pointA); // 出错回滚到pointA
transaction.commit(); // 提交出错前的内容
transaction.commit(); // 提交快照前的代码
}
pointA.release(); // release savepoint (结束后也会被自动释放)
} catch (Exception ex) {
@@ -27,7 +27,7 @@ public class SQLUpdateBatchTests extends TestHandler {
List<Long> updates = sqlManager.createInsertBatch("test_user_table")
.columns("uuid", "username", "age")
.setAllParams(generateParams())
.allValues(generateParams())
.returnGeneratedKeys(Long.class)
.execute();
@@ -13,7 +13,7 @@ public class SQLUpdateReturnKeysTest extends SQLUpdateBatchTests {
public void onTest(SQLManager sqlManager) throws SQLException {
List<Integer> generatedKeys = sqlManager.createInsertBatch("test_user_table")
.columns("uuid", "username", "age")
.setAllParams(generateParams())
.allValues(generateParams())
.returnGeneratedKeys(Integer.class)
.execute();
@@ -38,16 +38,16 @@ public class PreparedSQLBatchUpdateActionImpl<T extends Number>
}
@Override
public PreparedSQLBatchUpdateActionImpl<T> setAllParams(Iterable<Object[]> allParams) {
public PreparedSQLBatchUpdateActionImpl<T> allValues(Iterable<Object[]> allValues) {
List<Object[]> paramsList = new ArrayList<>();
allParams.forEach(paramsList::add);
allValues.forEach(paramsList::add);
this.allParams = paramsList;
return this;
}
@Override
public PreparedSQLBatchUpdateActionImpl<T> addParamsBatch(Object... params) {
this.allParams.add(params);
public PreparedSQLBatchUpdateActionImpl<T> values(Object... values) {
this.allParams.add(values);
return this;
}
@@ -60,7 +60,7 @@ public class PreparedSQLBatchUpdateActionImpl<T extends Number>
@Override
public <N extends Number> PreparedSQLBatchUpdateActionImpl<N> returnGeneratedKeys(Class<N> keyTypeClass) {
return new PreparedSQLBatchUpdateActionImpl<>(getManager(), keyTypeClass, getActionUUID(), getSQLContent())
.setAllParams(allParams).returnGeneratedKeys();
.allValues(allParams).returnGeneratedKeys();
}
@Override
@@ -150,7 +150,7 @@ public class TableCreateBuilderImpl extends AbstractSQLBuilder implements TableC
}
@Override
public TableCreateBuilder columns(@NotNull String... columns) {
public TableCreateBuilder setColumns(@NotNull String... columns) {
Objects.requireNonNull(columns, "columns could not be null");
this.columns = Arrays.asList(columns);
return this;
@@ -130,7 +130,7 @@ public class SQLManagerImpl implements SQLManager {
@Override
public List<Integer> executeSQLBatch(String sql, Iterable<Object[]> paramsBatch) {
return new PreparedSQLBatchUpdateActionImpl<>(this, Integer.class, sql).setAllParams(paramsBatch).execute(null);
return new PreparedSQLBatchUpdateActionImpl<>(this, Integer.class, sql).allValues(paramsBatch).execute(null);
}
@Override
@@ -210,7 +210,7 @@ public class SQLManagerImpl implements SQLManager {
}
@Override
public InsertBuilder<PreparedSQLUpdateAction<Integer>> createInsert(@NotNull String tableName) {
public InsertBuilder<PreparedSQLUpdateAction<Integer>> insertInto(@NotNull String tableName) {
return new InsertBuilderImpl<PreparedSQLUpdateAction<Integer>>(this, tableName) {
@Override
public PreparedSQLUpdateAction<Integer> columns(List<String> columnNames) {