mybatis plus3.1.0 使用多租户插件

文章目录

概要

mybatis plus3.1.0使用多租户插件和3.5有点区别,不能直接通过MybatisPlusInterceptor 进行配置。mybatis plus 3.1.0版本的AbstractSqlParserHandler 只有两个实现在这里插入图片描述在这里插入图片描述
在这里插入图片描述
所以 想要使用租户解析器 需要借助PaginationInterceptor 分页拦截器,把TenantSqlParser这个sql解析器加载到PaginationInterceptor 这个拦截器里进行处理。

详细

		<dependency>
			<groupId>com.baomidou</groupId>
			<artifactId>mybatis-plus-boot-starter</artifactId>
			<version>3.1.0</version>
		</dependency>

通过实现TenantHandler 接口 自定义租户处理器

public class MyTenantLineHandler implements TenantHandler {

    /**
     * 租户字段名
     */
    private static final String SYSTEM_TENANT_ID = "tenant_id";

    /**
     * 默认的租户ID
     */
    public static final Long DEFAULT_TENANT_ID = 1L;

    /**
     * 需要过滤的表
     */
    private static final List<String> IGNORE_TENANT_TABLES = new ArrayList<>();
    static {
        IGNORE_TENANT_TABLES.add("manage_user");
    }

    /**
     * 获取租户ID值
     */
    @Override
    public Expression getTenantId() {
        System.out.println("获取租户ID值");
        //获取登录用户的租户ID
        Long loginUserTenantId = getLoginUserTenantId();
        if (loginUserTenantId == null){
            loginUserTenantId = DEFAULT_TENANT_ID;
        }
        return new LongValue(loginUserTenantId);
    }

    /**
     * 租户字段名,默认是tenant_id,如果想改成其他字段,在这里返回即可
     */
    @Override
    public String getTenantIdColumn() {
        return SYSTEM_TENANT_ID;
    }

    /**
     * 不需要进行租户隔离的表,在这里返回true
     */
    @Override
    public boolean doTableFilter(String tableName) {
        if (IGNORE_TENANT_TABLES.contains(tableName)){
            //不需要租户隔离
            return true;
        }else {
            //需要租户隔离
            return false;
        }
    }

    public Long getLoginUserTenantId(){
        //模拟获取登录用户的租户ID,可以从登录用户缓存信息中获取
        return 2L;
    }

分页拦截器, 租户核心配置:TenantSqlParser

@Configuration
@MapperScan(basePackages = {"com.test.*.business.*.mapper"})
public class MybatisPlusConfig {
    
    //3.1.0 版本 通过分页拦截器配置
    @Bean
    public PaginationInterceptor paginationInterceptor() {
        // 租户 SQL 解析器
        TenantSqlParser tenantSqlParser = new TenantSqlParser();
        tenantSqlParser.setTenantHandler(new MyTenantLineHandler());
        
        //分页拦截器
        PaginationInterceptor paginationInterceptor = new PaginationInterceptor();
//      paginationInterceptor.setLocalPage(false);// 开启 PageHelper 的支持
        List<ISqlParser> sqlParserList = new ArrayList<>();
        // 攻击 SQL 阻断解析
        sqlParserList.add(new BlockAttackSqlParser());
        // 增加租户处理
        sqlParserList.add(tenantSqlParser);
        // 加入解析链
        paginationInterceptor.setSqlParserList(sqlParserList);
        return paginationInterceptor;

    }


//    3.5.0 版本可以这样配置
// 新多租户插件配置,一缓和二缓遵循mybatis的规则,需要设置 MybatisConfiguration#useDeprecatedExecutor = false 避免缓存万一出现问题
//    @Bean
//    public MybatisPlusInterceptor mybatisPlusInterceptor() {
//        MybatisPlusInterceptor interceptor = new MybatisPlusInterceptor();
//        // 攻击 SQL 阻断解析器、加入解析链
//        interceptor.addInnerInterceptor(new BlockAttackInnerInterceptor());
//        // 添加多租户插件
//        interceptor.addInnerInterceptor(new TenantLineInnerInterceptor(new MyTenantLineHandler()));
//        //如果配置多个插件,切记分页最后添加,如果有多数据源可以不配具体类型 否则都建议配上具体的DbType
//        //用了分页插件必须设置 MybatisConfiguration#useDeprecatedExecutor = false
//        PaginationInnerInterceptor paginationInnerInterceptor = new PaginationInnerInterceptor(DbType.POSTGRE_SQL);
//        //设置单页分页最大数量
//        paginationInnerInterceptor.setMaxLimit(500L);
//        interceptor.addInnerInterceptor(paginationInnerInterceptor);
//        return interceptor;
//    }
//    @Bean
//    public ConfigurationCustomizer configurationCustomizer() {
//        return configuration -> configuration.setUseDeprecatedExecutor(false);
//    }

}

配置结束后,就能成功使用了。

注:如果部分SQL不需要加上租户ID,除了在TenantHandler 配置过滤,还可以通过租户注解 @SqlParser(filter = true) 的形式过滤特定的sql,目前该注解只能作用于Mapper的方法上

总结

多租户识别:插件通过拦截器机制,在 SQL 语句执行之前,获取当前请求的租户 ID。
SQL 语句动态修改:通过动态拼接 SQL ,在原有 SQL 语句中加入租户 ID ,实现租户数据的隔离。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值