Skip to content
Projects
Groups
Snippets
Help
Loading...
Help
Support
Submit feedback
Contribute to GitLab
Sign in
Toggle navigation
H
holmes
Project
Project
Details
Activity
Releases
Cycle Analytics
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Charts
Issues
0
Issues
0
List
Boards
Labels
Milestones
Merge Requests
0
Merge Requests
0
CI / CD
CI / CD
Pipelines
Jobs
Schedules
Charts
Wiki
Wiki
Snippets
Snippets
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Charts
Create a new issue
Jobs
Commits
Issue Boards
Open sidebar
QA
holmes
Commits
0584c7e7
Commit
0584c7e7
authored
Jun 23, 2021
by
黎博
Browse files
Options
Browse Files
Download
Plain Diff
Merge branch 'master' into ldap
parents
aa5d6cc8
2ca6b89b
Changes
7
Hide whitespace changes
Inline
Side-by-side
Showing
7 changed files
with
941 additions
and
0 deletions
+941
-0
pom.xml
pom.xml
+8
-0
DbSyncController.java
...java/cn/qg/holmes/controller/effect/DbSyncController.java
+81
-0
DatabaseSyncService.java
...java/cn/qg/holmes/service/effect/DatabaseSyncService.java
+21
-0
DatabaseSyncServiceImpl.java
...g/holmes/service/effect/impl/DatabaseSyncServiceImpl.java
+712
-0
K8sService.java
src/main/java/cn/qg/holmes/utils/K8sService.java
+80
-0
kube-config.yml
src/main/resources/kube-config.yml
+18
-0
tke-cluster-ca.crt
src/main/resources/tke-cluster-ca.crt
+21
-0
No files found.
pom.xml
View file @
0584c7e7
...
@@ -148,6 +148,14 @@
...
@@ -148,6 +148,14 @@
<version>
4.1.1
</version>
<version>
4.1.1
</version>
</dependency>
</dependency>
<!-- https://mvnrepository.com/artifact/io.fabric8/kubernetes-client -->
<dependency>
<groupId>
io.fabric8
</groupId>
<artifactId>
kubernetes-client
</artifactId>
<version>
5.4.1
</version>
</dependency>
</dependencies>
</dependencies>
<build>
<build>
...
...
src/main/java/cn/qg/holmes/controller/effect/DbSyncController.java
0 → 100644
View file @
0584c7e7
package
cn
.
qg
.
holmes
.
controller
.
effect
;
import
cn.qg.holmes.common.JsonResult
;
import
cn.qg.holmes.service.effect.DatabaseSyncService
;
import
cn.qg.holmes.utils.K8sService
;
import
lombok.extern.slf4j.Slf4j
;
import
org.springframework.beans.factory.annotation.Autowired
;
import
org.springframework.beans.factory.annotation.Value
;
import
org.springframework.web.bind.annotation.*
;
import
java.util.List
;
import
java.util.Map
;
@Slf4j
@CrossOrigin
@RestController
@RequestMapping
(
"/dbsync"
)
public
class
DbSyncController
{
@Autowired
DatabaseSyncService
databaseSyncService
;
@Value
(
"${dbsync.mysql.ip}"
)
private
String
ip
;
@Value
(
"${dbsync.mysql.port}"
)
private
String
port
;
@Value
(
"${dbsync.mysql.username}"
)
private
String
username
;
@Value
(
"${dbsync.mysql.password}"
)
private
String
password
;
@GetMapping
(
"/one"
)
public
JsonResult
syncSingleTable
(
@RequestParam
String
namespace
,
@RequestParam
String
dbName
,
@RequestParam
String
tableName
)
{
try
{
long
startTime
=
System
.
currentTimeMillis
();
Map
<
String
,
String
>
map
=
databaseSyncService
.
getMysqlInfoByNamespace
(
namespace
);
String
destIp
=
map
.
get
(
"ip"
);
String
destPort
=
map
.
get
(
"port"
);
log
.
info
(
"获取到{}环境的Mysql地址为:{}"
,
namespace
,
destIp
+
":"
+
destPort
);
if
(
tableName
.
equalsIgnoreCase
(
"all"
)
||
tableName
.
equals
(
""
))
{
log
.
info
(
"开始同步{}库下所有的表"
,
dbName
);
databaseSyncService
.
getDbInfoFromSource
(
ip
,
port
,
username
,
password
,
dbName
);
databaseSyncService
.
syncDbToDest
(
destIp
,
destPort
,
"qa"
,
"qatest"
,
dbName
,
namespace
);
}
else
{
log
.
info
(
"开始同步{}库下{}表"
,
dbName
,
tableName
);
databaseSyncService
.
getSingleTableFromSource
(
ip
,
port
,
username
,
password
,
dbName
,
tableName
);
databaseSyncService
.
syncSingleTableToDest
(
destIp
,
destPort
,
"qa"
,
"qatest"
,
dbName
,
tableName
);
}
long
endTime
=
System
.
currentTimeMillis
();
long
elapsedTime
=
(
endTime
-
startTime
)
/
1000
;
return
JsonResult
.
buildSuccessResult
(
elapsedTime
+
"s"
);
}
catch
(
Exception
e
)
{
e
.
printStackTrace
();
return
JsonResult
.
buildErrorStateResult
(
"同步失败!"
,
false
);
}
}
/**
* 获取数据库列表
* @return
*/
@GetMapping
(
"/dbs"
)
public
JsonResult
getDatabaseList
()
{
return
JsonResult
.
buildSuccessResult
(
databaseSyncService
.
getDatabaseList
(
ip
,
port
,
username
,
password
));
}
/**
* 获取某个库下的表列表
* @param dbName 数据库名
* @return
*/
@GetMapping
(
"/tables"
)
public
JsonResult
getTableList
(
@RequestParam
String
dbName
)
{
List
<
Object
>
tableList
=
databaseSyncService
.
getTableListByDb
(
ip
,
port
,
username
,
password
,
dbName
);
tableList
.
add
(
0
,
"all"
);
return
JsonResult
.
buildSuccessResult
(
tableList
);
}
}
src/main/java/cn/qg/holmes/service/effect/DatabaseSyncService.java
0 → 100644
View file @
0584c7e7
package
cn
.
qg
.
holmes
.
service
.
effect
;
import
java.util.List
;
import
java.util.Map
;
public
interface
DatabaseSyncService
{
boolean
getDbInfoFromSource
(
String
ip
,
String
port
,
String
username
,
String
password
,
String
dbName
);
boolean
syncDbToDest
(
String
ip
,
String
port
,
String
username
,
String
password
,
String
dbName
,
String
namespace
);
boolean
getSingleTableFromSource
(
String
ip
,
String
port
,
String
username
,
String
password
,
String
dbName
,
String
tableName
);
boolean
syncSingleTableToDest
(
String
ip
,
String
port
,
String
username
,
String
password
,
String
dbName
,
String
tableName
);
List
<
Object
>
getDatabaseList
(
String
ip
,
String
port
,
String
username
,
String
password
);
Map
<
String
,
String
>
getMysqlInfoByNamespace
(
String
namespace
);
List
<
Object
>
getTableListByDb
(
String
ip
,
String
port
,
String
username
,
String
password
,
String
dbName
);
}
\ No newline at end of file
src/main/java/cn/qg/holmes/service/effect/impl/DatabaseSyncServiceImpl.java
0 → 100644
View file @
0584c7e7
package
cn
.
qg
.
holmes
.
service
.
effect
.
impl
;
import
cn.qg.holmes.service.effect.DatabaseSyncService
;
import
cn.qg.holmes.utils.HttpClientUtils
;
import
cn.qg.holmes.utils.RedisUtils
;
import
com.alibaba.fastjson.JSON
;
import
com.jayway.jsonpath.JsonPath
;
import
lombok.extern.slf4j.Slf4j
;
import
org.springframework.beans.factory.annotation.Autowired
;
import
org.springframework.beans.factory.annotation.Value
;
import
org.springframework.stereotype.Service
;
import
java.math.BigDecimal
;
import
java.sql.*
;
import
java.util.ArrayList
;
import
java.util.HashMap
;
import
java.util.List
;
import
java.util.Map
;
@Slf4j
@Service
public
class
DatabaseSyncServiceImpl
implements
DatabaseSyncService
{
@Autowired
RedisUtils
redisUtils
;
@Value
(
"${tke.host}"
)
private
String
tkeHost
;
@Value
(
"${cash_loan_flow.sql}"
)
private
String
cashLoanFlowSql
;
@Value
(
"${contract.sql}"
)
private
String
contractSql
;
@Value
(
"${payment_center.sql}"
)
private
String
paymentCenterSql
;
private
final
String
dbSyncPrefix
=
"dbsync:"
;
/**
* 从中间库获取数据库相关信息
* @param ip 中间库 ip
* @param port 中间库 port
* @param username 中间库用户名
* @param password 中间库密码
* @param dbName 数据库名
* @return
*/
@Override
public
boolean
getDbInfoFromSource
(
String
ip
,
String
port
,
String
username
,
String
password
,
String
dbName
)
{
String
driver
=
"com.mysql.jdbc.Driver"
;
String
url
=
"jdbc:mysql://"
+
ip
+
":"
+
port
+
"/"
+
dbName
;
String
createTableKey
=
dbSyncPrefix
+
dbName
+
":create"
;
String
insertTableKey
=
dbSyncPrefix
+
dbName
+
":insert"
;
String
dbRedisKey
=
dbSyncPrefix
+
dbName
;
Connection
connection
=
null
;
PreparedStatement
preparedStatement
=
null
;
String
dbRedisValue
=
""
;
String
insertRedisValue
=
""
;
List
<
Object
>
createTableRedisValue
=
new
ArrayList
<>();
List
<
String
>
columnNameList
=
new
ArrayList
<>();
List
<
String
>
columnTypeList
=
new
ArrayList
<>();
try
{
Class
.
forName
(
driver
);
connection
=
DriverManager
.
getConnection
(
url
,
username
,
password
);
if
(!
redisUtils
.
hasKey
(
dbRedisKey
))
{
String
dbSql
=
String
.
format
(
"SHOW CREATE DATABASE %s"
,
dbName
);
preparedStatement
=
connection
.
prepareStatement
(
dbSql
);
ResultSet
dbResultSet
=
preparedStatement
.
executeQuery
();
while
(
dbResultSet
.
next
())
{
dbRedisValue
=
dbResultSet
.
getString
(
2
);
}
// 设置建库语句的redis值
redisUtils
.
set
(
dbRedisKey
,
dbRedisValue
,
86400
);
}
if
(!
redisUtils
.
hasKey
(
createTableKey
))
{
DatabaseMetaData
databaseMetaData
=
connection
.
getMetaData
();
// 获取所有表名
ResultSet
tableResultSet
=
databaseMetaData
.
getTables
(
null
,
null
,
null
,
new
String
[]{
"TABLE"
});
while
(
tableResultSet
.
next
())
{
String
tableName
=
tableResultSet
.
getString
(
"TABLE_NAME"
);
// 获取所有建表语句
String
sql
=
String
.
format
(
"SHOW CREATE TABLE %s"
,
tableName
);
preparedStatement
=
connection
.
prepareStatement
(
sql
);
ResultSet
pResultSet
=
preparedStatement
.
executeQuery
();
while
(
pResultSet
.
next
())
{
createTableRedisValue
.
add
(
pResultSet
.
getString
(
2
));
}
if
(!
redisUtils
.
hasKey
(
insertTableKey
))
{
ResultSet
columnResultSet
=
databaseMetaData
.
getColumns
(
null
,
"%"
,
tableName
,
"%"
);
while
(
columnResultSet
.
next
())
{
// 字段名称
String
columnName
=
columnResultSet
.
getString
(
"COLUMN_NAME"
);
// 数据类型
String
columnType
=
columnResultSet
.
getString
(
"TYPE_NAME"
);
columnNameList
.
add
(
columnName
);
columnTypeList
.
add
(
columnType
);
}
String
columnArrayStr
=
null
;
for
(
String
column
:
columnNameList
)
{
if
(
null
==
columnArrayStr
)
{
columnArrayStr
=
"`"
+
column
+
"`"
;
}
else
{
columnArrayStr
=
columnArrayStr
+
","
+
"`"
+
column
+
"`"
;
}
}
String
selectSQL
=
String
.
format
(
"select %s from %s"
,
columnArrayStr
,
tableName
);
preparedStatement
=
connection
.
prepareStatement
(
selectSQL
);
ResultSet
selectResultSet
=
preparedStatement
.
executeQuery
();
while
(
selectResultSet
.
next
())
{
String
rowValues
=
getRowValues
(
selectResultSet
,
columnNameList
.
size
(),
columnTypeList
);
String
insertSql
=
String
.
format
(
"insert into %s (%s) values(%s);"
,
tableName
,
columnArrayStr
,
rowValues
);
insertSql
=
insertSql
.
replaceAll
(
"\n"
,
"<br/>"
);
insertSql
=
insertSql
+
"\n"
;
insertRedisValue
+=
insertSql
;
}
columnNameList
.
clear
();
columnTypeList
.
clear
();
}
}
redisUtils
.
lSet
(
createTableKey
,
createTableRedisValue
,
86400
);
redisUtils
.
set
(
insertTableKey
,
insertRedisValue
,
86400
);
}
}
catch
(
Exception
e
)
{
e
.
printStackTrace
();
}
finally
{
try
{
if
(
connection
!=
null
)
{
connection
.
close
();
}
if
(
preparedStatement
!=
null
)
{
preparedStatement
.
close
();
}
}
catch
(
Exception
e
)
{
e
.
printStackTrace
();
}
}
return
true
;
}
/**
* 同步数据库信息到目标地址
* @param ip 目标库ip
* @param port 目标库端口
* @param username 目标库用户名
* @param password 目标库密码
* @param dbName 目标库名称
* @return
*/
@Override
public
boolean
syncDbToDest
(
String
ip
,
String
port
,
String
username
,
String
password
,
String
dbName
,
String
namespace
)
{
String
driver
=
"com.mysql.jdbc.Driver"
;
String
url
=
"jdbc:mysql://"
+
ip
+
":"
+
port
;
String
createTableKey
=
dbSyncPrefix
+
dbName
+
":create"
;
String
insertTableKey
=
dbSyncPrefix
+
dbName
+
":insert"
;
String
dbRedisKey
=
dbSyncPrefix
+
dbName
;
Connection
connection
=
null
;
Connection
newConnection
=
null
;
PreparedStatement
preparedStatement
=
null
;
try
{
Class
.
forName
(
driver
);
connection
=
DriverManager
.
getConnection
(
url
,
username
,
password
);
// 删除原有数据库
String
dropDbSql
=
String
.
format
(
"DROP DATABASE IF EXISTS %s"
,
dbName
);
log
.
info
(
"删除原有数据库:{}"
,
dropDbSql
);
preparedStatement
=
connection
.
prepareStatement
(
dropDbSql
);
preparedStatement
.
execute
();
// 重新创建数据库
String
createDbSql
=
redisUtils
.
get
(
dbRedisKey
).
toString
();
log
.
info
(
"重新创建数据库:{}"
,
createDbSql
);
preparedStatement
=
connection
.
prepareStatement
(
createDbSql
);
preparedStatement
.
execute
();
connection
.
close
();
// 重新设置连接,并指定数据库
newConnection
=
DriverManager
.
getConnection
(
url
+
"/"
+
dbName
,
username
,
password
);
newConnection
.
setAutoCommit
(
false
);
// 从redis中获取要同步的表结构
List
<
Object
>
createTableRedisValue
=
redisUtils
.
lGet
(
createTableKey
,
0
,
redisUtils
.
lGetListSize
(
createTableKey
));
Statement
statement
=
newConnection
.
createStatement
();
log
.
info
(
"开始同步表结构!"
);
long
structureStartTime
=
System
.
currentTimeMillis
();
for
(
Object
sql:
createTableRedisValue
)
{
statement
.
addBatch
(
sql
.
toString
());
}
statement
.
executeBatch
();
statement
.
clearBatch
();
long
structureEndTime
=
System
.
currentTimeMillis
();
log
.
info
(
"表结构同步完成,共花费{}秒"
,
(
structureEndTime
-
structureStartTime
)
/
1000
);
// 从redis中同步表数据
String
insertTableRedisValue
=
redisUtils
.
get
(
insertTableKey
).
toString
();
log
.
info
(
"开始同步表数据!"
);
long
dataStartTime
=
System
.
currentTimeMillis
();
for
(
String
insertSql:
insertTableRedisValue
.
split
(
"\n"
))
{
// statement.addBatch(replaceDomain(insertSql, namespace));
statement
.
addBatch
(
insertSql
);
}
statement
.
executeBatch
();
statement
.
clearBatch
();
long
dataEndTime
=
System
.
currentTimeMillis
();
log
.
info
(
"表数据同步完成,共花费{}秒"
,
(
dataEndTime
-
dataStartTime
)
/
1000
);
// 判断是否需要update
if
(
dbName
.
equals
(
"cash_loan_flow"
))
{
for
(
String
sql:
cashLoanFlowSql
.
split
(
"\n"
))
{
log
.
info
(
"执行update sql: {}"
,
sql
);
statement
.
addBatch
(
sql
);
}
statement
.
executeBatch
();
statement
.
clearBatch
();
}
if
(
dbName
.
equals
(
"contract"
))
{
for
(
String
sql:
contractSql
.
split
(
"\n"
))
{
log
.
info
(
"执行update sql: {}"
,
sql
);
statement
.
addBatch
(
sql
);
}
statement
.
executeBatch
();
statement
.
clearBatch
();
}
if
(
dbName
.
equals
(
"payment_center"
))
{
for
(
String
sql:
paymentCenterSql
.
split
(
"\n"
))
{
log
.
info
(
"执行update sql: {}"
,
sql
);
statement
.
addBatch
(
sql
);
}
statement
.
executeBatch
();
statement
.
clearBatch
();
}
newConnection
.
commit
();
}
catch
(
Exception
e
)
{
e
.
printStackTrace
();
}
finally
{
try
{
if
(
connection
!=
null
)
{
connection
.
close
();
}
if
(
newConnection
!=
null
)
{
newConnection
.
close
();
}
if
(
preparedStatement
!=
null
)
{
preparedStatement
.
close
();
}
}
catch
(
Exception
e
)
{
e
.
printStackTrace
();
}
}
return
true
;
}
@Override
public
boolean
getSingleTableFromSource
(
String
ip
,
String
port
,
String
username
,
String
password
,
String
dbName
,
String
tableName
)
{
String
driver
=
"com.mysql.jdbc.Driver"
;
String
url
=
"jdbc:mysql://"
+
ip
+
":"
+
port
+
"/"
+
dbName
;
String
tableCreateKey
=
dbSyncPrefix
+
dbName
+
":"
+
tableName
+
":create"
;
String
tableInsertKey
=
dbSyncPrefix
+
dbName
+
":"
+
tableName
+
":insert"
;
String
insertRedisValue
=
""
;
Connection
connection
=
null
;
PreparedStatement
preparedStatement
=
null
;
List
<
String
>
columnNameList
=
new
ArrayList
<>();
List
<
String
>
columnTypeList
=
new
ArrayList
<>();
try
{
Class
.
forName
(
driver
);
connection
=
DriverManager
.
getConnection
(
url
,
username
,
password
);
connection
.
setAutoCommit
(
true
);
DatabaseMetaData
databaseMetaData
=
connection
.
getMetaData
();
if
(!
redisUtils
.
hasKey
(
tableCreateKey
))
{
String
sql
=
String
.
format
(
"SHOW CREATE TABLE %s"
,
tableName
);
preparedStatement
=
connection
.
prepareStatement
(
sql
);
ResultSet
resultSet
=
preparedStatement
.
executeQuery
();
while
(
resultSet
.
next
())
{
redisUtils
.
set
(
tableCreateKey
,
resultSet
.
getString
(
2
),
600
);
}
}
if
(!
redisUtils
.
hasKey
(
tableInsertKey
))
{
ResultSet
columnResultSet
=
databaseMetaData
.
getColumns
(
null
,
"%"
,
tableName
,
"%"
);
while
(
columnResultSet
.
next
())
{
// 字段名称
String
columnName
=
columnResultSet
.
getString
(
"COLUMN_NAME"
);
// 数据类型
String
columnType
=
columnResultSet
.
getString
(
"TYPE_NAME"
);
columnNameList
.
add
(
columnName
);
columnTypeList
.
add
(
columnType
);;
}
String
columnArrayStr
=
null
;
for
(
String
column
:
columnNameList
)
{
if
(
null
==
columnArrayStr
)
{
columnArrayStr
=
"`"
+
column
+
"`"
;
}
else
{
columnArrayStr
=
columnArrayStr
+
","
+
"`"
+
column
+
"`"
;
}
}
String
selectSQL
=
String
.
format
(
"select %s from %s"
,
columnArrayStr
,
tableName
);
preparedStatement
=
connection
.
prepareStatement
(
selectSQL
);
ResultSet
selectResultSet
=
preparedStatement
.
executeQuery
();
while
(
selectResultSet
.
next
())
{
String
rowValues
=
getRowValues
(
selectResultSet
,
columnNameList
.
size
(),
columnTypeList
);
String
insertSql
=
String
.
format
(
"insert into %s (%s) values(%s);"
,
tableName
,
columnArrayStr
,
rowValues
);
insertSql
=
insertSql
.
replaceAll
(
"\n"
,
"<br/>"
);
insertSql
=
insertSql
+
"\n"
;
insertRedisValue
+=
insertSql
;
}
redisUtils
.
set
(
tableInsertKey
,
insertRedisValue
,
600
);
}
}
catch
(
Exception
e
)
{
e
.
printStackTrace
();
return
false
;
}
finally
{
try
{
if
(
connection
!=
null
)
{
connection
.
close
();
}
if
(
preparedStatement
!=
null
)
{
preparedStatement
.
close
();
}
}
catch
(
Exception
e
)
{
e
.
printStackTrace
();
}
}
return
true
;
}
@Override
public
boolean
syncSingleTableToDest
(
String
ip
,
String
port
,
String
username
,
String
password
,
String
dbName
,
String
tableName
)
{
String
driver
=
"com.mysql.jdbc.Driver"
;
String
url
=
"jdbc:mysql://"
+
ip
+
":"
+
port
+
"/"
+
dbName
;
String
tableCreateKey
=
dbSyncPrefix
+
dbName
+
":"
+
tableName
+
":create"
;
String
tableInsertKey
=
dbSyncPrefix
+
dbName
+
":"
+
tableName
+
":insert"
;
Connection
connection
=
null
;
PreparedStatement
preparedStatement
=
null
;
Statement
statement
=
null
;
try
{
Class
.
forName
(
driver
);
connection
=
DriverManager
.
getConnection
(
url
,
username
,
password
);
connection
.
setAutoCommit
(
false
);
String
createTableSql
=
redisUtils
.
get
(
tableCreateKey
).
toString
();
String
insertTableSql
=
redisUtils
.
get
(
tableInsertKey
).
toString
();
// 如果表存在,则首先删除表
String
dropTableSql
=
String
.
format
(
"DROP TABLE if exists %s"
,
tableName
);
preparedStatement
=
connection
.
prepareStatement
(
dropTableSql
);
preparedStatement
.
execute
();
// 重新创建表
preparedStatement
=
connection
.
prepareStatement
(
createTableSql
);
preparedStatement
.
execute
();
statement
=
connection
.
createStatement
();
for
(
String
insertSql:
insertTableSql
.
split
(
"\n"
))
{
statement
.
addBatch
(
insertSql
);
}
statement
.
executeBatch
();
statement
.
clearBatch
();
connection
.
commit
();
}
catch
(
Exception
e
)
{
e
.
printStackTrace
();
return
false
;
}
finally
{
try
{
if
(
connection
!=
null
)
{
connection
.
close
();
}
if
(
preparedStatement
!=
null
)
{
preparedStatement
.
close
();
}
if
(
statement
!=
null
)
{
statement
.
close
();
}
}
catch
(
Exception
e
)
{
e
.
printStackTrace
();
}
}
return
true
;
}
/**
* 获取数据库列表
* @param ip 同步库ip
* @param port 同步库端口号
* @param username 同步库用户名
* @param password 同步库密码
* @return
*/
@Override
public
List
<
Object
>
getDatabaseList
(
String
ip
,
String
port
,
String
username
,
String
password
)
{
String
driver
=
"com.mysql.jdbc.Driver"
;
String
url
=
"jdbc:mysql://"
+
ip
+
":"
+
port
;
List
<
Object
>
databaseList
=
new
ArrayList
<>();
String
dbListRedisKey
=
dbSyncPrefix
+
":db:list"
;
if
(
redisUtils
.
hasKey
(
dbListRedisKey
))
{
databaseList
=
redisUtils
.
lGet
(
dbListRedisKey
,
0
,
redisUtils
.
lGetListSize
(
dbListRedisKey
));
log
.
info
(
"从redis获取到的数据库列表为:{}"
,
databaseList
);
}
else
{
Connection
connection
=
null
;
try
{
Class
.
forName
(
driver
);
connection
=
DriverManager
.
getConnection
(
url
,
username
,
password
);
connection
.
setAutoCommit
(
true
);
String
showDatabasesSql
=
"SHOW DATABASES"
;
PreparedStatement
preparedStatement
=
connection
.
prepareStatement
(
showDatabasesSql
);
ResultSet
dbListResultSet
=
preparedStatement
.
executeQuery
();
while
(
dbListResultSet
.
next
())
{
databaseList
.
add
(
dbListResultSet
.
getString
(
1
));
}
preparedStatement
.
close
();
// 设置数据库列表缓存,缓存24个小时
log
.
info
(
"从同步库获取到的数据库列表为:{}"
,
databaseList
);
redisUtils
.
lSet
(
dbListRedisKey
,
databaseList
,
86400
);
}
catch
(
Exception
e
)
{
e
.
printStackTrace
();
}
finally
{
try
{
if
(
connection
!=
null
)
{
connection
.
close
();
}
}
catch
(
Exception
e
)
{
connection
=
null
;
}
}
}
return
databaseList
;
}
/**
* 根据namespace获取对应的mysql ip和端口
* @param namespace
* @return
*/
@Override
public
Map
<
String
,
String
>
getMysqlInfoByNamespace
(
String
namespace
)
{
Map
<
String
,
String
>
headers
=
new
HashMap
<>();
Map
<
String
,
String
>
params
=
new
HashMap
<>();
headers
.
put
(
"cluster"
,
"qa"
);
params
.
put
(
"namespace"
,
namespace
);
params
.
put
(
"serviceName"
,
"mysql"
);
params
.
put
(
"type"
,
"base"
);
String
response
=
HttpClientUtils
.
doPostJson
(
tkeHost
+
"/service/details"
,
headers
,
JSON
.
toJSONString
(
params
));
String
mysqlIp
=
JsonPath
.
read
(
response
,
"$.data.lanIp"
).
toString
();
String
mysqlPort
=
JsonPath
.
read
(
response
,
"$.data.portMappings[0].nodePort"
).
toString
();
Map
<
String
,
String
>
result
=
new
HashMap
<>();
result
.
put
(
"ip"
,
mysqlIp
);
result
.
put
(
"port"
,
mysqlPort
);
return
result
;
}
/**
* 获取某个数据库下表列表
* @param ip mysql ip
* @param port mysql port
* @param username mysql 用户名
* @param password mysql 密码
* @param dbName 数据库名
* @return
*/
@Override
public
List
<
Object
>
getTableListByDb
(
String
ip
,
String
port
,
String
username
,
String
password
,
String
dbName
)
{
String
driver
=
"com.mysql.jdbc.Driver"
;
String
url
=
"jdbc:mysql://"
+
ip
+
":"
+
port
+
"/"
+
dbName
;
Connection
connection
=
null
;
PreparedStatement
preparedStatement
=
null
;
List
<
Object
>
tableList
=
new
ArrayList
<>();
try
{
Class
.
forName
(
driver
);
connection
=
DriverManager
.
getConnection
(
url
,
username
,
password
);
connection
.
setAutoCommit
(
false
);
String
tablesSql
=
"SHOW TABLES"
;
preparedStatement
=
connection
.
prepareStatement
(
tablesSql
);
ResultSet
tableListResultSet
=
preparedStatement
.
executeQuery
();
while
(
tableListResultSet
.
next
())
{
tableList
.
add
(
tableListResultSet
.
getString
(
1
));
}
return
tableList
;
}
catch
(
Exception
e
)
{
e
.
printStackTrace
();
return
null
;
}
finally
{
try
{
if
(
preparedStatement
!=
null
)
{
preparedStatement
.
close
();
}
if
(
connection
!=
null
)
{
connection
.
close
();
}
}
catch
(
Exception
e
)
{
connection
=
null
;
}
}
}
/**
* 获取表数据一行的所有值
* @param rs
* @param size
* @param columnTypeList
* @return
*/
private
String
getRowValues
(
ResultSet
rs
,
int
size
,
List
<
String
>
columnTypeList
)
{
try
{
String
rowValues
=
null
;
for
(
int
i
=
1
;
i
<=
size
;
i
++)
{
String
columnValue
=
null
;
// 获取字段值
columnValue
=
getValue
(
rs
,
i
,
columnTypeList
.
get
(
i
-
1
));
// 如果是空值不添加单引号
if
(
null
!=
columnValue
)
{
// if (columnValue.contains("'")) {
// columnValue = "\"" + columnValue + "\"";
// } else {
// columnValue = "'" + columnValue + "'";
// }
columnValue
=
columnValue
.
replace
(
"'"
,
"\\'"
);
columnValue
=
columnValue
.
replace
(
"\""
,
"\\\""
);
columnValue
=
"'"
+
columnValue
+
"'"
;
}
// 拼接字段值
if
(
null
==
rowValues
)
{
rowValues
=
columnValue
;
}
else
{
rowValues
=
rowValues
+
","
+
columnValue
;
}
}
return
rowValues
;
}
catch
(
Exception
e
)
{
e
.
printStackTrace
();
System
.
out
.
println
(
"获取表数据一行的所有值异常"
);
return
null
;
}
}
/**
* 根据类型获取字段值
* @return
* @author 2018年9月6日 上午11:16:00
*/
private
String
getValue
(
ResultSet
resultSet
,
Integer
index
,
String
columnType
)
{
try
{
if
(
"int"
.
equals
(
columnType
)
||
"INT"
.
equals
(
columnType
))
{
// 整数
Object
intValue
=
resultSet
.
getObject
(
index
);
if
(
null
==
intValue
)
{
return
null
;
}
return
intValue
+
""
;
}
else
if
(
"bigint"
.
equals
(
columnType
)
||
"BIGINT"
.
equals
(
columnType
))
{
// 长整形
Object
value
=
resultSet
.
getObject
(
index
);
if
(
null
==
value
)
{
return
null
;
}
return
value
+
""
;
}
else
if
(
"bigint unsigned"
.
equals
(
columnType
)
||
"BIGINT UNSIGNED"
.
equals
(
columnType
))
{
Object
value
=
resultSet
.
getObject
(
index
);
if
(
null
==
value
)
{
return
null
;
}
return
value
+
""
;
}
else
if
(
"smallint"
.
equals
(
columnType
)
||
"SMALLINT"
.
equals
(
columnType
))
{
// 整数
Object
value
=
resultSet
.
getObject
(
index
);
if
(
null
==
value
)
{
return
null
;
}
return
value
+
""
;
}
else
if
(
"tinyint"
.
equals
(
columnType
)
||
"TINYINT"
.
equals
(
columnType
))
{
// 整数
Object
value
=
resultSet
.
getObject
(
index
);
if
(
null
==
value
)
{
return
null
;
}
return
value
+
""
;
}
else
if
(
"mediumint"
.
equals
(
columnType
)
||
"MEDIUMINT"
.
equals
(
columnType
))
{
// 长整形
Object
value
=
resultSet
.
getObject
(
index
);
if
(
null
==
value
)
{
return
null
;
}
return
value
+
""
;
}
else
if
(
"integer"
.
equals
(
columnType
)
||
"INTEGER"
.
equals
(
columnType
))
{
// 整数
Object
value
=
resultSet
.
getObject
(
index
);
if
(
null
==
value
)
{
return
null
;
}
return
value
+
""
;
}
else
if
(
"float"
.
equals
(
columnType
)
||
"FLOAT"
.
equals
(
columnType
))
{
// 浮点数
Object
value
=
resultSet
.
getObject
(
index
);
if
(
null
==
value
)
{
return
null
;
}
return
value
+
""
;
}
else
if
(
"double"
.
equals
(
columnType
)
||
"DOUBLE"
.
equals
(
columnType
))
{
// 浮点数
Object
value
=
resultSet
.
getObject
(
index
);
if
(
null
==
value
)
{
return
null
;
}
return
value
+
""
;
}
else
if
(
"decimal"
.
equals
(
columnType
)
||
"DECIMAL"
.
equals
(
columnType
))
{
// 浮点数-金额类型
BigDecimal
value
=
resultSet
.
getBigDecimal
(
index
);
if
(
null
==
value
)
{
return
null
;
}
return
value
.
toString
();
}
else
if
(
"char"
.
equals
(
columnType
)
||
"CHAR"
.
equals
(
columnType
))
{
// 字符串类型
String
value
=
resultSet
.
getString
(
index
);
return
value
;
}
else
if
(
"varchar"
.
equals
(
columnType
)
||
"VARCHAR"
.
equals
(
columnType
))
{
// 字符串类型
String
value
=
resultSet
.
getString
(
index
);
return
value
;
}
else
if
(
"tinytext"
.
equals
(
columnType
)
||
"TINYTEXT"
.
equals
(
columnType
))
{
// 字符串类型
String
value
=
resultSet
.
getString
(
index
);
return
value
;
}
else
if
(
"text"
.
equals
(
columnType
)
||
"TEXT"
.
equals
(
columnType
))
{
// 字符串类型
String
value
=
resultSet
.
getString
(
index
);
return
value
;
}
else
if
(
"mediumtext"
.
equals
(
columnType
)
||
"MEDIUMTEXT"
.
equals
(
columnType
))
{
// 字符串类型
String
value
=
resultSet
.
getString
(
index
);
return
value
;
}
else
if
(
"longtext"
.
equals
(
columnType
)
||
"LONGTEXT"
.
equals
(
columnType
))
{
// 字符串类型
String
value
=
resultSet
.
getString
(
index
);
return
value
;
}
else
if
(
"year"
.
equals
(
columnType
)
||
"YEAR"
.
equals
(
columnType
))
{
// 时间类型:范围 1901/2155 格式 YYYY
String
year
=
resultSet
.
getString
(
index
);
if
(
null
==
year
)
{
return
null
;
}
// 只需要年的字符即可,
return
year
.
substring
(
0
,
4
);
}
else
if
(
"date"
.
equals
(
columnType
)
||
"DATE"
.
equals
(
columnType
))
{
// 时间类型:范围 '1000-01-01'--'9999-12-31' 格式 YYYY-MM-DD
return
resultSet
.
getString
(
index
);
}
else
if
(
"time"
.
equals
(
columnType
)
||
"TIME"
.
equals
(
columnType
))
{
// 时间类型:范围 '-838:59:59'到'838:59:59' 格式 HH:MM:SS
return
resultSet
.
getString
(
index
);
}
else
if
(
"datetime"
.
equals
(
columnType
)
||
"DATETIME"
.
equals
(
columnType
))
{
// 时间类型:范围 '1000-01-01 00:00:00'--'9999-12-31 23:59:59' 格式 YYYY-MM-DD HH:MM:SS
return
resultSet
.
getString
(
index
);
}
else
if
(
"timestamp"
.
equals
(
columnType
)
||
"TIMESTAMP"
.
equals
(
columnType
))
{
// 时间类型:范围 1970-01-01 00:00:00/2037 年某时 格式 YYYYMMDD HHMMSS 混合日期和时间值,时间戳
return
resultSet
.
getString
(
index
);
}
else
{
Object
value
=
resultSet
.
getObject
(
index
);
if
(
null
==
value
)
{
return
null
;
}
return
value
+
""
;
}
}
catch
(
Exception
e
)
{
e
.
printStackTrace
();
System
.
err
.
println
(
"获取数据库类型值异常"
);
return
"0000-00-00 00:00:00"
;
}
}
private
String
replaceDomain
(
String
sql
,
String
namespace
)
{
if
(
sql
.
contains
(
"xyqb.com"
))
{
return
sql
.
replace
(
".xyqb.com"
,
"-"
+
namespace
+
".liangkebang.net"
);
}
else
if
(
sql
.
contains
(
".q-gp.com"
))
{
return
sql
.
replace
(
".q-gp.com"
,
"-"
+
namespace
+
".liangkebang.net"
);
}
else
{
return
sql
;
}
}
}
src/main/java/cn/qg/holmes/utils/K8sService.java
0 → 100644
View file @
0584c7e7
package
cn
.
qg
.
holmes
.
utils
;
import
io.fabric8.kubernetes.api.model.Namespace
;
import
io.fabric8.kubernetes.client.Config
;
import
io.fabric8.kubernetes.client.DefaultKubernetesClient
;
import
io.fabric8.kubernetes.client.KubernetesClient
;
import
lombok.extern.slf4j.Slf4j
;
import
org.springframework.core.io.ClassPathResource
;
import
org.springframework.stereotype.Component
;
import
java.io.BufferedReader
;
import
java.io.IOException
;
import
java.io.InputStream
;
import
java.io.InputStreamReader
;
import
java.util.ArrayList
;
import
java.util.HashMap
;
import
java.util.List
;
import
java.util.Map
;
@Slf4j
//@Component
public
class
K8sService
{
private
KubernetesClient
kubernetesClient
;
public
K8sService
()
{
try
{
String
configYAML
=
String
.
join
(
"\n"
,
readConfigFile
(
"kube-config.yml"
));
Config
config
=
Config
.
fromKubeconfig
(
configYAML
);
kubernetesClient
=
new
DefaultKubernetesClient
(
config
);
String
configCrt
=
String
.
join
(
"\n"
,
readConfigFile
(
"tke-cluster-ca.crt"
));
config
.
setCaCertData
(
configCrt
);
}
catch
(
Exception
e
)
{
log
.
info
(
"k8s service 初始化失败!"
);
e
.
printStackTrace
();
}
}
/**
* 读取k8s配置文件
* @param file 配置文件名
* @return
* @throws IOException
*/
public
static
List
<
String
>
readConfigFile
(
String
file
)
throws
IOException
{
String
str
=
""
;
ClassPathResource
resource
=
new
ClassPathResource
(
file
);
InputStream
in
=
resource
.
getInputStream
();
BufferedReader
br
=
new
BufferedReader
(
new
InputStreamReader
(
in
));
List
<
String
>
result
=
new
ArrayList
<>();
while
((
str
=
br
.
readLine
())
!=
null
)
{
result
.
add
(
str
);
}
return
result
;
}
/**
* 获取namespace列表
* @return
*/
public
List
<
Map
<
String
,
Object
>>
getNamespaceList
()
{
List
<
Map
<
String
,
Object
>>
resultList
=
new
ArrayList
<>();
List
<
Namespace
>
namespaceList
=
kubernetesClient
.
namespaces
().
list
().
getItems
();
for
(
Namespace
namespace:
namespaceList
)
{
log
.
info
(
namespace
.
toString
());
if
(
namespace
.
getMetadata
().
getAnnotations
()
!=
null
)
{
Map
<
String
,
Object
>
map
=
new
HashMap
<>();
map
.
put
(
"name"
,
namespace
.
getMetadata
().
getName
());
map
.
put
(
"description"
,
namespace
.
getMetadata
().
getAnnotations
().
get
(
"description"
));
map
.
put
(
"owner"
,
namespace
.
getMetadata
().
getAnnotations
().
get
(
"owner"
));
map
.
put
(
"status"
,
namespace
.
getStatus
().
getPhase
());
map
.
put
(
"createdAt"
,
namespace
.
getMetadata
().
getCreationTimestamp
());
resultList
.
add
(
map
);
}
}
return
resultList
;
}
}
src/main/resources/kube-config.yml
0 → 100644
View file @
0584c7e7
apiVersion
:
v1
clusters
:
-
cluster
:
certificate-authority-data
:
LS0tLS1CRUdJTiBDRVJUSUZJQ0FURS0tLS0tCk1JSURaRENDQWt5Z0F3SUJBZ0lJQWlFbzhnb1ZhZVl3RFFZSktvWklodmNOQVFFTEJRQXdVREVMTUFrR0ExVUUKQmhNQ1EwNHhLakFSQmdOVkJBb1RDblJsYm1ObGJuUjVkVzR3RlFZRFZRUUtFdzV6ZVhOMFpXMDZiV0Z6ZEdWeQpjekVWTUJNR0ExVUVBeE1NWTJ4ekxXRmpabmcwY0hacU1CNFhEVEU1TURFd016QXpNRFExTWxvWERUTTVNREV3Ck16QXpNRFExTWxvd1VERUxNQWtHQTFVRUJoTUNRMDR4S2pBUkJnTlZCQW9UQ25SbGJtTmxiblI1ZFc0d0ZRWUQKVlFRS0V3NXplWE4wWlcwNmJXRnpkR1Z5Y3pFVk1CTUdBMVVFQXhNTVkyeHpMV0ZqWm5nMGNIWnFNSUlCSWpBTgpCZ2txaGtpRzl3MEJBUUVGQUFPQ0FROEFNSUlCQ2dLQ0FRRUE1UnVyS0hSMG5GMlAyNndlU01haittbXltdytsCkEvODFyNUl3QVFZaXoxSDRRT3IrVFdiZjd0Z2JsWXNOemJpSk5qTk56VkRiQ2RidkhZaHhLNlVjemJDOGJocXEKakE4Y29tcCtkbENlNm13VEJKNzRwM08rSlduNFJOY0QreHJ4dXJ6aE9GRFZra1RrRWNqMDZXT25oMk9Dc0VaQwpCeVczWlBYQ2p1ZG8wNUprTUhXaEUvcERmSWEyYWIxNmRZeGZ2SWhzdjhYcWdRMm92T0RvOEg5aVBmWkMvVkl4CmpoUWtPem1SbmRlRXgvWlpiWTlvMW9PbWwxcjl3ZnRXWklzWTJYbTY0SzRrVDg3YWZURi9xaXZ4OEdXOXBwRHkKb3JZVlhnVVFKVkRHMmIyWXdGYldYdlB3SzZZYlNVOUdydUplUnFmdklLaSt3S3RxQzBMZ1pZckxVd0lEQVFBQgpvMEl3UURBT0JnTlZIUThCQWY4RUJBTUNBb1F3SFFZRFZSMGxCQll3RkFZSUt3WUJCUVVIQXdJR0NDc0dBUVVGCkJ3TUJNQThHQTFVZEV3RUIvd1FGTUFNQkFmOHdEUVlKS29aSWh2Y05BUUVMQlFBRGdnRUJBRi9jYzF0RGZUSFEKeDVyRmpyUEt5YW5xOWJWb2YySlorMnhiaHp1b2sxU2ljYlNwdExia0h4VDh6cmlVeHNQM3djbFluSVFtN25XNgo5VEl6S1hJOUgra3ZFbDNQQXZyU1VVRnFOSytLWlBEZFpQdnNvcFZ1dDNtc3ZQeWRnNGRlODgzd0EwSmQ1dWl1CjNKV0xBYm1hekhZT01taEQyRW9yc1VpWTZ3NXVJNy9rMld6bUgzelVGd250WDRNMjFYR3JrZm5IUUVhVHQvaHQKR3JsUWpQVzgwNzFwSm9UaVgxNURzd2VNTS9KZEtMV3FTaHVJdWY3YXNqcFUrSWRtQjU3U0g3NER0eTNEaTU4QwpHVldBQjEzc3BtZGpIbGhDeTlRZGxpQzhkUzVGai80SFRIdDJHYTBDREZLRVk0TnF3SGUvK0hqNmRWOTJrcmJHCmdaNkZRa2FId1ZrPQotLS0tLUVORCBDRVJUSUZJQ0FURS0tLS0tCg==
server
:
https://cls-acfx4pvj.ccs.tencent-cloud.com
name
:
local
contexts
:
-
context
:
cluster
:
local
user
:
admin
name
:
cls-acfx4pvj-context-default
current-context
:
cls-acfx4pvj-context-default
kind
:
Config
preferences
:
{}
users
:
-
name
:
admin
user
:
token
:
BIsuBv18csrBHVXClYZ4ln3izUYJt9Xa
\ No newline at end of file
src/main/resources/tke-cluster-ca.crt
0 → 100644
View file @
0584c7e7
-----BEGIN CERTIFICATE-----
MIIDZDCCAkygAwIBAgIIAiEo8goVaeYwDQYJKoZIhvcNAQELBQAwUDELMAkGA1UE
BhMCQ04xKjARBgNVBAoTCnRlbmNlbnR5dW4wFQYDVQQKEw5zeXN0ZW06bWFzdGVy
czEVMBMGA1UEAxMMY2xzLWFjZng0cHZqMB4XDTE5MDEwMzAzMDQ1MloXDTM5MDEw
MzAzMDQ1MlowUDELMAkGA1UEBhMCQ04xKjARBgNVBAoTCnRlbmNlbnR5dW4wFQYD
VQQKEw5zeXN0ZW06bWFzdGVyczEVMBMGA1UEAxMMY2xzLWFjZng0cHZqMIIBIjAN
BgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEA5RurKHR0nF2P26weSMaj+mmymw+l
A/81r5IwAQYiz1H4QOr+TWbf7tgblYsNzbiJNjNNzVDbCdbvHYhxK6UczbC8bhqq
jA8comp+dlCe6mwTBJ74p3O+JWn4RNcD+xrxurzhOFDVkkTkEcj06WOnh2OCsEZC
ByW3ZPXCjudo05JkMHWhE/pDfIa2ab16dYxfvIhsv8XqgQ2ovODo8H9iPfZC/VIx
jhQkOzmRndeEx/ZZbY9o1oOml1r9wftWZIsY2Xm64K4kT87afTF/qivx8GW9ppDy
orYVXgUQJVDG2b2YwFbWXvPwK6YbSU9GruJeRqfvIKi+wKtqC0LgZYrLUwIDAQAB
o0IwQDAOBgNVHQ8BAf8EBAMCAoQwHQYDVR0lBBYwFAYIKwYBBQUHAwIGCCsGAQUF
BwMBMA8GA1UdEwEB/wQFMAMBAf8wDQYJKoZIhvcNAQELBQADggEBAF/cc1tDfTHQ
x5rFjrPKyanq9bVof2JZ+2xbhzuok1SicbSptLbkHxT8zriUxsP3wclYnIQm7nW6
9TIzKXI9H+kvEl3PAvrSUUFqNK+KZPDdZPvsopVut3msvPydg4de883wA0Jd5uiu
3JWLAbmazHYOMmhD2EorsUiY6w5uI7/k2WzmH3zUFwntX4M21XGrkfnHQEaTt/ht
GrlQjPW8071pJoTiX15DsweMM/JdKLWqShuIuf7asjpU+IdmB57SH74Dty3Di58C
GVWAB13spmdjHlhCy9QdliC8dS5Fj/4HTHt2Ga0CDFKEY4NqwHe/+Hj6dV92krbG
gZ6FQkaHwVk=
-----END CERTIFICATE-----
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment