SQLインジェクター
MyBatis-Plus は、sqlInjector
グローバル設定を通じてカスタムSQLメソッドを注入する柔軟なメカニズムを提供しています。ISqlInjector
インターフェースを実装するか、AbstractSqlInjector
抽象クラスを継承することで、カスタムの汎用メソッドを MyBatis コンテナに注入できます。
SQLインジェクターは、開発者が特定のビジネスロジックとクエリ要件に合わせてSQLステートメントの生成を拡張およびカスタマイズすることを可能にします。以下はSQLインジェクターの使用例と実現できる機能です:
使用例
-
カスタムクエリメソッド:標準のCRUD操作が複雑なクエリ要件を満たせない場合、SQLインジェクターを使用してカスタムクエリメソッドを追加できます。
-
複雑なデータ処理:複数テーブルの結合、サブクエリ、集計関数などの複雑なデータ処理が必要な場合、SQLインジェクターは対応するSQLステートメントの生成を支援します。
-
パフォーマンス最適化:カスタムSQLステートメントを使用して、特定のクエリシナリオのパフォーマンスを最適化できます。
-
データ権限制御:ユーザー権限に基づいてSQLステートメントを動的に生成する必要がある場合、SQLインジェクターを使用してデータ権限の制御を実装できます。
-
レガシーシステムの移行:レガシーシステムを MyBatis-Plus に移行する際、既存のSQLステートメント構造を維持する必要がある場合、SQLインジェクターはこの移行を支援します。
機能
-
カスタムSQLメソッドの注入:
ISqlInjector
インターフェースを実装することで、カスタムSQLメソッドを MyBatis コンテナに注入できます。いかなる複雑な SQL クエリであっても構いません。 -
BaseMapperの拡張:
BaseMapper
を継承した上で、SQLインジェクターを使用して追加のクエリメソッドを追加できます。これらのメソッドは自動的に MyBatis-Plus によって認識され使用されます。 -
柔軟なSQL生成:SQLインジェクターは柔軟なSQL生成メカニズムを提供し、ビジネス要件に基づいて SELECT、INSERT、UPDATE、DELETE などの様々なSQLステートメントを生成できます。
-
サードパーティデータベース機能の統合:データベースの特定の機能(ストアドプロシージャ、トリガーなど)を使用する必要がある場合、SQLインジェクターはこれらの機能を呼び出すSQLステートメントの生成を支援します。
-
動的SQLのサポート:一部のシナリオでは、SQLステートメントを実行時の条件に基づいて動的に生成する必要があります。SQLインジェクターはこのような動的SQLの生成をサポートします。
SQLインジェクターを通じて、MyBatis-Plus は強力な拡張ポイントを提供し、開発者がプロジェクトの具体的な要件に基づいてSQLステートメントを柔軟にカスタマイズおよび最適化し、アプリケーションのパフォーマンスと適応性を向上させることができます。
インジェクターの設定
MyBatis-Plus では、sqlInjector
設定はグローバル設定項目で、ISqlInjector
インターフェースを実装したクラスを指定するために使用されます。このクラスは、カスタムSQLメソッドを MyBatis の Mapper インターフェースに注入する責務を負います。
public interface ISqlInjector {
/** * SQLが既に注入されているかどうかをチェックします(既に注入されている場合は再注入しません) * * @param builderAssistant mapper 構築アシスタント * @param mapperClass mapper インターフェースの class オブジェクト */ void inspectInject(MapperBuilderAssistant builderAssistant, Class<?> mapperClass);}
デフォルトのインジェクター実装は DefaultSqlInjector です。これを参考にして独自のインジェクターを作成できます。
以下は sqlInjector
を設定する方法の例です。
提供された参考情報に基づいて、MyBatis-Plus でカスタムのグローバルメソッドを実装する方法を確認できます。これには、論理削除、自動入力、カスタムの insert
および insertBatch
メソッドが含まれます。以下は、より詳細な手順とサンプルコードです:
カスタムグローバルメソッドの設定方法
ステップ 1: SQLの定義
まず、カスタムメソッドのSQLステートメントを定義する必要があります。これは通常、AbstractMethod
を継承したクラスで行われます。例えば、MysqlInsertAllBatch
などです。
public class MysqlInsertAllBatch extends AbstractMethod {
/** * @since 3.5.0 */ public MysqlInsertAllBatch() { super("mysqlInsertAllBatch"); }
@Override public MappedStatement injectMappedStatement(Class<?> mapperClass, Class<?> modelClass, TableInfo tableInfo) { // SQLステートメントを定義 (主キー+通常のフィールド) insert into table(....) values(....),(....) String sql = "INSERT INTO " + tableInfo.getTableName() + "(" + tableInfo.getKeyColumn() + "," + tableInfo.getFieldList().stream().map(TableFieldInfo::getColumn).collect(Collectors.joining(",")) + ") VALUES "; String value = "(" + "#{" + ENTITY + DOT + tableInfo.getKeyProperty() + "}" + "," + tableInfo.getFieldList().stream().map(tableFieldInfo -> "#{" + ENTITY + DOT + tableFieldInfo.getProperty() + "}") .collect(Collectors.joining(",")) + ")"; String valuesScript = SqlScriptUtils.convertForeach(value, "list", null, ENTITY, COMMA); SqlSource sqlSource = super.createSqlSource(configuration, "<script>" + sql + valuesScript + "</script>", modelClass); KeyGenerator keyGenerator = tableInfo.getIdType() == IdType.AUTO ? Jdbc3KeyGenerator.INSTANCE : NoKeyGenerator.INSTANCE; // 3番目のパラメータは baseMapper のカスタムメソッド名と一致する必要があります return this.addInsertMappedStatement(mapperClass, modelClass, this.methodName, sqlSource, keyGenerator,tableInfo.getKeyProperty(), tableInfo.getKeyColumn()); }}
ステップ 2: カスタムメソッドの登録
次に、DefaultSqlInjector
を継承したクラスを作成し、getMethodList
メソッドをオーバーライドしてカスタムメソッドを登録します。
public class MyLogicSqlInjector extends DefaultSqlInjector {
@Override public List<AbstractMethod> getMethodList(Class<?> mapperClass) { List<AbstractMethod> methodList = super.getMethodList(mapperClass); methodList.add(new DeleteAll()); methodList.add(new MyInsertAll()); methodList.add(new MysqlInsertAllBatch()); return methodList; }}
ステップ 3: BaseMapper の定義
次に、BaseMapper インターフェースでカスタムメソッドを定義する必要があります。
public interface MyBaseMapper<T> extends BaseMapper<T> {
Integer deleteAll();
int myInsertAll(T entity);
int mysqlInsertAllBatch(@Param("list") List<T> batchList);}
ステップ 4: SqlInjectorの設定
最後に、設定ファイルでカスタムSQLインジェクターを指定する必要があります。
application.yml
での設定
mybatis-plus: global-config: sql-injector: com.example.MyLogicSqlInjector
application.properties
での設定
mybatis-plus.global-config.sql-injector=com.example.MyLogicSqlInjector
注意事項
- カスタムメソッドを定義する際は、メソッド名が注入するSQLステートメントのIDと一致することを確認してください。
- カスタムのバッチ挿入と自動入力機能を使用する際は、Mapperメソッドのパラメータに
@Param
アノテーションを使用し、名前が MyBatis-Plus のデフォルトサポート(list
、collection
、array
)に準拠していることを確認してください。 - カスタムSQLステートメントは、ビジネス要件に基づいて記述し、実行したい操作を正しく実行できることを確認してください。
上記の手順により、MyBatis-Plus でカスタムのグローバルメソッドを正常に実装できます。実際の使用では、ビジネス要件に基づいてSQLステートメントとメソッドの実装を調整することを忘れないでください。
その他の例
カスタム BaseMapper の例 を参照すると、カスタムSQLインジェクターを作成する方法や、プロジェクトでそれらを使用する方法といった、詳細な手順を見つけることができます。
この方法により、MyBatis-Plus は特定のビジネス要件を満たすために機能を拡張すると同時に、コードの読みやすさと保守性を維持することを可能にします。