001/*
002 *  Copyright (c) 2022-2025, Mybatis-Flex (fuhai999@gmail.com).
003 *  <p>
004 *  Licensed under the Apache License, Version 2.0 (the "License");
005 *  you may not use this file except in compliance with the License.
006 *  You may obtain a copy of the License at
007 *  <p>
008 *  http://www.apache.org/licenses/LICENSE-2.0
009 *  <p>
010 *  Unless required by applicable law or agreed to in writing, software
011 *  distributed under the License is distributed on an "AS IS" BASIS,
012 *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
013 *  See the License for the specific language governing permissions and
014 *  limitations under the License.
015 */
016package com.mybatisflex.core.row;
017
018import com.mybatisflex.core.FlexGlobalConfig;
019import com.mybatisflex.core.exception.FlexExceptions;
020import com.mybatisflex.core.paginate.Page;
021import com.mybatisflex.core.query.CPI;
022import com.mybatisflex.core.query.QueryCondition;
023import com.mybatisflex.core.query.QueryTable;
024import com.mybatisflex.core.query.QueryWrapper;
025import com.mybatisflex.core.transaction.Propagation;
026import com.mybatisflex.core.transaction.TransactionalManager;
027import com.mybatisflex.core.util.CollectionUtil;
028import org.apache.ibatis.session.SqlSessionFactory;
029import com.mybatisflex.core.util.MapUtil;
030
031import java.util.Arrays;
032import java.util.Collection;
033import java.util.List;
034import java.util.Map;
035import java.util.concurrent.ConcurrentHashMap;
036import java.util.function.BiConsumer;
037import java.util.function.Supplier;
038
039/**
040 * 针对 RowMapper 的静态方法进行封装
041 */
042public class Db {
043
044    private Db() {
045    }
046
047    private static final Map<String, RowMapperInvoker> INVOKER_MAP = new ConcurrentHashMap<>();
048    static RowMapperInvoker defaultRowMapperInvoker;
049
050    public static RowMapperInvoker invoker() {
051        if (defaultRowMapperInvoker == null) {
052            FlexGlobalConfig defaultConfig = FlexGlobalConfig.getDefaultConfig();
053            SqlSessionFactory sqlSessionFactory = defaultConfig.getSqlSessionFactory();
054            defaultRowMapperInvoker = new RowMapperInvoker(sqlSessionFactory);
055        }
056        return defaultRowMapperInvoker;
057    }
058
059    public static RowMapperInvoker invoker(String environmentId) {
060        return MapUtil.computeIfAbsent(INVOKER_MAP, environmentId, key -> {
061            SqlSessionFactory sqlSessionFactory = FlexGlobalConfig.getConfig(key).getSqlSessionFactory();
062            return new RowMapperInvoker(sqlSessionFactory);
063        });
064    }
065
066
067    /**
068     * 往 schema.tableName 插入一条 row 数据
069     *
070     * @param schema    模式
071     * @param tableName 表名
072     * @param row       数据
073     */
074    public static int insert(String schema, String tableName, Row row) {
075        return invoker().insert(schema, tableName, row);
076    }
077
078    /**
079     * 往 tableName 插入一条 row 数据
080     *
081     * @param tableName 表名
082     * @param row       数据
083     */
084    public static int insert(String tableName, Row row) {
085        return invoker().insert(null, tableName, row);
086    }
087
088
089    /**
090     * 直接编写 sql 插入数据
091     *
092     * @param sql  sql 内容
093     * @param args sql 参数
094     */
095    public static int insertBySql(String sql, Object... args) {
096        return invoker().insertBySql(sql, args);
097    }
098
099
100    /**
101     * 批量插入数据
102     *
103     * @param schema    模式
104     * @param tableName 表名
105     * @param rows      数据
106     */
107    public static int[] insertBatch(String schema, String tableName, Collection<Row> rows) {
108        return insertBatch(schema, tableName, rows, rows.size());
109    }
110
111    /**
112     * 批量插入数据
113     *
114     * @param tableName 表名
115     * @param rows      数据
116     */
117    public static int[] insertBatch(String tableName, Collection<Row> rows) {
118        return insertBatch(null, tableName, rows, rows.size());
119    }
120
121    /**
122     * 批量插入数据
123     *
124     * @param schema    模式
125     * @param tableName 表名
126     * @param rows      数据
127     * @param batchSize 每次提交的数据量
128     */
129    public static int[] insertBatch(String schema, String tableName, Collection<Row> rows, int batchSize) {
130        return executeBatch(rows, batchSize, RowMapper.class, (mapper, row) -> mapper.insert(schema, tableName, row));
131    }
132
133    /**
134     * 批量插入数据
135     *
136     * @param tableName 表名
137     * @param rows      数据
138     * @param batchSize 每次提交的数据量
139     */
140    public static int[] insertBatch(String tableName, Collection<Row> rows, int batchSize) {
141        return executeBatch(rows, batchSize, RowMapper.class, (mapper, row) -> mapper.insert(null, tableName, row));
142    }
143
144    /**
145     * 批量插入数据,根据第一条内容来构建插入的字段,效率比 {@link #insertBatch(String, String, Collection, int)} 高
146     *
147     * @param schema    模式
148     * @param tableName 表名
149     * @param rows      数据
150     */
151    public static int insertBatchWithFirstRowColumns(String schema, String tableName, List<Row> rows) {
152        return invoker().insertBatchWithFirstRowColumns(schema, tableName, rows);
153    }
154
155    /**
156     * 批量插入数据,根据第一条内容来构建插入的字段,效率比 {@link #insertBatch(String, String, Collection, int)} 高
157     *
158     * @param tableName 表名
159     * @param rows      数据
160     */
161    public static int insertBatchWithFirstRowColumns(String tableName, List<Row> rows) {
162        return invoker().insertBatchWithFirstRowColumns(null, tableName, rows);
163    }
164
165    /**
166     * 编写 delete sql 来删除数据
167     *
168     * @param sql  sql 内容
169     * @param args 参数
170     */
171    public static int deleteBySql(String sql, Object... args) {
172        return invoker().deleteBySql(sql, args);
173    }
174
175    /**
176     * 根据主键来删除数据,其中 row 是通过 {@link Row#ofKey(RowKey, Object)} 来进行构建的
177     *
178     * @param schema    模式
179     * @param tableName 表名
180     * @param row       主键 和 id值
181     */
182    public static int deleteById(String schema, String tableName, Row row) {
183        return invoker().deleteById(schema, tableName, row);
184    }
185
186    /**
187     * 根据主键来删除数据,其中 row 是通过 {@link Row#ofKey(RowKey, Object)} 来进行构建的
188     *
189     * @param tableName 表名
190     * @param row       主键 和 id值
191     */
192    public static int deleteById(String tableName, Row row) {
193        return invoker().deleteById(null, tableName, row);
194    }
195
196
197    /**
198     * 根据主键来删除 1 条数据
199     *
200     * @param schema     模式
201     * @param tableName  表名
202     * @param primaryKey 主键字段名称
203     * @param id         主键值
204     */
205    public static int deleteById(String schema, String tableName, String primaryKey, Object id) {
206        return invoker().deleteById(schema, tableName, primaryKey, id);
207    }
208
209    /**
210     * 根据主键来删除 1 条数据
211     *
212     * @param tableName  表名
213     * @param primaryKey 主键字段名称
214     * @param id         主键值
215     */
216    public static int deleteById(String tableName, String primaryKey, Object id) {
217        return invoker().deleteById(null, tableName, primaryKey, id);
218    }
219
220
221    /**
222     * 根据 id 集合来批量删除数据
223     *
224     * @param schema     模式
225     * @param tableName  表名
226     * @param primaryKey 主键字段名称
227     * @param ids        id 集合
228     */
229    public static int deleteBatchByIds(String schema, String tableName, String primaryKey, Collection<?> ids) {
230        return invoker().deleteBatchByIds(schema, tableName, primaryKey, ids);
231    }
232
233    /**
234     * 根据 id 集合来批量删除数据
235     *
236     * @param tableName  表名
237     * @param primaryKey 主键字段名称
238     * @param ids        id 集合
239     */
240    public static int deleteBatchByIds(String tableName, String primaryKey, Collection<?> ids) {
241        return invoker().deleteBatchByIds(null, tableName, primaryKey, ids);
242    }
243
244    /**
245     * 根据 map 构建的 where 条件来删除数据
246     *
247     * @param schema       模式
248     * @param tableName    表名
249     * @param whereColumns where 条件
250     */
251    public static int deleteByMap(String schema, String tableName, Map<String, Object> whereColumns) {
252        return invoker().deleteByQuery(schema, tableName, new QueryWrapper().where(whereColumns));
253    }
254
255    /**
256     * 根据 map 构建的 where 条件来删除数据
257     *
258     * @param tableName    表名
259     * @param whereColumns where 条件
260     */
261    public static int deleteByMap(String tableName, Map<String, Object> whereColumns) {
262        return invoker().deleteByQuery(null, tableName, new QueryWrapper().where(whereColumns));
263    }
264
265    /**
266     * 根据 condition 条件删除数据
267     *
268     * @param schema    模式
269     * @param tableName 表名
270     * @param condition 条件内容
271     */
272    public static int deleteByCondition(String schema, String tableName, QueryCondition condition) {
273        return invoker().deleteByQuery(schema, tableName, new QueryWrapper().where(condition));
274    }
275
276    /**
277     * 根据 condition 条件删除数据
278     *
279     * @param tableName 表名
280     * @param condition 条件内容
281     */
282    public static int deleteByCondition(String tableName, QueryCondition condition) {
283        return invoker().deleteByQuery(null, tableName, new QueryWrapper().where(condition));
284    }
285
286
287    /**
288     * 根据 query 构建的条件来删除数据
289     *
290     * @param schema       模式
291     * @param tableName    表名
292     * @param queryWrapper query
293     */
294    public static int deleteByQuery(String schema, String tableName, QueryWrapper queryWrapper) {
295        return invoker().deleteByQuery(schema, tableName, queryWrapper);
296    }
297
298    /**
299     * 根据 query 构建的条件来删除数据
300     *
301     * @param tableName    表名
302     * @param queryWrapper query
303     */
304    public static int deleteByQuery(String tableName, QueryWrapper queryWrapper) {
305        return invoker().deleteByQuery(null, tableName, queryWrapper);
306    }
307
308    /**
309     * 根据原生 sql 来更新数据
310     *
311     * @param sql  sql 内容
312     * @param args sql 参数
313     */
314    public static int updateBySql(String sql, Object... args) {
315        return invoker().updateBySql(sql, args);
316    }
317
318
319    /**
320     * @param sql
321     * @param batchArgsSetter
322     * @return
323     */
324    public static int[] updateBatch(String sql, BatchArgsSetter batchArgsSetter) {
325        int batchSize = batchArgsSetter.getBatchSize();
326        return invoker().executeBatch(batchSize, batchSize, RowMapper.class
327            , (mapper, index) -> mapper.updateBySql(sql, batchArgsSetter.getSqlArgs(index)));
328
329    }
330
331
332    /**
333     * 根据 id 来更新数据
334     *
335     * @param schema    模式
336     * @param tableName 表名
337     * @param row       id 及其内容
338     */
339    public static int updateById(String schema, String tableName, Row row) {
340        return invoker().updateById(schema, tableName, row);
341    }
342
343
344    /**
345     * 根据 id 来更新数据
346     *
347     * @param tableName 表名
348     * @param row       id 及其内容
349     */
350    public static int updateById(String tableName, Row row) {
351        return invoker().updateById(null, tableName, row);
352    }
353
354    /**
355     * 根据 map 构建的条件来更新数据
356     *
357     * @param schema       模式
358     * @param tableName    表名
359     * @param data         数据内容
360     * @param whereColumns where 条件
361     */
362    public static int updateByMap(String schema, String tableName, Row data, Map<String, Object> whereColumns) {
363        return invoker().updateByQuery(schema, tableName, data, new QueryWrapper().where(whereColumns));
364    }
365
366
367    /**
368     * 根据 map 构建的条件来更新数据
369     *
370     * @param tableName    表名
371     * @param data         数据内容
372     * @param whereColumns where 条件
373     */
374    public static int updateByMap(String tableName, Row data, Map<String, Object> whereColumns) {
375        return invoker().updateByQuery(null, tableName, data, new QueryWrapper().where(whereColumns));
376    }
377
378    /**
379     * 根据 condition 来更新数据
380     *
381     * @param schema    模式
382     * @param tableName 表名
383     * @param data      数据
384     * @param condition 条件
385     */
386    public static int updateByCondition(String schema, String tableName, Row data, QueryCondition condition) {
387        return invoker().updateByQuery(schema, tableName, data, new QueryWrapper().where(condition));
388    }
389
390    /**
391     * 根据 condition 来更新数据
392     *
393     * @param tableName 表名
394     * @param data      数据
395     * @param condition 条件
396     */
397    public static int updateByCondition(String tableName, Row data, QueryCondition condition) {
398        return invoker().updateByQuery(null, tableName, data, new QueryWrapper().where(condition));
399    }
400
401
402    /**
403     * 根据 query 构建的条件来更新数据
404     *
405     * @param schema       模式
406     * @param tableName    表名
407     * @param data         数据内容
408     * @param queryWrapper queryWrapper 条件
409     */
410    public static int updateByQuery(String schema, String tableName, Row data, QueryWrapper queryWrapper) {
411        return invoker().updateByQuery(schema, tableName, data, queryWrapper);
412    }
413
414    /**
415     * 根据 query 构建的条件来更新数据
416     *
417     * @param tableName    表名
418     * @param data         数据内容
419     * @param queryWrapper queryWrapper 条件
420     */
421    public static int updateByQuery(String tableName, Row data, QueryWrapper queryWrapper) {
422        return invoker().updateByQuery(null, tableName, data, queryWrapper);
423    }
424
425
426    /**
427     * 根据主键来批量更新数据
428     *
429     * @param schema    模式
430     * @param tableName 表名
431     * @param rows      还有主键的数据
432     */
433    public static int updateBatchById(String schema, String tableName, List<Row> rows) {
434        return invoker().updateBatchById(schema, tableName, rows);
435    }
436
437    /**
438     * 根据主键来批量更新数据
439     *
440     * @param tableName 表名
441     * @param rows      还有主键的数据
442     */
443    public static int updateBatchById(String tableName, List<Row> rows) {
444        return invoker().updateBatchById(null, tableName, rows);
445    }
446
447
448    /**
449     * 根据主键来批量更新数据
450     *
451     * @param entities  实体
452     * @param batchSize 批次大小
453     * @return int
454     */
455    public static <T> int updateEntitiesBatch(Collection<T> entities, int batchSize) {
456        List<T> list = CollectionUtil.toList(entities);
457        return Arrays.stream(executeBatch(list, batchSize, RowMapper.class, RowMapper::updateEntity)).sum();
458    }
459
460
461    /**
462     * 根据主键来批量更新数据
463     *
464     * @param entities 实体
465     * @return int 影响行数
466     */
467    public static <T> int updateEntitiesBatch(Collection<T> entities) {
468        return updateEntitiesBatch(entities, RowMapper.DEFAULT_BATCH_SIZE);
469    }
470
471
472
473    /**
474     * 批量执行工具方法
475     *
476     * @param totalSize   执行总量
477     * @param batchSize   每一批次的数据量
478     * @param mapperClass 通过那个 Mapper 来执行
479     * @param consumer    执行内容
480     * @param <M>         Mapper
481     * @return 执行影响的行数
482     */
483    public static <M> int[] executeBatch(int totalSize, int batchSize, Class<M> mapperClass, BiConsumer<M, Integer> consumer) {
484        return invoker().executeBatch(totalSize, batchSize, mapperClass, consumer);
485    }
486
487
488    /**
489     * 批量执行工具方法
490     *
491     * @param datas       数据
492     * @param mapperClass mapper 类
493     * @param consumer    消费者
494     * @param <M>         mapper
495     * @param <D>         数据类型
496     * @return 返回每条执行是否成功的结果
497     */
498    public static <M, D> int[] executeBatch(Collection<D> datas, Class<M> mapperClass, BiConsumer<M, D> consumer) {
499        return executeBatch(datas, RowMapper.DEFAULT_BATCH_SIZE, mapperClass, consumer);
500    }
501
502
503    /**
504     * 批量执行工具方法
505     *
506     * @param datas       数据
507     * @param batchSize   每批次执行多少条
508     * @param mapperClass mapper 类
509     * @param consumer    消费者
510     * @param <M>         mapper
511     * @param <E>         数据类型
512     * @return 返回每条执行是否成功的结果
513     */
514    public static <M, E> int[] executeBatch(Collection<E> datas, int batchSize, Class<M> mapperClass, BiConsumer<M, E> consumer) {
515        return invoker().executeBatch(datas, batchSize, mapperClass, consumer);
516    }
517
518    /**
519     * 根据 sql 来查询 1 条数据
520     *
521     * @param sql  sql 内容
522     * @param args sql 参数
523     */
524    public static Row selectOneBySql(String sql, Object... args) {
525        return invoker().selectOneBySql(sql, args);
526    }
527
528
529    /**
530     * 根据 id 来查询 1 条数据
531     *
532     * @param schema    模式
533     * @param tableName 表名
534     * @param row       主键和 id 值
535     */
536    public static Row selectOneById(String schema, String tableName, Row row) {
537        return invoker().selectOneById(schema, tableName, row);
538    }
539
540    /**
541     * 根据 id 来查询 1 条数据
542     *
543     * @param tableName 表名
544     * @param row       主键和 id 值
545     */
546    public static Row selectOneById(String tableName, Row row) {
547        return invoker().selectOneById(null, tableName, row);
548    }
549
550
551    /**
552     * 根据主键来查询 1 条数据
553     *
554     * @param schema     模式
555     * @param tableName  表名
556     * @param primaryKey 主键字段名称
557     * @param id         主键值
558     */
559    public static Row selectOneById(String schema, String tableName, String primaryKey, Object id) {
560        return invoker().selectOneById(schema, tableName, primaryKey, id);
561    }
562
563    /**
564     * 根据主键来查询 1 条数据
565     *
566     * @param tableName  表名
567     * @param primaryKey 主键字段名称
568     * @param id         主键值
569     */
570    public static Row selectOneById(String tableName, String primaryKey, Object id) {
571        return invoker().selectOneById(null, tableName, primaryKey, id);
572    }
573
574    /**
575     * 根据 map 来查询 1 条数据
576     *
577     * @param schema       模式
578     * @param tableName    表名
579     * @param whereColumns where条件
580     */
581    public static Row selectOneByMap(String schema, String tableName, Map whereColumns) {
582        return invoker().selectOneByQuery(schema, tableName, new QueryWrapper().where(whereColumns).limit(1L));
583    }
584
585
586    /**
587     * 根据 map 来查询 1 条数据
588     *
589     * @param tableName    表名
590     * @param whereColumns where条件
591     */
592    public static Row selectOneByMap(String tableName, Map whereColumns) {
593        return invoker().selectOneByQuery(null, tableName, new QueryWrapper().where(whereColumns).limit(1L));
594    }
595
596    /**
597     * 根据 condition 来查询数据
598     *
599     * @param schema    模式
600     * @param tableName 表名
601     * @param condition 条件
602     */
603    public static Row selectOneByCondition(String schema, String tableName, QueryCondition condition) {
604        return invoker().selectOneByQuery(schema, tableName, new QueryWrapper().where(condition).limit(1L));
605    }
606
607    /**
608     * 根据 condition 来查询数据
609     *
610     * @param tableName 表名
611     * @param condition 条件
612     */
613    public static Row selectOneByCondition(String tableName, QueryCondition condition) {
614        return invoker().selectOneByQuery(null, tableName, new QueryWrapper().where(condition).limit(1L));
615    }
616
617
618    /**
619     * 根据 queryWrapper 来查询 1 条数据
620     *
621     * @param schema       模式
622     * @param tableName    表名
623     * @param queryWrapper queryWrapper
624     */
625    public static Row selectOneByQuery(String schema, String tableName, QueryWrapper queryWrapper) {
626        return invoker().selectOneByQuery(schema, tableName, queryWrapper);
627    }
628
629    /**
630     * 根据 queryWrapper 来查询 1 条数据
631     *
632     * @param tableName    表名
633     * @param queryWrapper queryWrapper
634     */
635    public static Row selectOneByQuery(String tableName, QueryWrapper queryWrapper) {
636        return invoker().selectOneByQuery(null, tableName, queryWrapper);
637    }
638
639
640    /**
641     * 直接根据 queryWrapper 查询 1 条数据
642     *
643     * @param queryWrapper 必须带有 from 的 queryWrapper
644     */
645    public static Row selectOneByQuery(QueryWrapper queryWrapper) {
646        List<QueryTable> queryTables = CPI.getQueryTables(queryWrapper);
647        if (queryTables == null || queryTables.isEmpty()) {
648            throw FlexExceptions.wrap("table must not be null or empty in Db.selectOneByQuery");
649        }
650        return invoker().selectOneByQuery(null, null, queryWrapper);
651    }
652
653
654    /**
655     * 通过 sql 来查询多条数据
656     *
657     * @param sql  sql 内容
658     * @param args sql 参数
659     */
660    public static List<Row> selectListBySql(String sql, Object... args) {
661        return invoker().selectListBySql(sql, args);
662    }
663
664
665    /**
666     * 通过 map 构建的条件来查询数据列表
667     *
668     * @param schema       模式
669     * @param tableName    表名
670     * @param whereColumns where 条件
671     */
672    public static List<Row> selectListByMap(String schema, String tableName, Map<String, Object> whereColumns) {
673        return invoker().selectListByQuery(schema, tableName, new QueryWrapper().where(whereColumns));
674    }
675
676    /**
677     * 通过 map 构建的条件来查询数据列表
678     *
679     * @param tableName    表名
680     * @param whereColumns where 条件
681     */
682    public static List<Row> selectListByMap(String tableName, Map<String, Object> whereColumns) {
683        return invoker().selectListByQuery(null, tableName, new QueryWrapper().where(whereColumns));
684    }
685
686
687    /**
688     * 根据 map 构建的条件来查询数据列表
689     *
690     * @param schema       模式
691     * @param tableName    表名
692     * @param whereColumns 条件
693     * @param count        数据量
694     */
695    public static List<Row> selectListByMap(String schema, String tableName, Map<String, Object> whereColumns, Long count) {
696        return invoker().selectListByQuery(schema, tableName, new QueryWrapper().where(whereColumns).limit(count));
697    }
698
699    /**
700     * 根据 map 构建的条件来查询数据列表
701     *
702     * @param tableName    表名
703     * @param whereColumns 条件
704     * @param count        数据量
705     */
706    public static List<Row> selectListByMap(String tableName, Map<String, Object> whereColumns, Long count) {
707        return invoker().selectListByQuery(null, tableName, new QueryWrapper().where(whereColumns).limit(count));
708    }
709
710
711    /**
712     * 通过 condition 条件来查询数据列表
713     *
714     * @param schema    模式
715     * @param tableName 表名
716     * @param condition where 条件
717     */
718    public static List<Row> selectListByCondition(String schema, String tableName, QueryCondition condition) {
719        return invoker().selectListByQuery(schema, tableName, new QueryWrapper().where(condition));
720    }
721
722
723    /**
724     * 通过 condition 条件来查询数据列表
725     *
726     * @param tableName 表名
727     * @param condition where 条件
728     */
729    public static List<Row> selectListByCondition(String tableName, QueryCondition condition) {
730        return invoker().selectListByQuery(null, tableName, new QueryWrapper().where(condition));
731    }
732
733    /**
734     * 根据 condition 条件来查询数据列表
735     *
736     * @param schema    模式
737     * @param tableName 表名
738     * @param condition 条件
739     * @param count     数据量
740     */
741    public static List<Row> selectListByCondition(String schema, String tableName, QueryCondition condition, Long count) {
742        return invoker().selectListByQuery(schema, tableName, new QueryWrapper().where(condition).limit(count));
743    }
744
745    /**
746     * 根据 condition 条件来查询数据列表
747     *
748     * @param tableName 表名
749     * @param condition 条件
750     * @param count     数据量
751     */
752    public static List<Row> selectListByCondition(String tableName, QueryCondition condition, Long count) {
753        return invoker().selectListByQuery(null, tableName, new QueryWrapper().where(condition).limit(count));
754    }
755
756
757    /**
758     * 通过 query 来查询数据列表
759     *
760     * @param schema       模式
761     * @param tableName    表名
762     * @param queryWrapper query 条件
763     */
764    public static List<Row> selectListByQuery(String schema, String tableName, QueryWrapper queryWrapper) {
765        return invoker().selectListByQuery(schema, tableName, queryWrapper);
766    }
767
768
769    /**
770     * 通过 query 来查询数据列表
771     *
772     * @param tableName    表名
773     * @param queryWrapper query 条件
774     */
775    public static List<Row> selectListByQuery(String tableName, QueryWrapper queryWrapper) {
776        return invoker().selectListByQuery(null, tableName, queryWrapper);
777    }
778
779
780    /**
781     * 通过 query 来查询数据列表
782     *
783     * @param queryWrapper 必须带有 from 的 queryWrapper
784     */
785    public static List<Row> selectListByQuery(QueryWrapper queryWrapper) {
786        List<QueryTable> queryTables = CPI.getQueryTables(queryWrapper);
787        if (queryTables == null || queryTables.isEmpty()) {
788            throw FlexExceptions.wrap("table must not be null or empty in Db.selectListByQuery");
789        }
790        return invoker().selectListByQuery(null, null, queryWrapper);
791    }
792
793    /**
794     * 查询某张表的所有数据
795     *
796     * @param schema    模式
797     * @param tableName 表名
798     */
799    public static List<Row> selectAll(String schema, String tableName) {
800        return invoker().selectAll(schema, tableName);
801    }
802
803    /**
804     * 查询某张表的所有数据
805     *
806     * @param tableName 表名
807     */
808    public static List<Row> selectAll(String tableName) {
809        return invoker().selectAll(null, tableName);
810    }
811
812    /**
813     * 查询某个内容,数据返回的应该只有 1 行 1 列
814     *
815     * @param sql  sql 内容
816     * @param args sql 参数
817     */
818    public static Object selectObject(String sql, Object... args) {
819        return invoker().selectObject(sql, args);
820    }
821
822
823    /**
824     * 根据 queryWrapper 查询内容,数据返回的应该只有 1 行 1 列
825     *
826     * @param schema       模式
827     * @param tableName    表名
828     * @param queryWrapper query 封装
829     * @return 数据内容
830     */
831    public static Object selectObject(String schema, String tableName, QueryWrapper queryWrapper) {
832        return invoker().selectObjectByQuery(schema, tableName, queryWrapper);
833    }
834
835    /**
836     * 根据 queryWrapper 查询内容,数据返回的应该只有 1 行 1 列
837     *
838     * @param tableName    表名
839     * @param queryWrapper query 封装
840     * @return 数据内容
841     */
842    public static Object selectObject(String tableName, QueryWrapper queryWrapper) {
843        return invoker().selectObjectByQuery(null, tableName, queryWrapper);
844    }
845
846
847    /**
848     * 根据 queryWrapper 查询内容,数据返回的应该只有 1 行 1 列
849     *
850     * @param queryWrapper query 封装
851     * @return 数据内容
852     */
853    public static Object selectObject(QueryWrapper queryWrapper) {
854        return invoker().selectObjectByQuery(null, null, queryWrapper);
855    }
856
857    /**
858     * 根据 queryWrapper 查询内容,数据返回为Map  第一列的值作为key 第二列的值作为value
859     *
860     * @param queryWrapper query 封装
861     * @return 数据内容
862     */
863    public static Map selectFirstAndSecondColumnsAsMap(QueryWrapper queryWrapper) {
864        return invoker().selectFirstAndSecondColumnsAsMapByQuery(null, null, queryWrapper);
865    }
866
867    /**
868     * 查询某个内容,数据返回为Map  第一列的值作为key 第二列的值作为value
869     *
870     * @param sql  sql 内容
871     * @param args sql 参数
872     */
873    public static Map selectFirstAndSecondColumnsAsMap(String sql, Object... args) {
874        return invoker().selectFirstAndSecondColumnsAsMap(sql, args);
875    }
876
877    /**
878     * 根据 queryWrapper 查询内容,数据返回为Map  第一列的值作为key 第二列的值作为value
879     *
880     * @param schema       模式
881     * @param tableName    表名
882     * @param queryWrapper query 封装
883     * @return 数据内容
884     */
885    public static Map selectFirstAndSecondColumnsAsMap(String schema, String tableName, QueryWrapper queryWrapper) {
886        return invoker().selectFirstAndSecondColumnsAsMapByQuery(schema, tableName, queryWrapper);
887    }
888
889    /**
890     * 根据 queryWrapper 查询内容,数据返回为Map  第一列的值作为key 第二列的值作为value
891     *
892     * @param tableName    表名
893     * @param queryWrapper query 封装
894     * @return 数据内容
895     */
896    public static Map selectFirstAndSecondColumnsAsMap(String tableName, QueryWrapper queryWrapper) {
897        return invoker().selectFirstAndSecondColumnsAsMapByQuery(null, tableName, queryWrapper);
898    }
899
900    /**
901     * 查询某列内容,数据返回应该有 多行 1 列
902     *
903     * @param sql  sql 内容
904     * @param args sql 参数
905     */
906    public static List<Object> selectObjectList(String sql, Object... args) {
907        return invoker().selectObjectList(sql, args);
908    }
909
910
911    /**
912     * 根据 queryWrapper 查询内容,数据返回的应该只有 1 行 1 列
913     *
914     * @param schema       模式
915     * @param tableName    表名
916     * @param queryWrapper query 封装
917     * @return 数据内容
918     */
919    public static List<Object> selectObjectList(String schema, String tableName, QueryWrapper queryWrapper) {
920        return invoker().selectObjectListByQuery(schema, tableName, queryWrapper);
921    }
922
923    /**
924     * 根据 queryWrapper 查询内容,数据返回的应该只有 1 行 1 列
925     *
926     * @param tableName    表名
927     * @param queryWrapper query 封装
928     * @return 数据内容
929     */
930    public static List<Object> selectObjectList(String tableName, QueryWrapper queryWrapper) {
931        return invoker().selectObjectListByQuery(null, tableName, queryWrapper);
932    }
933
934
935    /**
936     * 根据 queryWrapper 查询内容,数据返回的应该只有 1 行 1 列
937     *
938     * @param queryWrapper query 封装
939     * @return 数据内容
940     */
941    public static List<Object> selectObjectList(QueryWrapper queryWrapper) {
942        return invoker().selectObjectListByQuery(null, null, queryWrapper);
943    }
944
945
946    /**
947     * 查收 count 数据,一般用于 select count(*)...
948     * 或者返回的内容是一行1列,且是数值类型的也可以用此方法
949     *
950     * @param sql  sql 内容
951     * @param args sql 参数
952     */
953    public static long selectCount(String sql, Object... args) {
954        return invoker().selectCount(sql, args);
955    }
956
957
958    /**
959     * 根据 condition 条件来查询数量
960     *
961     * @param schema    模式
962     * @param tableName 表名
963     * @param condition 条件
964     */
965    public static long selectCountByCondition(String schema, String tableName, QueryCondition condition) {
966        return invoker().selectCountByQuery(schema, tableName, new QueryWrapper().where(condition));
967    }
968
969    /**
970     * 根据 condition 条件来查询数量
971     *
972     * @param tableName 表名
973     * @param condition 条件
974     */
975    public static long selectCountByCondition(String tableName, QueryCondition condition) {
976        return invoker().selectCountByQuery(null, tableName, new QueryWrapper().where(condition));
977    }
978
979
980    /**
981     * 根据 query 构建的条件来查询数据量
982     *
983     * @param schema       模式
984     * @param tableName    表名
985     * @param queryWrapper query 条件
986     */
987    public static long selectCountByQuery(String schema, String tableName, QueryWrapper queryWrapper) {
988        return invoker().selectCountByQuery(schema, tableName, queryWrapper);
989    }
990
991    /**
992     * 根据 query 构建的条件来查询数据量
993     *
994     * @param tableName    表名
995     * @param queryWrapper query 条件
996     */
997    public static long selectCountByQuery(String tableName, QueryWrapper queryWrapper) {
998        return invoker().selectCountByQuery(null, tableName, queryWrapper);
999    }
1000
1001
1002    /**
1003     * 直接根据 query 来查询数据量
1004     *
1005     * @param queryWrapper 必须带有表名的 queryWrapper
1006     * @return 数据量
1007     */
1008    public static long selectCountByQuery(QueryWrapper queryWrapper) {
1009        List<QueryTable> queryTables = CPI.getQueryTables(queryWrapper);
1010        if (queryTables == null || queryTables.isEmpty()) {
1011            throw FlexExceptions.wrap("Query tables must not be null or empty in Db.selectCountByQuery");
1012        }
1013        return invoker().selectCountByQuery(null, null, queryWrapper);
1014    }
1015
1016
1017    /**
1018     * 分页查询
1019     *
1020     * @param schema     模式
1021     * @param tableName  表名
1022     * @param pageNumber 当前的页码
1023     * @param pageSize   每页的数据量
1024     * @param condition  条件
1025     */
1026    public static Page<Row> paginate(String schema, String tableName, Number pageNumber, Number pageSize, QueryCondition condition) {
1027        return invoker().paginate(schema, tableName, new Page<>(pageNumber, pageSize), QueryWrapper.create().where(condition));
1028    }
1029
1030
1031    /**
1032     * 分页查询
1033     *
1034     * @param tableName  表名
1035     * @param pageNumber 当前的页码
1036     * @param pageSize   每页的数据量
1037     * @param condition  条件
1038     */
1039    public static Page<Row> paginate(String tableName, Number pageNumber, Number pageSize, QueryCondition condition) {
1040        return invoker().paginate(null, tableName, new Page<>(pageNumber, pageSize), QueryWrapper.create().where(condition));
1041    }
1042
1043
1044    /**
1045     * 分页查询
1046     *
1047     * @param schema     模式
1048     * @param tableName  表名
1049     * @param pageNumber 当前的页码
1050     * @param pageSize   每页的数据量
1051     * @param totalRow   数据总量
1052     * @param condition  条件
1053     */
1054    public static Page<Row> paginate(String schema, String tableName, Number pageNumber, Number pageSize, Number totalRow, QueryCondition condition) {
1055        return invoker().paginate(schema, tableName, new Page<>(pageNumber, pageSize, totalRow), QueryWrapper.create().where(condition));
1056    }
1057
1058    /**
1059     * 分页查询
1060     *
1061     * @param tableName  表名
1062     * @param pageNumber 当前的页码
1063     * @param pageSize   每页的数据量
1064     * @param totalRow   数据总量
1065     * @param condition  条件
1066     */
1067    public static Page<Row> paginate(String tableName, Number pageNumber, Number pageSize, Number totalRow, QueryCondition condition) {
1068        return invoker().paginate(null, tableName, new Page<>(pageNumber, pageSize, totalRow), QueryWrapper.create().where(condition));
1069    }
1070
1071
1072    /**
1073     * 分页查询
1074     *
1075     * @param schema       模式
1076     * @param tableName    表名
1077     * @param pageNumber   当前的页码
1078     * @param pageSize     每页的数据量
1079     * @param queryWrapper 条件
1080     */
1081    public static Page<Row> paginate(String schema, String tableName, Number pageNumber, Number pageSize, QueryWrapper queryWrapper) {
1082        return invoker().paginate(schema, tableName, new Page<>(pageNumber, pageSize), queryWrapper);
1083    }
1084
1085    /**
1086     * 分页查询
1087     *
1088     * @param tableName    表名
1089     * @param pageNumber   当前的页码
1090     * @param pageSize     每页的数据量
1091     * @param queryWrapper 条件
1092     */
1093    public static Page<Row> paginate(String tableName, Number pageNumber, Number pageSize, QueryWrapper queryWrapper) {
1094        return invoker().paginate(null, tableName, new Page<>(pageNumber, pageSize), queryWrapper);
1095    }
1096
1097
1098    /**
1099     * 分页查询
1100     *
1101     * @param schema       模式
1102     * @param tableName    表名
1103     * @param pageNumber   当前的页码
1104     * @param pageSize     每页的数据量
1105     * @param totalRow     数据总量
1106     * @param queryWrapper 条件
1107     */
1108    public static Page<Row> paginate(String schema, String tableName, Number pageNumber, Number pageSize, Number totalRow, QueryWrapper queryWrapper) {
1109        return invoker().paginate(schema, tableName, new Page<>(pageNumber, pageSize, totalRow), queryWrapper);
1110    }
1111
1112    /**
1113     * 分页查询
1114     *
1115     * @param tableName    表名
1116     * @param pageNumber   当前的页码
1117     * @param pageSize     每页的数据量
1118     * @param totalRow     数据总量
1119     * @param queryWrapper 条件
1120     */
1121    public static Page<Row> paginate(String tableName, Number pageNumber, Number pageSize, Number totalRow, QueryWrapper queryWrapper) {
1122        return invoker().paginate(null, tableName, new Page<>(pageNumber, pageSize, totalRow), queryWrapper);
1123    }
1124
1125
1126    /**
1127     * 分页查询
1128     *
1129     * @param schema       模式
1130     * @param tableName    表名
1131     * @param page         page 对象,若 page 有 totalCount 值,则不会再去查询分类的数据总量
1132     * @param queryWrapper 条件
1133     */
1134    public static Page<Row> paginate(String schema, String tableName, Page<Row> page, QueryWrapper queryWrapper) {
1135        return invoker().paginate(schema, tableName, page, queryWrapper);
1136    }
1137
1138    /**
1139     * 分页查询
1140     *
1141     * @param tableName    表名
1142     * @param page         page 对象,若 page 有 totalCount 值,则不会再去查询分类的数据总量
1143     * @param queryWrapper 条件
1144     */
1145    public static Page<Row> paginate(String tableName, Page<Row> page, QueryWrapper queryWrapper) {
1146        return invoker().paginate(null, tableName, page, queryWrapper);
1147    }
1148
1149
1150    /**
1151     * 进行事务操作,返回 null 或者 false 或者 抛出异常,事务回滚
1152     */
1153    public static boolean tx(Supplier<Boolean> supplier) {
1154        return tx(supplier, Propagation.REQUIRED);
1155    }
1156
1157    /**
1158     * 进行事务操作,返回 null 或者 false 或者 抛出异常, 事务回滚
1159     */
1160    public static boolean tx(Supplier<Boolean> supplier, Propagation propagation) {
1161        Boolean result = TransactionalManager.exec(supplier, propagation, false);
1162        return result != null && result;
1163    }
1164
1165    /**
1166     * 进行事务操作,和返回结果无关,只有抛出异常时,事务回滚
1167     */
1168    public static <T> T txWithResult(Supplier<T> supplier) {
1169        return txWithResult(supplier, Propagation.REQUIRED);
1170    }
1171
1172    /**
1173     * 进行事务操作,和返回结果无关,只有抛出异常时,事务回滚
1174     */
1175    public static <T> T txWithResult(Supplier<T> supplier, Propagation propagation) {
1176        return TransactionalManager.exec(supplier, propagation, true);
1177    }
1178
1179}