add 简单迁移租户模块,修改相关功能
parent
66d25f3a3b
commit
5e4e7ba73a
@ -0,0 +1,39 @@
|
|||||||
|
package com.ruoyi.common.core.constant;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 全局的key常量 (业务无关的key)
|
||||||
|
*
|
||||||
|
* @author Lion Li
|
||||||
|
*/
|
||||||
|
public interface GlobalConstants {
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 全局 redis key (业务无关的key)
|
||||||
|
*/
|
||||||
|
String GLOBAL_REDIS_KEY = "global:";
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 登录用户 redis key
|
||||||
|
*/
|
||||||
|
String LOGIN_TOKEN_KEY = GLOBAL_REDIS_KEY + "Authorization:login:token:";
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 验证码 redis key
|
||||||
|
*/
|
||||||
|
String CAPTCHA_CODE_KEY = GLOBAL_REDIS_KEY + "captcha_codes:";
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 防重提交 redis key
|
||||||
|
*/
|
||||||
|
String REPEAT_SUBMIT_KEY = GLOBAL_REDIS_KEY + "repeat_submit:";
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 限流 redis key
|
||||||
|
*/
|
||||||
|
String RATE_LIMIT_KEY = GLOBAL_REDIS_KEY + "rate_limit:";
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 登录账户密码错误次数 redis key
|
||||||
|
*/
|
||||||
|
String PWD_ERR_CNT_KEY = GLOBAL_REDIS_KEY + "pwd_err_cnt:";
|
||||||
|
}
|
@ -0,0 +1,45 @@
|
|||||||
|
package com.ruoyi.common.core.constant;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 租户常量信息
|
||||||
|
*
|
||||||
|
* @author Lion Li
|
||||||
|
*/
|
||||||
|
public interface TenantConstants {
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 租户正常状态
|
||||||
|
*/
|
||||||
|
String NORMAL = "0";
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 租户封禁状态
|
||||||
|
*/
|
||||||
|
String DISABLE = "1";
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 超级管理员ID
|
||||||
|
*/
|
||||||
|
Long SUPER_ADMIN_ID = 1L;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 超级管理员角色 roleKey
|
||||||
|
*/
|
||||||
|
String SUPER_ADMIN_ROLE_KEY = "superadmin";
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 租户管理员角色 roleKey
|
||||||
|
*/
|
||||||
|
String TENANT_ADMIN_ROLE_KEY = "admin";
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 租户管理员角色名称
|
||||||
|
*/
|
||||||
|
String TENANT_ADMIN_ROLE_NAME = "管理员";
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 默认租户ID
|
||||||
|
*/
|
||||||
|
String DEFAULT_TENANT_ID = "000000";
|
||||||
|
|
||||||
|
}
|
@ -0,0 +1,36 @@
|
|||||||
|
<?xml version="1.0" encoding="UTF-8"?>
|
||||||
|
<project xmlns="http://maven.apache.org/POM/4.0.0"
|
||||||
|
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
|
||||||
|
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
|
||||||
|
<parent>
|
||||||
|
<groupId>com.ruoyi</groupId>
|
||||||
|
<artifactId>ruoyi-common</artifactId>
|
||||||
|
<version>1.6.0</version>
|
||||||
|
</parent>
|
||||||
|
<modelVersion>4.0.0</modelVersion>
|
||||||
|
|
||||||
|
<artifactId>ruoyi-common-tenant</artifactId>
|
||||||
|
|
||||||
|
<description>
|
||||||
|
ruoyi-common-tenant 租户模块
|
||||||
|
</description>
|
||||||
|
|
||||||
|
<dependencies>
|
||||||
|
<dependency>
|
||||||
|
<groupId>com.ruoyi</groupId>
|
||||||
|
<artifactId>ruoyi-common-mybatis</artifactId>
|
||||||
|
</dependency>
|
||||||
|
|
||||||
|
<dependency>
|
||||||
|
<groupId>com.ruoyi</groupId>
|
||||||
|
<artifactId>ruoyi-common-redis</artifactId>
|
||||||
|
</dependency>
|
||||||
|
|
||||||
|
<dependency>
|
||||||
|
<groupId>com.alibaba</groupId>
|
||||||
|
<artifactId>transmittable-thread-local</artifactId>
|
||||||
|
</dependency>
|
||||||
|
|
||||||
|
</dependencies>
|
||||||
|
|
||||||
|
</project>
|
@ -0,0 +1,100 @@
|
|||||||
|
package com.ruoyi.common.tenant.config;
|
||||||
|
|
||||||
|
import cn.dev33.satoken.dao.SaTokenDao;
|
||||||
|
import cn.hutool.core.util.ObjectUtil;
|
||||||
|
import com.baomidou.mybatisplus.extension.plugins.MybatisPlusInterceptor;
|
||||||
|
import com.baomidou.mybatisplus.extension.plugins.inner.InnerInterceptor;
|
||||||
|
import com.baomidou.mybatisplus.extension.plugins.inner.TenantLineInnerInterceptor;
|
||||||
|
import com.ruoyi.common.core.utils.reflect.ReflectUtils;
|
||||||
|
import com.ruoyi.common.mybatis.config.MybatisPlusConfiguration;
|
||||||
|
import com.ruoyi.common.redis.config.RedisConfiguration;
|
||||||
|
import com.ruoyi.common.redis.config.properties.RedissonProperties;
|
||||||
|
import com.ruoyi.common.tenant.core.TenantSaTokenDao;
|
||||||
|
import com.ruoyi.common.tenant.handle.PlusTenantLineHandler;
|
||||||
|
import com.ruoyi.common.tenant.handle.TenantKeyPrefixHandler;
|
||||||
|
import com.ruoyi.common.tenant.manager.TenantSpringCacheManager;
|
||||||
|
import com.ruoyi.common.tenant.properties.TenantProperties;
|
||||||
|
import org.redisson.config.ClusterServersConfig;
|
||||||
|
import org.redisson.config.SingleServerConfig;
|
||||||
|
import org.redisson.spring.starter.RedissonAutoConfigurationCustomizer;
|
||||||
|
import org.springframework.boot.autoconfigure.AutoConfiguration;
|
||||||
|
import org.springframework.boot.autoconfigure.condition.ConditionalOnProperty;
|
||||||
|
import org.springframework.boot.context.properties.EnableConfigurationProperties;
|
||||||
|
import org.springframework.cache.CacheManager;
|
||||||
|
import org.springframework.context.annotation.Bean;
|
||||||
|
import org.springframework.context.annotation.Primary;
|
||||||
|
|
||||||
|
import java.util.ArrayList;
|
||||||
|
import java.util.List;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 租户配置类
|
||||||
|
*
|
||||||
|
* @author Lion Li
|
||||||
|
*/
|
||||||
|
@EnableConfigurationProperties(TenantProperties.class)
|
||||||
|
@AutoConfiguration(after = {RedisConfiguration.class, MybatisPlusConfiguration.class})
|
||||||
|
@ConditionalOnProperty(value = "tenant.enable", havingValue = "true")
|
||||||
|
public class TenantConfig {
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 初始化租户配置
|
||||||
|
*/
|
||||||
|
@Bean
|
||||||
|
public boolean tenantInit(MybatisPlusInterceptor mybatisPlusInterceptor,
|
||||||
|
TenantProperties tenantProperties) {
|
||||||
|
List<InnerInterceptor> interceptors = new ArrayList<>();
|
||||||
|
// 多租户插件 必须放到第一位
|
||||||
|
interceptors.add(tenantLineInnerInterceptor(tenantProperties));
|
||||||
|
interceptors.addAll(mybatisPlusInterceptor.getInterceptors());
|
||||||
|
mybatisPlusInterceptor.setInterceptors(interceptors);
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 多租户插件
|
||||||
|
*/
|
||||||
|
public TenantLineInnerInterceptor tenantLineInnerInterceptor(TenantProperties tenantProperties) {
|
||||||
|
return new TenantLineInnerInterceptor(new PlusTenantLineHandler(tenantProperties));
|
||||||
|
}
|
||||||
|
|
||||||
|
@Bean
|
||||||
|
public RedissonAutoConfigurationCustomizer tenantRedissonCustomizer(RedissonProperties redissonProperties) {
|
||||||
|
return config -> {
|
||||||
|
TenantKeyPrefixHandler nameMapper = new TenantKeyPrefixHandler(redissonProperties.getKeyPrefix());
|
||||||
|
SingleServerConfig singleServerConfig = ReflectUtils.invokeGetter(config, "singleServerConfig");
|
||||||
|
if (ObjectUtil.isNotNull(singleServerConfig)) {
|
||||||
|
// 使用单机模式
|
||||||
|
// 设置多租户 redis key前缀
|
||||||
|
singleServerConfig.setNameMapper(nameMapper);
|
||||||
|
ReflectUtils.invokeSetter(config, "singleServerConfig", singleServerConfig);
|
||||||
|
}
|
||||||
|
ClusterServersConfig clusterServersConfig = ReflectUtils.invokeGetter(config, "clusterServersConfig");
|
||||||
|
// 集群配置方式 参考下方注释
|
||||||
|
if (ObjectUtil.isNotNull(clusterServersConfig)) {
|
||||||
|
// 设置多租户 redis key前缀
|
||||||
|
clusterServersConfig.setNameMapper(nameMapper);
|
||||||
|
ReflectUtils.invokeSetter(config, "clusterServersConfig", clusterServersConfig);
|
||||||
|
}
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 多租户缓存管理器
|
||||||
|
*/
|
||||||
|
@Primary
|
||||||
|
@Bean
|
||||||
|
public CacheManager tenantCacheManager() {
|
||||||
|
return new TenantSpringCacheManager();
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 多租户鉴权dao实现
|
||||||
|
*/
|
||||||
|
@Primary
|
||||||
|
@Bean
|
||||||
|
public SaTokenDao tenantSaTokenDao() {
|
||||||
|
return new TenantSaTokenDao();
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
@ -0,0 +1,21 @@
|
|||||||
|
package com.ruoyi.common.tenant.core;
|
||||||
|
|
||||||
|
import com.ruoyi.common.core.web.domain.BaseEntity;
|
||||||
|
import lombok.Data;
|
||||||
|
import lombok.EqualsAndHashCode;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 租户基类
|
||||||
|
*
|
||||||
|
* @author Michelle.Chung
|
||||||
|
*/
|
||||||
|
@Data
|
||||||
|
@EqualsAndHashCode(callSuper = true)
|
||||||
|
public class TenantEntity extends BaseEntity {
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 租户编号
|
||||||
|
*/
|
||||||
|
private String tenantId;
|
||||||
|
|
||||||
|
}
|
@ -0,0 +1,18 @@
|
|||||||
|
package com.ruoyi.common.tenant.exception;
|
||||||
|
|
||||||
|
|
||||||
|
import com.ruoyi.common.core.exception.base.BaseException;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 租户异常类
|
||||||
|
*
|
||||||
|
* @author Lion Li
|
||||||
|
*/
|
||||||
|
public class TenantException extends BaseException {
|
||||||
|
|
||||||
|
private static final long serialVersionUID = 1L;
|
||||||
|
|
||||||
|
public TenantException(String code, Object... args) {
|
||||||
|
super("tenant", code, args, null);
|
||||||
|
}
|
||||||
|
}
|
@ -0,0 +1,58 @@
|
|||||||
|
package com.ruoyi.common.tenant.handle;
|
||||||
|
|
||||||
|
import com.baomidou.mybatisplus.extension.plugins.handler.TenantLineHandler;
|
||||||
|
import com.ruoyi.common.core.utils.StringUtils;
|
||||||
|
import com.ruoyi.common.tenant.helper.TenantHelper;
|
||||||
|
import com.ruoyi.common.tenant.properties.TenantProperties;
|
||||||
|
import lombok.AllArgsConstructor;
|
||||||
|
import net.sf.jsqlparser.expression.Expression;
|
||||||
|
import net.sf.jsqlparser.expression.NullValue;
|
||||||
|
import net.sf.jsqlparser.expression.StringValue;
|
||||||
|
import com.ruoyi.common.satoken.utils.LoginHelper;
|
||||||
|
|
||||||
|
import java.util.Arrays;
|
||||||
|
import java.util.List;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 自定义租户处理器
|
||||||
|
*
|
||||||
|
* @author Lion Li
|
||||||
|
*/
|
||||||
|
@AllArgsConstructor
|
||||||
|
public class PlusTenantLineHandler implements TenantLineHandler {
|
||||||
|
|
||||||
|
private final TenantProperties tenantProperties;
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public Expression getTenantId() {
|
||||||
|
String tenantId = LoginHelper.getTenantId();
|
||||||
|
if (StringUtils.isBlank(tenantId)) {
|
||||||
|
return new NullValue();
|
||||||
|
}
|
||||||
|
String dynamicTenantId = TenantHelper.getDynamic();
|
||||||
|
if (StringUtils.isNotBlank(dynamicTenantId)) {
|
||||||
|
// 返回动态租户
|
||||||
|
return new StringValue(dynamicTenantId);
|
||||||
|
}
|
||||||
|
// 返回固定租户
|
||||||
|
return new StringValue(tenantId);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public boolean ignoreTable(String tableName) {
|
||||||
|
String tenantId = LoginHelper.getTenantId();
|
||||||
|
// 判断是否有租户
|
||||||
|
if (StringUtils.isNotBlank(tenantId)) {
|
||||||
|
// 不需要过滤租户的表
|
||||||
|
List<String> excludes = tenantProperties.getExcludes();
|
||||||
|
// 非业务表
|
||||||
|
excludes.addAll(Arrays.asList(
|
||||||
|
"gen_table",
|
||||||
|
"gen_table_column"
|
||||||
|
));
|
||||||
|
return excludes.contains(tableName);
|
||||||
|
}
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
@ -0,0 +1,59 @@
|
|||||||
|
package com.ruoyi.common.tenant.handle;
|
||||||
|
|
||||||
|
|
||||||
|
import com.ruoyi.common.core.constant.GlobalConstants;
|
||||||
|
import com.ruoyi.common.core.utils.StringUtils;
|
||||||
|
import com.ruoyi.common.redis.handler.KeyPrefixHandler;
|
||||||
|
import com.ruoyi.common.tenant.helper.TenantHelper;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 多租户redis缓存key前缀处理
|
||||||
|
*
|
||||||
|
* @author Lion Li
|
||||||
|
*/
|
||||||
|
public class TenantKeyPrefixHandler extends KeyPrefixHandler {
|
||||||
|
|
||||||
|
public TenantKeyPrefixHandler(String keyPrefix) {
|
||||||
|
super(keyPrefix);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 增加前缀
|
||||||
|
*/
|
||||||
|
@Override
|
||||||
|
public String map(String name) {
|
||||||
|
if (StringUtils.isBlank(name)) {
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
if (StringUtils.contains(name, GlobalConstants.GLOBAL_REDIS_KEY)) {
|
||||||
|
return super.map(name);
|
||||||
|
}
|
||||||
|
String tenantId = TenantHelper.getTenantId();
|
||||||
|
if (StringUtils.startsWith(name, tenantId)) {
|
||||||
|
// 如果存在则直接返回
|
||||||
|
return super.map(name);
|
||||||
|
}
|
||||||
|
return super.map(tenantId + ":" + name);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 去除前缀
|
||||||
|
*/
|
||||||
|
@Override
|
||||||
|
public String unmap(String name) {
|
||||||
|
String unmap = super.unmap(name);
|
||||||
|
if (StringUtils.isBlank(unmap)) {
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
if (StringUtils.contains(name, GlobalConstants.GLOBAL_REDIS_KEY)) {
|
||||||
|
return super.unmap(name);
|
||||||
|
}
|
||||||
|
String tenantId = TenantHelper.getTenantId();
|
||||||
|
if (StringUtils.startsWith(unmap, tenantId)) {
|
||||||
|
// 如果存在则删除
|
||||||
|
return unmap.substring((tenantId + ":").length());
|
||||||
|
}
|
||||||
|
return unmap;
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
@ -0,0 +1,110 @@
|
|||||||
|
package com.ruoyi.common.tenant.helper;
|
||||||
|
|
||||||
|
import cn.dev33.satoken.context.SaHolder;
|
||||||
|
import cn.dev33.satoken.spring.SpringMVCUtil;
|
||||||
|
import cn.hutool.core.convert.Convert;
|
||||||
|
import com.alibaba.ttl.TransmittableThreadLocal;
|
||||||
|
import com.baomidou.mybatisplus.core.plugins.IgnoreStrategy;
|
||||||
|
import com.baomidou.mybatisplus.core.plugins.InterceptorIgnoreHelper;
|
||||||
|
import com.ruoyi.common.core.constant.GlobalConstants;
|
||||||
|
import com.ruoyi.common.core.utils.SpringUtils;
|
||||||
|
import com.ruoyi.common.core.utils.StringUtils;
|
||||||
|
import com.ruoyi.common.redis.utils.RedisUtils;
|
||||||
|
import com.ruoyi.common.satoken.utils.LoginHelper;
|
||||||
|
import lombok.AccessLevel;
|
||||||
|
import lombok.NoArgsConstructor;
|
||||||
|
import lombok.extern.slf4j.Slf4j;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 租户助手
|
||||||
|
*
|
||||||
|
* @author Lion Li
|
||||||
|
*/
|
||||||
|
@Slf4j
|
||||||
|
@NoArgsConstructor(access = AccessLevel.PRIVATE)
|
||||||
|
public class TenantHelper {
|
||||||
|
|
||||||
|
private static final String DYNAMIC_TENANT_KEY = GlobalConstants.GLOBAL_REDIS_KEY + "dynamicTenant";
|
||||||
|
|
||||||
|
private static final ThreadLocal<String> TEMP_DYNAMIC_TENANT = new TransmittableThreadLocal<>();
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 租户功能是否启用
|
||||||
|
*/
|
||||||
|
public static boolean isEnable() {
|
||||||
|
return Convert.toBool(SpringUtils.getProperty("tenant.enable"), false);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 开启忽略租户(开启后需手动调用 {@link #disableIgnore()} 关闭)
|
||||||
|
*/
|
||||||
|
public static void enableIgnore() {
|
||||||
|
InterceptorIgnoreHelper.handle(IgnoreStrategy.builder().tenantLine(true).build());
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 关闭忽略租户
|
||||||
|
*/
|
||||||
|
public static void disableIgnore() {
|
||||||
|
InterceptorIgnoreHelper.clearIgnoreStrategy();
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 设置动态租户(一直有效 需要手动清理)
|
||||||
|
* <p>
|
||||||
|
* 如果为非web环境 那么只在当前线程内生效
|
||||||
|
*/
|
||||||
|
public static void setDynamic(String tenantId) {
|
||||||
|
if (!SpringMVCUtil.isWeb()) {
|
||||||
|
TEMP_DYNAMIC_TENANT.set(tenantId);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
String cacheKey = DYNAMIC_TENANT_KEY + ":" + LoginHelper.getUserId();
|
||||||
|
RedisUtils.setCacheObject(cacheKey, tenantId);
|
||||||
|
SaHolder.getStorage().set(cacheKey, tenantId);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 获取动态租户(一直有效 需要手动清理)
|
||||||
|
* <p>
|
||||||
|
* 如果为非web环境 那么只在当前线程内生效
|
||||||
|
*/
|
||||||
|
public static String getDynamic() {
|
||||||
|
if (!SpringMVCUtil.isWeb()) {
|
||||||
|
return TEMP_DYNAMIC_TENANT.get();
|
||||||
|
}
|
||||||
|
String cacheKey = DYNAMIC_TENANT_KEY + ":" + LoginHelper.getUserId();
|
||||||
|
String tenantId = (String) SaHolder.getStorage().get(cacheKey);
|
||||||
|
if (StringUtils.isNotBlank(tenantId)) {
|
||||||
|
return tenantId;
|
||||||
|
}
|
||||||
|
tenantId = RedisUtils.getCacheObject(cacheKey);
|
||||||
|
SaHolder.getStorage().set(cacheKey, tenantId);
|
||||||
|
return tenantId;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 清除动态租户
|
||||||
|
*/
|
||||||
|
public static void clearDynamic() {
|
||||||
|
if (!SpringMVCUtil.isWeb()) {
|
||||||
|
TEMP_DYNAMIC_TENANT.remove();
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
String cacheKey = DYNAMIC_TENANT_KEY + ":" + LoginHelper.getUserId();
|
||||||
|
RedisUtils.deleteObject(cacheKey);
|
||||||
|
SaHolder.getStorage().delete(cacheKey);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 获取当前租户id(动态租户优先)
|
||||||
|
*/
|
||||||
|
public static String getTenantId() {
|
||||||
|
String tenantId = TenantHelper.getDynamic();
|
||||||
|
if (StringUtils.isBlank(tenantId)) {
|
||||||
|
tenantId = LoginHelper.getTenantId();
|
||||||
|
}
|
||||||
|
return tenantId;
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
@ -0,0 +1,33 @@
|
|||||||
|
package com.ruoyi.common.tenant.manager;
|
||||||
|
|
||||||
|
|
||||||
|
import com.ruoyi.common.core.constant.GlobalConstants;
|
||||||
|
import com.ruoyi.common.core.utils.StringUtils;
|
||||||
|
import com.ruoyi.common.redis.manager.PlusSpringCacheManager;
|
||||||
|
import com.ruoyi.common.tenant.helper.TenantHelper;
|
||||||
|
import org.springframework.cache.Cache;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 重写 cacheName 处理方法 支持多租户
|
||||||
|
*
|
||||||
|
* @author Lion Li
|
||||||
|
*/
|
||||||
|
public class TenantSpringCacheManager extends PlusSpringCacheManager {
|
||||||
|
|
||||||
|
public TenantSpringCacheManager() {
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public Cache getCache(String name) {
|
||||||
|
if (StringUtils.contains(name, GlobalConstants.GLOBAL_REDIS_KEY)) {
|
||||||
|
return super.getCache(name);
|
||||||
|
}
|
||||||
|
String tenantId = TenantHelper.getTenantId();
|
||||||
|
if (StringUtils.startsWith(name, tenantId)) {
|
||||||
|
// 如果存在则直接返回
|
||||||
|
return super.getCache(name);
|
||||||
|
}
|
||||||
|
return super.getCache(tenantId + ":" + name);
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
@ -0,0 +1,27 @@
|
|||||||
|
package com.ruoyi.common.tenant.properties;
|
||||||
|
|
||||||
|
import lombok.Data;
|
||||||
|
import org.springframework.boot.context.properties.ConfigurationProperties;
|
||||||
|
|
||||||
|
import java.util.List;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 租户 配置属性
|
||||||
|
*
|
||||||
|
* @author Lion Li
|
||||||
|
*/
|
||||||
|
@Data
|
||||||
|
@ConfigurationProperties(prefix = "tenant")
|
||||||
|
public class TenantProperties {
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 是否启用
|
||||||
|
*/
|
||||||
|
private Boolean enable;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 排除表
|
||||||
|
*/
|
||||||
|
private List<String> excludes;
|
||||||
|
|
||||||
|
}
|
@ -0,0 +1 @@
|
|||||||
|
com.ruoyi.common.tenant.config.TenantConfig
|
Loading…
Reference in New Issue