动态数据源无需重启刷新
This commit is contained in:
parent
257db6a837
commit
e9f729ebc8
|
|
@ -0,0 +1,24 @@
|
|||
package com.nu.modules.common;
|
||||
|
||||
import org.jeecg.modules.data.loader.DataSourceLoader;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.web.bind.annotation.PostMapping;
|
||||
import org.springframework.web.bind.annotation.RequestMapping;
|
||||
import org.springframework.web.bind.annotation.RestController;
|
||||
|
||||
/**
|
||||
* 系统工具
|
||||
*/
|
||||
@RestController
|
||||
@RequestMapping("/api/sysUtils")
|
||||
public class SysUtilsApi {
|
||||
|
||||
@Autowired
|
||||
private DataSourceLoader dataSourceLoader;
|
||||
|
||||
@PostMapping("/refreshDS")
|
||||
public String refresh() {
|
||||
dataSourceLoader.refreshDataSources();
|
||||
return "数据源已刷新";
|
||||
}
|
||||
}
|
||||
|
|
@ -119,6 +119,7 @@ public class ShiroConfig {
|
|||
filterChainDefinitionMap.put("/weixin/**", "anon"); //授权接口排除
|
||||
filterChainDefinitionMap.put("/api/pad/loginApi/**", "anon"); //pad登录-信息获取接口
|
||||
filterChainDefinitionMap.put("/sys/common/open/static/**", "anon");//获取本地文件资源
|
||||
filterChainDefinitionMap.put("/api/sysUtils/refreshDS", "anon");//刷新数据源
|
||||
|
||||
filterChainDefinitionMap.put("/sys/getLoginQrcode/**", "anon"); //登录二维码
|
||||
filterChainDefinitionMap.put("/sys/getQrcodeToken/**", "anon"); //监听扫码
|
||||
|
|
|
|||
|
|
@ -12,6 +12,7 @@ import org.springframework.stereotype.Service;
|
|||
import javax.annotation.PostConstruct;
|
||||
import javax.sql.DataSource;
|
||||
import java.util.List;
|
||||
import java.util.stream.Collectors;
|
||||
|
||||
@Slf4j
|
||||
@Service
|
||||
|
|
@ -27,11 +28,50 @@ public class DataSourceLoader {
|
|||
refreshDataSources();
|
||||
}
|
||||
|
||||
// public void refreshDataSources() {
|
||||
// DynamicRoutingDataSource ds = (DynamicRoutingDataSource) dataSource;
|
||||
// DataSource mainDataSource = ds.getDataSource("devops");
|
||||
//
|
||||
// // 从主数据源读取配置
|
||||
// List<DataSourceEntity> configs = new JdbcTemplate(mainDataSource).query(
|
||||
// "SELECT id, code, name, db_type, db_driver, db_url, db_name, db_username ,db_password ,sys_org_code FROM sys_data_source",
|
||||
// (rs, rowNum) -> new DataSourceEntity(
|
||||
// rs.getString("id"),
|
||||
// rs.getString("code"),
|
||||
// rs.getString("name"),
|
||||
// rs.getString("db_type"),
|
||||
// rs.getString("db_driver"),
|
||||
// rs.getString("db_url"),
|
||||
// rs.getString("db_name"),
|
||||
// rs.getString("db_username"),
|
||||
// rs.getString("db_password"),
|
||||
// rs.getString("sys_org_code")
|
||||
// )
|
||||
// );
|
||||
//
|
||||
// // 创建并添加数据源
|
||||
// configs.forEach(config -> {
|
||||
// DataSourceProperty dataSourceProperty = new DataSourceProperty();
|
||||
// dataSourceProperty.setUrl(config.getDbUrl());
|
||||
// dataSourceProperty.setUsername(config.getDbUsername());
|
||||
// String dbPassword = SecurityUtil.jiemi(config.getDbPassword());
|
||||
// dataSourceProperty.setPassword(dbPassword);
|
||||
// dataSourceProperty.setDriverClassName(config.getDbDriver());
|
||||
// DataSource dynamicDataSource = dataSourceCreator.createDataSource(dataSourceProperty);
|
||||
// ds.addDataSource(config.getCode(), dynamicDataSource);
|
||||
// });
|
||||
// }
|
||||
|
||||
public void refreshDataSources() {
|
||||
DynamicRoutingDataSource ds = (DynamicRoutingDataSource) dataSource;
|
||||
DataSource mainDataSource = ds.getDataSource("devops");
|
||||
|
||||
// 从主数据源读取配置
|
||||
// 1. 从固定的主数据源(如 devops)读取最新的动态数据源配置
|
||||
DataSource mainDataSource = ds.getDataSource("devops"); // 必须是静态配置的,不能被动态删除!
|
||||
if (mainDataSource == null) {
|
||||
log.error("无法获取主数据源 'devops',刷新动态数据源失败!");
|
||||
return;
|
||||
}
|
||||
|
||||
List<DataSourceEntity> configs = new JdbcTemplate(mainDataSource).query(
|
||||
"SELECT id, code, name, db_type, db_driver, db_url, db_name, db_username ,db_password ,sys_org_code FROM sys_data_source",
|
||||
(rs, rowNum) -> new DataSourceEntity(
|
||||
|
|
@ -48,17 +88,33 @@ public class DataSourceLoader {
|
|||
)
|
||||
);
|
||||
|
||||
// 创建并添加数据源
|
||||
configs.forEach(config -> {
|
||||
DataSourceProperty dataSourceProperty = new DataSourceProperty();
|
||||
dataSourceProperty.setUrl(config.getDbUrl());
|
||||
dataSourceProperty.setUsername(config.getDbUsername());
|
||||
String dbPassword = SecurityUtil.jiemi(config.getDbPassword());
|
||||
dataSourceProperty.setPassword(dbPassword);
|
||||
dataSourceProperty.setDriverClassName(config.getDbDriver());
|
||||
DataSource dynamicDataSource = dataSourceCreator.createDataSource(dataSourceProperty);
|
||||
ds.addDataSource(config.getCode(), dynamicDataSource);
|
||||
});
|
||||
}
|
||||
|
||||
// 2. 新增或更新
|
||||
for (DataSourceEntity config : configs) {
|
||||
String code = config.getCode();
|
||||
if (code == null || code.isEmpty()) {
|
||||
log.warn("跳过无效数据源配置(code 为空): {}", config);
|
||||
continue;
|
||||
}
|
||||
|
||||
try {
|
||||
DataSourceProperty prop = new DataSourceProperty();
|
||||
prop.setUrl(config.getDbUrl());
|
||||
prop.setUsername(config.getDbUsername());
|
||||
prop.setPassword(SecurityUtil.jiemi(config.getDbPassword()));
|
||||
prop.setDriverClassName(config.getDbDriver());
|
||||
|
||||
DataSource newDs = dataSourceCreator.createDataSource(prop);
|
||||
ds.addDataSource(code, newDs); // 如果已存在,会先 close 旧的再替换(DynamicRoutingDataSource 内部逻辑)
|
||||
log.info("已添加/更新动态数据源: {}", code);
|
||||
} catch (Exception e) {
|
||||
log.error("创建/更新数据源失败,code={}", code, e);
|
||||
}
|
||||
}
|
||||
|
||||
log.info("动态数据源同步完成。当前动态数据源列表: {}",
|
||||
ds.getDataSources().keySet().stream()
|
||||
.filter(name -> !name.equals("master"))
|
||||
.collect(Collectors.toList()));
|
||||
}
|
||||
}
|
||||
|
|
|
|||
Loading…
Reference in New Issue