MybatisPlus动态表名
官网文档
https://baomidou.com/plugins/dynamic-table-name/
Java代码
配置拦截器
import com.baomidou.mybatisplus.extension.plugins.MybatisPlusInterceptor;
import com.baomidou.mybatisplus.extension.plugins.inner.DynamicTableNameInnerInterceptor;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import java.text.SimpleDateFormat;
import java.util.Date;
/**
* MyBatis Plus 配置
* 动态表名插件
*/
@Configuration
public class MyBatisPlusConfig {
public static ThreadLocal<String> tableNameHolder = new ThreadLocal<>();
@Bean
public MybatisPlusInterceptor mybatisPlusInterceptor() {
MybatisPlusInterceptor interceptor = new MybatisPlusInterceptor();
// 添加动态表名插件
DynamicTableNameInnerInterceptor dynamicTableNameInnerInterceptor = new DynamicTableNameInnerInterceptor();
dynamicTableNameInnerInterceptor.setTableNameHandler((sql, tableName) -> {
// 从 ThreadLocal 中获取动态表名
String dynamicTableName = tableNameHolder.get();
if (dynamicTableName != null) {
return dynamicTableName; // 返回动态表名
}
return tableName; // 默认表名
});
interceptor.addInnerInterceptor(dynamicTableNameInnerInterceptor);
return interceptor;
}
/**
* 生成动态表名
* @param originalTableName 原表名
* @param cityid 城市
* @return 动态表名
*/
public static String generateDynamicTableName(String originalTableName, String cityid) {
// 获取当前年份
SimpleDateFormat sdf = new SimpleDateFormat("yyyy");
String year = sdf.format(new Date());
// 生成动态表名
return originalTableName + "_" + cityid + "_" + year;
}
}
使用动态表名
import com.baoer.terminaltcpserver.config.MyBatisPlusConfig;
public class SomeService {
public void someMethod() {
// 假设原表名为 "feedbacklog"
String originalTableName = "feedbacklog";
String cityid = "1";
// 1.生成动态表名
String dynamicTableName = MyBatisPlusConfig.generateDynamicTableName(originalTableName, cityid);
// 2.设置到 ThreadLocal 中
MyBatisPlusConfig.tableNameHolder.set(dynamicTableName);
try {
// 执行数据库操作
// 例如:userMapper.selectList(null);
} finally {
// 3.清除 ThreadLocal 中的值
MyBatisPlusConfig.tableNameHolder.remove();
}
}
}
拦截器无感替换表名
pom
<dependency>
<groupId>com.baomidou</groupId>
<artifactId>mybatis-plus-boot-starter</artifactId>
<version>3.5.3</version> <!-- 或项目现有版本,兼容 JDK 8 -->
</dependency>
动态表名处理器
package com.baoer.handler;
import com.baomidou.mybatisplus.extension.plugins.handler.TableNameHandler;
import com.lw.dillon.admin.framework.security.core.LoginUser;
import com.lw.dillon.admin.framework.security.core.util.SecurityFrameworkUtils;
import org.apache.commons.lang3.StringUtils;
import java.time.LocalDate;
/**
* 流水数据动态表名处理器
* 主表: device_data
* 分表: device_data_{cityId}_{year}
*/
public class DynamicIbeDevDataTableNameHandler implements TableNameHandler {
private static final String ORIGINAL_TABLE = "device_data";
@Override
public String dynamicTableName(String sql, String tableName) {
if (!ORIGINAL_TABLE.equals(tableName)) {
return tableName; // 只处理主表
}
LoginUser loginUser = SecurityFrameworkUtils.getLoginUser();
if (loginUser == null || loginUser.getDeptId() == null) {
// 未登录或区域id,返回主表(或抛异常/默认表)
return ORIGINAL_TABLE;
}
String cityId = loginUser.getDeptId().toString();
if (StringUtils.isBlank(cityId)) {
return ORIGINAL_TABLE;
}
int year = LocalDate.now().getYear(); // 当前年份,如 2025
return ORIGINAL_TABLE + "_" + cityId + "_" + year;
}
}
MyBatis-Plus 配置类
package com.baoer.config;
import com.baoer.handler.DynamicDeviceDataTableNameHandler;
import com.baomidou.mybatisplus.annotation.DbType;
import com.baomidou.mybatisplus.extension.plugins.MybatisPlusInterceptor;
import com.baomidou.mybatisplus.extension.plugins.inner.DynamicTableNameInnerInterceptor;
import com.baomidou.mybatisplus.extension.plugins.inner.PaginationInnerInterceptor;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
@Configuration
public class MybatisPlusConfig {
@Bean
public MybatisPlusInterceptor mybatisPlusInterceptor() {
System.out.println("自定义表名替换 MybatisPlusInterceptor 已加载!");
MybatisPlusInterceptor interceptor = new MybatisPlusInterceptor();
// 动态表名拦截器(必须在分页之前添加)
DynamicTableNameInnerInterceptor dynamicTableNameInnerInterceptor = new DynamicTableNameInnerInterceptor();
dynamicTableNameInnerInterceptor.setTableNameHandler(new DynamicDeviceDataTableNameHandler());
interceptor.addInnerInterceptor(dynamicTableNameInnerInterceptor);
// 分页拦截器
interceptor.addInnerInterceptor(new PaginationInnerInterceptor(DbType.MYSQL));
return interceptor;
}
}
配置类不生效(无打印)
@SpringBootApplication
@ComponentScan(basePackages = {"cn.iocoder.yudao", "com.autumn"}) // 添加你的自定义包
public class YudaoServerApplication { ... }
Bean 冲突(BeanDefinitionOverrideException)
框架已有 mybatisPlusInterceptor bean。
在 application.yml 添加:YAML
spring:
main:
allow-bean-definition-overriding: true
如果这篇文章对你有用,可以关注本人微信公众号获取更多ヽ(^ω^)ノ ~


浙公网安备 33010602011771号