四. MyBatis Plus X 单表查询,连表查询,动态表名展示
随着业务量的增长,部分表的数据量过于庞大,可以设置保留少量数据的查询表,或者是根据时间段进行分表,由于表的结构是一致的,所以只需要更改表名即可。
例如 t_sys_log 系统日志表,随着访问量的增大,日志表的数据很快可以达到千万级,那么可以对表进行切分,一年一张表,且设置一张 t_sys_log_ro(ro == read-only,非固定)表,里面设置三个月的数据,便于快速查询。
表明动态设置只针对wrapper入参查询
1.单表替换表名
使用方式
推荐使用改方法:fw.setTableName("t_test_a_ro");
或者也可以使用这种方式:fw.addTableName("t_test_a", "t_test_a_ro");
@Log
@ApiOperation(value = "分页查询")
@GetMapping("page")
// @RequiresPermissions("test:a:page")
public Object page(String query) {
FindWrapper<TestAVo> fw = getWrapper(query, TestAVo.class);
fw.setTableName("t_test_a_ro");
IPage<TestADto> page = testAMgr.page(fw);
return buildPage(page, LIST);
}
技术原理
/**
* <p>
* 根据 entity 条件,查询全部记录
* </p>
*
* @param wrapper 实体对象封装操作类(可以为 null)
*/
List<D> list(@Param(Constants.WRAPPER) Wrapper<V> wrapper);
上面这段会生成如下查询sql
<script>
SELECT <choose>
<when test="ew != null and ew.sqlSelect != null">
${ew.sqlSelect}
</when>
<otherwise>
t_test_a.`id` t_test_a__id, t_test_a.`c_id` t_test_a__c_id,
t_test_a.`b_id` t_test_a__b_id, t_test_a.`a_id` t_test_a__a_id,
t_test_a.`crt_tm` t_test_a__crt_tm, t_test_a.`crt_by` t_test_a__crt_by,
t_test_a.`upd_tm` t_test_a__upd_tm, t_test_a.`upd_by` t_test_a__upd_by,
t_test_a.`edit_flag` t_test_a__edit_flag
</otherwise>
</choose> FROM <choose>
<when test="ew != null and ew.tableName != null">
${ew.tableName} t_test_a
</when>
<otherwise>t_test_a</otherwise>
</choose>
<trim prefix="WHERE" prefixOverrides="AND|OR">
<choose>
<when test="ew != null">
<if test="ew.entity != null">
<if test="ew.entity.id != null">id=#{ew.entity.id}</if>
<if test="ew.entity.cId != null"> AND c_id=#{ew.entity.cId}</if>
<if test="ew.entity.bId != null"> AND b_id=#{ew.entity.bId}</if>
<if test="ew.entity.aId != null"> AND a_id=#{ew.entity.aId}</if>
<if test="ew.entity.crtTm != null"> AND crt_tm=#{ew.entity.crtTm}</if>
<if test="ew.entity.crtBy != null"> AND crt_by=#{ew.entity.crtBy}</if>
<if test="ew.entity.updTm != null"> AND upd_tm=#{ew.entity.updTm}</if>
<if test="ew.entity.updBy != null"> AND upd_by=#{ew.entity.updBy}</if>
</if>
AND edit_flag=0
<if test="ew.sqlSegment != null and ew.sqlSegment != '' and ew.nonEmptyOfWhere">
AND ${ew.sqlSegment}
</if>
<if test="ew.sqlSegment != null and ew.sqlSegment != '' and ew.emptyOfWhere">
${ew.sqlSegment}
</if>
</when>
<otherwise> AND edit_flag=0</otherwise>
</choose>
</trim>
</script>
2.多表连查替换表名
使用方式
fw.addTableName("t_test_a", "t_test_a_ro");
@Log
@ApiOperation(value = "listTestAATestB")
@GetMapping("listTestAATestB")
public Object listTestAATestB(String query) {
FindWrapper<TestAVo> fw = getWrapper(query, TestAVo.class);
fw.addTableName("t_test_a", "t_test_a_ro");
fw.addTableName("t_test_b", "t_test_b_ro");
List<TestADto> list = testAMgr.listTestAATestB(fw);
return buildList(list);
}
技术原理
/**
* t_test_a 与 t_test_b 一对一连表查询
*/
@Link( print = true, printRm = false,
ones = { @OneToOne(rightClass = TestBVo.class, rightColumn = "a_id") })
List<TestADto> listTestAATestB(@Param(Constants.WRAPPER) Wrapper<TestAVo> wrapper);
如果设置了别名,fw.addTableName("t_test_a", "t_test_a_ro"); 就要改为 fw.addTableName(别名, "t_test_a_ro");
上面这段会生成如下查询sql
<script>
SELECT <choose>
<when test="ew != null and ew.sqlSelect != null">
${ew.sqlSelect}
</when>
<otherwise> t_test_a.`id` t_test_a__id , t_test_a.`c_id` t_test_a__c_id ,
t_test_a.`b_id` t_test_a__b_id , t_test_a.`a_id` t_test_a__a_id ,
t_test_a.`crt_tm` t_test_a__crt_tm , t_test_a.`crt_by` t_test_a__crt_by ,
t_test_a.`upd_tm` t_test_a__upd_tm , t_test_a.`upd_by` t_test_a__upd_by ,
t_test_a.`edit_flag` t_test_a__edit_flag , t_test_b.`id` t_test_b__id ,
t_test_b.`a_id` t_test_b__a_id , t_test_b.`c_id` t_test_b__c_id ,
t_test_b.`crt_tm` t_test_b__crt_tm , t_test_b.`crt_by` t_test_b__crt_by ,
t_test_b.`upd_tm` t_test_b__upd_tm , t_test_b.`upd_by` t_test_b__upd_by ,
t_test_b.`edit_flag` t_test_b__edit_flag
</otherwise>
</choose> FROM <choose>
<when test="ew != null and ew.tableNameMap != null and ew.tableNameMap.t_test_a != null">
${ew.tableNameMap.t_test_a} t_test_a
</when>
<otherwise>t_test_a t_test_a</otherwise>
</choose> INNER JOIN <choose>
<when test="ew != null and ew.tableNameMap != null and ew.tableNameMap.t_test_b != null">
${ew.tableNameMap.t_test_b} t_test_b
</when>
<otherwise>t_test_b t_test_b</otherwise>
</choose> <trim prefix="WHERE" prefixOverrides="AND|OR">
AND t_test_a.edit_flag=0 AND t_test_b.edit_flag=0 and t_test_a.b_id=t_test_b.id
<if test="ew != null">
<if test="ew.id != null">
AND t_test_a.id = ${ew.id}
</if>
<if test="ew.sqlSegment != null and ew.sqlSegment != '' and ew.nonEmptyOfWhere">
AND ${ew.sqlSegment}
</if>
<if test="ew.sqlSegment != null and ew.sqlSegment != '' and ew.emptyOfWhere">
${ew.sqlSegment}
</if>
</if>
</trim>
</script>