|
@@ -1,10 +1,12 @@
|
|
package org.dbsyncer.storage.support;
|
|
package org.dbsyncer.storage.support;
|
|
|
|
|
|
|
|
+import org.apache.commons.dbcp.DelegatingDatabaseMetaData;
|
|
import org.apache.commons.lang.StringUtils;
|
|
import org.apache.commons.lang.StringUtils;
|
|
|
|
+import org.dbsyncer.common.util.CollectionUtils;
|
|
import org.dbsyncer.connector.config.DatabaseConfig;
|
|
import org.dbsyncer.connector.config.DatabaseConfig;
|
|
import org.dbsyncer.connector.util.DatabaseUtil;
|
|
import org.dbsyncer.connector.util.DatabaseUtil;
|
|
|
|
+import org.dbsyncer.connector.util.JDBCUtil;
|
|
import org.dbsyncer.storage.AbstractStorageService;
|
|
import org.dbsyncer.storage.AbstractStorageService;
|
|
-import org.dbsyncer.storage.enums.StorageEnum;
|
|
|
|
import org.dbsyncer.storage.query.Query;
|
|
import org.dbsyncer.storage.query.Query;
|
|
import org.slf4j.Logger;
|
|
import org.slf4j.Logger;
|
|
import org.slf4j.LoggerFactory;
|
|
import org.slf4j.LoggerFactory;
|
|
@@ -14,6 +16,10 @@ import org.springframework.jdbc.core.JdbcTemplate;
|
|
import org.springframework.stereotype.Component;
|
|
import org.springframework.stereotype.Component;
|
|
|
|
|
|
import javax.annotation.PostConstruct;
|
|
import javax.annotation.PostConstruct;
|
|
|
|
+import java.io.*;
|
|
|
|
+import java.lang.reflect.Field;
|
|
|
|
+import java.sql.Connection;
|
|
|
|
+import java.sql.DatabaseMetaData;
|
|
import java.util.HashSet;
|
|
import java.util.HashSet;
|
|
import java.util.List;
|
|
import java.util.List;
|
|
import java.util.Map;
|
|
import java.util.Map;
|
|
@@ -39,6 +45,9 @@ public class MysqlStorageServiceImpl extends AbstractStorageService {
|
|
|
|
|
|
private final Object createTableLock = new Object();
|
|
private final Object createTableLock = new Object();
|
|
|
|
|
|
|
|
+ private static final String PREFIX_TABLE = "dbsyncer_";
|
|
|
|
+ private static final String QUERY_TABLE = "show tables where Tables_in_%s = \"%s\"";
|
|
|
|
+
|
|
@PostConstruct
|
|
@PostConstruct
|
|
private void init() {
|
|
private void init() {
|
|
config = null == config ? new DatabaseConfig() : config;
|
|
config = null == config ? new DatabaseConfig() : config;
|
|
@@ -55,8 +64,8 @@ public class MysqlStorageServiceImpl extends AbstractStorageService {
|
|
jdbcTemplate = DatabaseUtil.getJdbcTemplate(config);
|
|
jdbcTemplate = DatabaseUtil.getJdbcTemplate(config);
|
|
|
|
|
|
// 创建配置和日志表
|
|
// 创建配置和日志表
|
|
- createTableIfNotExist(StorageEnum.CONFIG.getType());
|
|
|
|
- createTableIfNotExist(StorageEnum.LOG.getType());
|
|
|
|
|
|
+ //createTableIfNotExist(StorageEnum.CONFIG.getType());
|
|
|
|
+ //createTableIfNotExist(StorageEnum.LOG.getType());
|
|
}
|
|
}
|
|
|
|
|
|
@Override
|
|
@Override
|
|
@@ -108,6 +117,8 @@ public class MysqlStorageServiceImpl extends AbstractStorageService {
|
|
}
|
|
}
|
|
|
|
|
|
private void createTableIfNotExist(String table) {
|
|
private void createTableIfNotExist(String table) {
|
|
|
|
+ // 前缀标识
|
|
|
|
+ table = PREFIX_TABLE.concat(table);
|
|
synchronized (createTableLock) {
|
|
synchronized (createTableLock) {
|
|
// 1、检查本地缓存
|
|
// 1、检查本地缓存
|
|
if (tables.contains(table)) {
|
|
if (tables.contains(table)) {
|
|
@@ -115,7 +126,74 @@ public class MysqlStorageServiceImpl extends AbstractStorageService {
|
|
}
|
|
}
|
|
|
|
|
|
// 2、检查DB中是否创建
|
|
// 2、检查DB中是否创建
|
|
- // show tables;
|
|
|
|
|
|
+ Connection connection = null;
|
|
|
|
+ Map<String, Object> map = null;
|
|
|
|
+ try {
|
|
|
|
+ connection = jdbcTemplate.getDataSource().getConnection();
|
|
|
|
+ DelegatingDatabaseMetaData md = (DelegatingDatabaseMetaData) connection.getMetaData();
|
|
|
|
+ DatabaseMetaData delegate = md.getDelegate();
|
|
|
|
+ String databaseName = getDatabaseName(delegate);
|
|
|
|
+ // show tables where Tables_in_dbsyncer = "dbsyncer_config"
|
|
|
|
+ String sql = String.format(QUERY_TABLE, databaseName, table);
|
|
|
|
+ logger.info(sql);
|
|
|
|
+ map = jdbcTemplate.queryForMap(sql);
|
|
|
|
+ } catch (Exception e) {
|
|
|
|
+ logger.error(e.getMessage());
|
|
|
|
+ } finally {
|
|
|
|
+ JDBCUtil.close(connection);
|
|
|
|
+ }
|
|
|
|
+
|
|
|
|
+ // 不存在表,则创建
|
|
|
|
+ if (CollectionUtils.isEmpty(map)) {
|
|
|
|
+ createTable(table);
|
|
|
|
+ }
|
|
|
|
+ }
|
|
|
|
+ }
|
|
|
|
+
|
|
|
|
+ private void createTable(String table) {
|
|
|
|
+ // /dbsyncer_config.sql
|
|
|
|
+ String sql = readSql(PREFIX_TABLE.concat(table).concat(".sql"));
|
|
|
|
+ jdbcTemplate.execute(sql);
|
|
|
|
+ }
|
|
|
|
+
|
|
|
|
+ private String getDatabaseName(DatabaseMetaData delegate) throws NoSuchFieldException, IllegalAccessException {
|
|
|
|
+ Class clazz = delegate.getClass().getSuperclass();
|
|
|
|
+ Field field = clazz.getDeclaredField("database");
|
|
|
|
+ field.setAccessible(true);
|
|
|
|
+ Object value = field.get(delegate);
|
|
|
|
+ return (String) value;
|
|
|
|
+ }
|
|
|
|
+
|
|
|
|
+ private String readSql(String filePath) {
|
|
|
|
+ StringBuilder res = new StringBuilder();
|
|
|
|
+ InputStream in = null;
|
|
|
|
+ InputStreamReader isr = null;
|
|
|
|
+ BufferedReader bf = null;
|
|
|
|
+ try {
|
|
|
|
+ in = this.getClass().getResourceAsStream(filePath);
|
|
|
|
+ isr = new InputStreamReader(in, "UTF-8");
|
|
|
|
+ bf = new BufferedReader(isr);
|
|
|
|
+ String newLine;
|
|
|
|
+ while ((newLine = bf.readLine()) != null) {
|
|
|
|
+ res.append(newLine);
|
|
|
|
+ }
|
|
|
|
+ } catch (IOException e) {
|
|
|
|
+ logger.error("failed read file:{}", filePath);
|
|
|
|
+ } finally {
|
|
|
|
+ close(bf);
|
|
|
|
+ close(isr);
|
|
|
|
+ close(in);
|
|
|
|
+ }
|
|
|
|
+ return res.toString();
|
|
|
|
+ }
|
|
|
|
+
|
|
|
|
+ private void close(Closeable closeable) {
|
|
|
|
+ if (null != closeable) {
|
|
|
|
+ try {
|
|
|
|
+ closeable.close();
|
|
|
|
+ } catch (IOException e) {
|
|
|
|
+ logger.error(e.getMessage());
|
|
|
|
+ }
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
|