mybatis-plus 从数据库加载多数据源,以及往spring动态添加数据源
import com.baomidou.dynamic.datasource.provider.AbstractJdbcDataSourceProvider;
import com.baomidou.dynamic.datasource.provider.DynamicDataSourceProvider;
import com.baomidou.dynamic.datasource.spring.boot.autoconfigure.DataSourceProperty;
import com.baomidou.dynamic.datasource.spring.boot.autoconfigure.DynamicDataSourceProperties;
import lombok.extern.slf4j.Slf4j;
import org.jeecg.common.util.security.JdbcSecurityUtil;
import org.jeecg.modules.system.util.SecurityUtil;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import java.sql.*;
import java.util.Map;
@Configuration
@Slf4j
public class DatasourceConfig {
@Bean
public DynamicDataSourceProvider dynamicDataSourceProvider(DynamicDataSourceProperties properties) {
Map<String, DataSourceProperty> datasourceMap = properties.getDatasource();
DataSourceProperty masterDataSourceProperty = datasourceMap.get(properties.getPrimary());
return new AbstractJdbcDataSourceProvider(masterDataSourceProperty.getDriverClassName(), masterDataSourceProperty.getUrl(), masterDataSourceProperty.getUsername(), masterDataSourceProperty.getPassword()) {
@Override
protected Map<String, DataSourceProperty> executeStmt(Statement statement) throws SQLException {
ResultSet resultSet = statement.executeQuery("select code, db_username username,db_password password,db_url url, db_driver driver from sys_data_source ");
while (resultSet.next()){
String code = resultSet.getString("code");
String username = resultSet.getString("username");
String password = resultSet.getString("password");
try {
password = SecurityUtil.jiemi(password);
} catch (Exception e) {
log.warn("SecurityUtil.jiemi error, code:{}", code, e);
continue;
}
String url = resultSet.getString("url");
String driver = resultSet.getString("driver");
addDatasource(code, username, password, url, driver, datasourceMap);
}
return datasourceMap;
}
};
}
private static void addDatasource(String code, String username, String password, String url, String driver, Map<String, DataSourceProperty> datasourceMap) {
if (!testConnection(code, username, password, url, driver)) return;
DataSourceProperty property = new DataSourceProperty();
property.setUsername(username);
property.setUrl(url);
property.setDriverClassName(driver);
property.setPassword(password);
datasourceMap.put(code, property);
}
private static boolean testConnection(String code, String username, String password, String url, String driver) {
log.info("test connection start. code:{}", code);
Connection var2 = null;
try {
Class.forName(driver);
} catch (ClassNotFoundException e) {
log.warn("class not found. code: {}", code, e);
return false;
}
try {
JdbcSecurityUtil.validate(url);
DriverManager.setLoginTimeout(3);
var2 = DriverManager.getConnection(url, username, password);
if (var2 == null) {
log.warn("connection fail. code: {}", code);
return false;
}
log.info("test connection success. code:{}", code);
} catch (Exception e) {
log.warn("connection error. code: {}", code, e);
return false;
} finally {
try {
if (var2 != null && !var2.isClosed()) {
var2.close();
}
} catch (SQLException e) {
log.warn(e.toString());
}
}
return true;
}
}
private void addDynamicDataSource(SysDataSource sysDataSource, String dbPassword) {
DataSourceProperty dataSourceProperty = new DataSourceProperty();
dataSourceProperty.setUrl(sysDataSource.getDbUrl());
dataSourceProperty.setPassword(dbPassword);
dataSourceProperty.setDriverClassName(sysDataSource.getDbDriver());
dataSourceProperty.setUsername(sysDataSource.getDbUsername());
DynamicRoutingDataSource ds = (DynamicRoutingDataSource) dataSource;
DataSource dataSource = dataSourceCreator.createDataSource(dataSourceProperty);
try {
ds.addDataSource(sysDataSource.getCode(), dataSource);
} catch (Exception e) {
e.printStackTrace();
}
}
private void removeDynamicDataSource(String code) {
DynamicRoutingDataSource ds = (DynamicRoutingDataSource) dataSource;
ds.removeDataSource(code);
}