You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
565 lines
20 KiB
565 lines
20 KiB
5 years ago
|
package com.fr.plugin.decision.utils;
|
||
|
|
||
|
import com.fr.data.core.db.ColumnInformation;
|
||
|
import com.fr.data.core.db.DBUtils;
|
||
|
import com.fr.data.impl.NameDatabaseConnection;
|
||
|
import com.fr.json.JSONArray;
|
||
|
import com.fr.json.JSONObject;
|
||
|
import com.fr.log.FineLoggerFactory;
|
||
|
import com.fr.stable.StringUtils;
|
||
|
import com.fr.web.utils.WebUtils;
|
||
|
|
||
|
import javax.servlet.http.HttpServletResponse;
|
||
|
import java.math.BigDecimal;
|
||
|
import java.sql.*;
|
||
|
import java.util.List;
|
||
|
import java.util.Map;
|
||
|
import java.util.regex.Matcher;
|
||
|
import java.util.regex.Pattern;
|
||
|
|
||
|
public class JdbcUtils {
|
||
|
|
||
|
public static Connection getConnection(String connection) {
|
||
|
NameDatabaseConnection db = new NameDatabaseConnection(connection);
|
||
|
try {
|
||
|
Connection conn = db.createConnection();
|
||
|
return conn;
|
||
|
} catch (Exception e) {
|
||
|
FineLoggerFactory.getLogger().error("HW_excel导入:" + connection + "数据连接创建失败");
|
||
|
}
|
||
|
return null;
|
||
|
}
|
||
|
|
||
|
public static String getCreateSql(int type, String tableName, JSONArray items){
|
||
|
String createSql = "";
|
||
|
switch (type){
|
||
|
case 1:
|
||
|
createSql = getOracleCreateSql(items,tableName);
|
||
|
break;
|
||
|
case 2:
|
||
|
createSql = getSqlServerCreateSql(items,tableName);
|
||
|
break;
|
||
|
case 3:
|
||
|
createSql = getMysqlCreateSql(items,tableName);
|
||
|
break;
|
||
|
case 4:
|
||
|
createSql = getPostGreCreateSql(items, tableName);
|
||
|
break;
|
||
|
case 5:
|
||
|
createSql = getSybaseCreateSql(items,tableName);
|
||
|
break;
|
||
|
}
|
||
|
FineLoggerFactory.getLogger().debug("HW_excel导入:建表语句为 " + createSql);
|
||
|
return createSql;
|
||
|
}
|
||
|
|
||
|
/*
|
||
|
mysql boolean 0/1
|
||
|
oracle char(1) 0/1 不允许为空
|
||
|
sqlServer bit 0/1
|
||
|
PostGre boolean 0/1/true/false
|
||
|
sybase bit 0/1 不允许为空
|
||
|
*/
|
||
|
|
||
|
private static String getMysqlCreateSql(JSONArray items, String tableName){
|
||
|
String sql = " ( ";
|
||
|
for (Object ja : items){
|
||
|
JSONObject item = new JSONObject(ja.toString());
|
||
|
String colname = "`" + item.getString("colName") + "`";
|
||
|
int colType = item.getInt("colType");
|
||
|
String colLen = item.getString("colLength");
|
||
|
String colTypeStr ;
|
||
|
switch (colType){
|
||
|
case 1:
|
||
|
colTypeStr = colname + " int,";
|
||
|
break;
|
||
|
case 3:
|
||
|
colTypeStr = colname + " boolean,";
|
||
|
break;
|
||
|
case 4:
|
||
|
colTypeStr = colname + " datetime,";
|
||
|
break;
|
||
|
case 5:
|
||
|
colTypeStr = colname + " decimal(" + colLen.split(",")[0]+","+ colLen.split(",")[1] + "),";
|
||
|
break;
|
||
|
default:
|
||
|
colTypeStr = colname + " varchar(" +colLen + "),";
|
||
|
break;
|
||
|
}
|
||
|
|
||
|
sql += colTypeStr;
|
||
|
}
|
||
|
return "create table "+ tableName + sql.substring(0,sql.length()-1) +" )" ;
|
||
|
}
|
||
|
|
||
|
private static String getSqlServerCreateSql(JSONArray items, String tableName){
|
||
|
String sql = " ( ";
|
||
|
for (Object ja : items){
|
||
|
JSONObject item = new JSONObject(ja.toString());
|
||
|
String colname = "[" + item.getString("colName") + "]" ;
|
||
|
int colType = item.getInt("colType");
|
||
|
String colLen = item.getString("colLength");
|
||
|
String colTypeStr ;
|
||
|
switch (colType){
|
||
|
case 1:
|
||
|
colTypeStr = colname + " int,";
|
||
|
break;
|
||
|
case 3:
|
||
|
colTypeStr = colname + " bit,";
|
||
|
break;
|
||
|
case 4:
|
||
|
colTypeStr = colname + " datetime,";
|
||
|
break;
|
||
|
case 5:
|
||
|
colTypeStr = colname + " decimal(" + colLen.split(",")[0] + "," + colLen.split(",")[1] + "),";
|
||
|
break;
|
||
|
default:
|
||
|
colTypeStr = colname + " varchar(" +colLen + "),";
|
||
|
break;
|
||
|
}
|
||
|
|
||
|
sql += colTypeStr;
|
||
|
}
|
||
|
return "create table "+ tableName + sql.substring(0,sql.length()-1) + " )" ;
|
||
|
}
|
||
|
|
||
|
|
||
|
private static String getOracleCreateSql(JSONArray items, String tableName){
|
||
|
String sql = " ( ";
|
||
|
for (Object ja : items){
|
||
|
JSONObject item = new JSONObject(ja.toString());
|
||
|
String colname = "\"" + item.getString("colName") + "\"";
|
||
|
int colType = item.getInt("colType");
|
||
|
String colLen = item.getString("colLength");
|
||
|
String colTypeStr ;
|
||
|
switch (colType){
|
||
|
case 1:
|
||
|
int len = Integer.parseInt(colLen) > 38 ? 38:Integer.parseInt(colLen);
|
||
|
colTypeStr = colname + " number(" + len + "),";
|
||
|
break;
|
||
|
case 3:
|
||
|
colTypeStr = colname + " char(1),";
|
||
|
break;
|
||
|
case 4:
|
||
|
colTypeStr = colname + " date,";
|
||
|
break;
|
||
|
case 5:
|
||
|
colTypeStr = colname + " decimal(" + colLen.split(",")[0] + "," + colLen.split(",")[1] + "),";
|
||
|
break;
|
||
|
default:
|
||
|
colTypeStr = colname + " varchar2(" +colLen + "),";
|
||
|
break;
|
||
|
}
|
||
|
|
||
|
sql += colTypeStr;
|
||
|
}
|
||
|
return "create table "+ tableName + sql.substring(0,sql.length()-1) + " )" ;
|
||
|
}
|
||
|
|
||
|
private static String getPostGreCreateSql(JSONArray items, String tableName){
|
||
|
String sql = " ( ";
|
||
|
for (Object ja : items){
|
||
|
JSONObject item = new JSONObject(ja.toString());
|
||
|
String colname = "\"" + item.getString("colName") + "\"";
|
||
|
int colType = item.getInt("colType");
|
||
|
String colLen = item.getString("colLength");
|
||
|
String colTypeStr ;
|
||
|
switch (colType){
|
||
|
case 1:
|
||
|
colTypeStr = colname + " integer,";
|
||
|
break;
|
||
|
case 3:
|
||
|
colTypeStr = colname + " boolean,";
|
||
|
break;
|
||
|
case 4:
|
||
|
colTypeStr = colname + " date,";
|
||
|
break;
|
||
|
case 5:
|
||
|
colTypeStr = colname + " decimal(" + colLen.split(",")[0] + ","+ colLen.split(",")[1] + "),";
|
||
|
break;
|
||
|
default:
|
||
|
colTypeStr = colname + " varchar(" + colLen + "),";
|
||
|
break;
|
||
|
}
|
||
|
|
||
|
sql += colTypeStr;
|
||
|
}
|
||
|
return "create table "+ tableName + sql.substring(0,sql.length()-1) + " )" ;
|
||
|
}
|
||
|
|
||
|
private static String getSybaseCreateSql(JSONArray items, String tableName){
|
||
|
String sql = " ( ";
|
||
|
for (Object ja : items){
|
||
|
JSONObject item = new JSONObject(ja.toString());
|
||
|
String colname = "[" + item.getString("colName") + "]" ;
|
||
|
int colType = item.getInt("colType");
|
||
|
String colLen = item.getString("colLength");
|
||
|
String colTypeStr ;
|
||
|
switch (colType){
|
||
|
case 1:
|
||
|
colTypeStr = colname + " int,";
|
||
|
break;
|
||
|
case 3:
|
||
|
colTypeStr = colname + " bit,";
|
||
|
break;
|
||
|
case 4:
|
||
|
colTypeStr = colname + " date,";
|
||
|
break;
|
||
|
case 5:
|
||
|
colTypeStr = colname + " decimal(" + colLen.split(",")[0] + "," + colLen.split(",")[1] + "),";
|
||
|
break;
|
||
|
default:
|
||
|
colTypeStr = colname + " varchar(" + colLen + "),";
|
||
|
break;
|
||
|
}
|
||
|
|
||
|
sql += colTypeStr;
|
||
|
}
|
||
|
return "create table "+ tableName + sql.substring(0,sql.length()-1) + " )" ;
|
||
|
}
|
||
|
|
||
|
public static String getInsertSql(String tableName, JSONArray items, int type){
|
||
|
String colStr = " (";
|
||
|
|
||
|
StringBuffer stringBuffer = new StringBuffer(" values (");
|
||
|
for (int i = 0, len = items.size(); i < len; i++) {
|
||
|
String colName = dealColName(items.getJSONObject(i).getString("colName"), type);
|
||
|
if (i == len - 1) {
|
||
|
colStr += colName + ")";
|
||
|
stringBuffer.append("?)");
|
||
|
} else {
|
||
|
colStr += colName + ",";
|
||
|
stringBuffer.append("?,");
|
||
|
}
|
||
|
}
|
||
|
|
||
|
FineLoggerFactory.getLogger().debug("HW_excel导入:插入语句为 " + "insert into " + tableName + colStr + stringBuffer.toString());
|
||
|
return "insert into " + tableName + colStr + stringBuffer.toString();
|
||
|
}
|
||
|
|
||
|
private static String dealColName(String colName, int type){
|
||
|
switch (type){
|
||
|
case 1:
|
||
|
case 4:
|
||
|
return "\"" + colName + "\"";
|
||
|
case 2:
|
||
|
case 5:
|
||
|
return "[" + colName + "]";
|
||
|
case 3:
|
||
|
return "`" + colName + "`";
|
||
|
}
|
||
|
return "";
|
||
|
}
|
||
|
|
||
|
public static String getDeleteSql(String tableName, int type){
|
||
|
return "delete from " + tableName;
|
||
|
}
|
||
|
|
||
|
public static String getDropSql(String tableName){
|
||
|
return "drop table " + tableName;
|
||
|
}
|
||
|
|
||
|
public static String getQuerySql(String tableName, int type, String schema){
|
||
|
switch (type){
|
||
|
case 1:
|
||
|
return "select * from " + tableName + " rownum < 5000";
|
||
|
case 2:
|
||
|
case 5:
|
||
|
return "select top(5000) * from " + tableName;
|
||
|
case 3:
|
||
|
case 4:
|
||
|
return "select * from " + tableName + " limit 0,5000";
|
||
|
default:
|
||
|
FineLoggerFactory.getLogger().debug("HW_excel导入:getQuerySql返回为空");
|
||
|
return "";
|
||
|
}
|
||
|
}
|
||
|
|
||
|
public static String getQueryColSql(String tableName, int type, String schema){
|
||
|
return "select * from " + tableName + " where 1=2";
|
||
|
}
|
||
|
|
||
|
/*
|
||
|
oracle:1
|
||
|
sqlserver:2
|
||
|
mysql:3
|
||
|
postgresql:4
|
||
|
sybase:5
|
||
|
*/
|
||
|
public static int getConnectionType(Connection conn) throws SQLException {
|
||
|
String DatabaseProductName = conn.getMetaData().getDatabaseProductName().trim().toUpperCase();
|
||
|
FineLoggerFactory.getLogger().debug("HW_excel导入:数据库 ProductName 为: " + DatabaseProductName);
|
||
|
|
||
|
if (StringUtils.contains(DatabaseProductName,"ORACLE")){
|
||
|
return 1;
|
||
|
}
|
||
|
if (StringUtils.contains(DatabaseProductName,"SQL SERVER")) {
|
||
|
return 2;
|
||
|
}
|
||
|
if (StringUtils.contains(DatabaseProductName,"MYSQL")){
|
||
|
return 3;
|
||
|
}
|
||
|
if (StringUtils.contains(DatabaseProductName,"POSTGRE")){
|
||
|
return 4;
|
||
|
}
|
||
|
if (StringUtils.contains(DatabaseProductName,"SYBASE")){
|
||
|
return 5;
|
||
|
}
|
||
|
|
||
|
return 0;
|
||
|
}
|
||
|
|
||
|
private static void dealPrepareStatement(PreparedStatement pstm, String value, int index, int type, int databaseType) throws SQLException {
|
||
|
try {
|
||
|
switch (type) {
|
||
|
case 1:
|
||
|
pstm.setInt(index, Double.valueOf(value).intValue());
|
||
|
break;
|
||
|
case 3:
|
||
|
switch (value.toUpperCase()) {
|
||
|
case "TRUE":
|
||
|
case "1":
|
||
|
if (databaseType == 4){
|
||
|
pstm.setBoolean(index, true);
|
||
|
} else {
|
||
|
pstm.setInt(index, 1);
|
||
|
} break;
|
||
|
case "FALSE":
|
||
|
case "0":
|
||
|
if (databaseType == 4){
|
||
|
pstm.setBoolean(index, false);
|
||
|
} else {
|
||
|
pstm.setInt(index, 0);
|
||
|
} break;
|
||
|
}
|
||
|
break;
|
||
|
case 4:
|
||
|
java.sql.Date date = java.sql.Date.valueOf(value);
|
||
|
pstm.setDate(index, date);
|
||
|
break;
|
||
|
case 5:
|
||
|
pstm.setFloat(index, Float.parseFloat(value));
|
||
|
break;
|
||
|
default:
|
||
|
if (isNumeric(value)){
|
||
|
pstm.setString(index, value.split("\\.")[0]);
|
||
|
} else {
|
||
|
pstm.setString(index, value);
|
||
|
}
|
||
|
}
|
||
|
} catch (Exception e){
|
||
|
pstm.setString(index, value);
|
||
|
}
|
||
|
}
|
||
|
|
||
|
|
||
|
/**
|
||
|
* 匹配是否为数字
|
||
|
* @param str 可能为中文,也可能是-19162431.1254,不使用BigDecimal的话,变成-1.91624311254E7
|
||
|
*/
|
||
|
public static boolean isNumeric(String str) {
|
||
|
// 该正则表达式可以匹配所有的数字 包括负数
|
||
|
Pattern pattern = Pattern.compile("-?[0-9]+(\\.0)");
|
||
|
String bigStr;
|
||
|
try {
|
||
|
bigStr = new BigDecimal(str).toString();
|
||
|
} catch (Exception e) {
|
||
|
return false;//异常 说明包含非数字。
|
||
|
}
|
||
|
|
||
|
Matcher isNum = pattern.matcher(bigStr); // matcher是全匹配
|
||
|
if (!isNum.matches()) {
|
||
|
return false;
|
||
|
}
|
||
|
return true;
|
||
|
}
|
||
|
|
||
|
/**
|
||
|
* 把从数据库中查询出来的 ResultSetMetaData 转为 JSONArray
|
||
|
*/
|
||
|
public static JSONArray formatRsToTableData(ResultSet rs) throws Exception{
|
||
|
ResultSetMetaData md = rs.getMetaData();
|
||
|
|
||
|
JSONArray jsonArray = new JSONArray();
|
||
|
while(rs.next()) {
|
||
|
JSONArray rowArray = new JSONArray();
|
||
|
for(int i=1; i<=md.getColumnCount(); i++) {
|
||
|
JSONObject jsonObject = new JSONObject();
|
||
|
jsonObject.put("text", rs.getString(i));
|
||
|
rowArray.add(jsonObject);
|
||
|
}
|
||
|
jsonArray.add(rowArray);
|
||
|
}
|
||
|
return jsonArray;
|
||
|
}
|
||
|
|
||
|
public static JSONArray formatRs2ColAttr(ColumnInformation[] columnInformations){
|
||
|
JSONArray colsAttr = JSONArray.create();
|
||
|
for(int i = 0; i < columnInformations.length; i++) {
|
||
|
JSONObject colAttr = JSONObject.create();
|
||
|
colAttr.put("colType", columnInformations[i].getColumnType());
|
||
|
colAttr.put("colName", columnInformations[i].getColumnName());
|
||
|
colAttr.put("colLength", columnInformations[i].getColumnSize());
|
||
|
colAttr.put("id",i+1);
|
||
|
colAttr.put("excelCol","");
|
||
|
colsAttr.add(colAttr);
|
||
|
}
|
||
|
return colsAttr;
|
||
|
}
|
||
|
|
||
|
public static void addPrimaryKeyColAttr(JSONArray colsAttr, List<String> primaryKeyCol) {
|
||
|
for (Object col:colsAttr) {
|
||
|
String colName = ((JSONObject) col).getString("colName");
|
||
|
if (primaryKeyCol.contains(colName)) {
|
||
|
((JSONObject) col).put("primaryKey", true);
|
||
|
} else {
|
||
|
((JSONObject) col).put("primaryKey", false);
|
||
|
}
|
||
|
}
|
||
|
}
|
||
|
|
||
|
public static JSONArray formatRsToJsonArray(ResultSet rs) throws Exception{
|
||
|
ResultSetMetaData md = rs.getMetaData();
|
||
|
|
||
|
JSONArray jsonArray = new JSONArray();
|
||
|
while(rs.next()) {
|
||
|
JSONObject jsonObject = new JSONObject();
|
||
|
for(int i=1; i<=md.getColumnCount(); i++) {
|
||
|
jsonObject.put(md.getColumnName(i), rs.getString(i));
|
||
|
}
|
||
|
jsonArray.add(jsonObject);
|
||
|
}
|
||
|
return jsonArray;
|
||
|
}
|
||
|
|
||
|
|
||
|
public static int changeStr2Type(String typeStr , int connType, int scale){
|
||
|
int type;
|
||
|
switch (typeStr.toUpperCase()){
|
||
|
case "INT":
|
||
|
case "INT4":
|
||
|
case "INTEGER":
|
||
|
type = 1; break;
|
||
|
case "BIT":
|
||
|
case "CHAR":
|
||
|
case "BOOL":
|
||
|
case "TINYINT":
|
||
|
case "BOOLEAN":
|
||
|
type = 3; break;
|
||
|
case "DATE":
|
||
|
case "DATETIME":
|
||
|
type = 4; break;
|
||
|
case "DECIMAL":
|
||
|
case "NUMERIC":
|
||
|
type = 5; break;
|
||
|
case "NUMBER": // oracle 整形和小数都是 number 类型,需要判断 scale
|
||
|
if (scale == 0) {
|
||
|
type = 1; break;
|
||
|
} else {
|
||
|
type = 5; break;
|
||
|
}
|
||
|
|
||
|
default:
|
||
|
type = 2;
|
||
|
}
|
||
|
return type;
|
||
|
}
|
||
|
|
||
|
public static int pstsExecBatch(PreparedStatement psts, JSONArray items, Map<String, List> values, int type) throws SQLException {
|
||
|
int count = 0;
|
||
|
for (int j =0; j< values.get(items.getJSONObject(0).get("colName")).size(); j++) {
|
||
|
for (int k=0; k<items.size();k++){
|
||
|
dealPrepareStatement(
|
||
|
psts,
|
||
|
values.get(items.getJSONObject(k).getString("colName")).get(j).toString(),
|
||
|
k+1,
|
||
|
items.getJSONObject(k).getInt("colType"),
|
||
|
type
|
||
|
);
|
||
|
}
|
||
|
count ++ ;
|
||
|
|
||
|
// sybase 执行 executeBatch 效率异常低,改用 execute
|
||
|
if(type == 5){
|
||
|
psts.execute();
|
||
|
continue;
|
||
|
}
|
||
|
|
||
|
psts.addBatch();
|
||
|
if( j!=0 && j%10000==0 ){
|
||
|
psts.executeBatch();
|
||
|
psts.clearBatch();
|
||
|
System.out.println("HW_excel导入:pstsExecBatch 批量执行完成");
|
||
|
FineLoggerFactory.getLogger().info("HW_excel导入:pstsExecBatch 批量执行完成");
|
||
|
}
|
||
|
}
|
||
|
|
||
|
System.out.println("HW_excel导入:pstsExecBatch 执行完成");
|
||
|
FineLoggerFactory.getLogger().info("HW_excel导入:pstsExecBatch 执行完成");
|
||
|
if(type == 5){
|
||
|
return count;
|
||
|
}
|
||
|
|
||
|
psts.executeBatch();
|
||
|
psts.clearBatch();
|
||
|
return count;
|
||
|
}
|
||
|
|
||
|
|
||
|
// 建表操作
|
||
|
public static int execCreatTable(String connection, String tableName, JSONArray items, HttpServletResponse res){
|
||
|
String createSql;
|
||
|
Statement smt = null;
|
||
|
Connection conn = getConnection(connection);
|
||
|
int line = -1;
|
||
|
|
||
|
try {
|
||
|
smt = conn.createStatement();
|
||
|
int type = JdbcUtils.getConnectionType(conn);
|
||
|
createSql = JdbcUtils.getCreateSql(type, tableName, items);
|
||
|
System.out.println("HW_excel导入:建表语句为 " + createSql);
|
||
|
FineLoggerFactory.getLogger().debug("HW_excel导入:建表语句为 " + createSql);
|
||
|
line = smt.executeUpdate(createSql);
|
||
|
|
||
|
} catch (Exception e){
|
||
|
e.printStackTrace();
|
||
|
System.out.println("HW_excel导入:建表执行异常!");
|
||
|
FineLoggerFactory.getLogger().info("HW_excel导入:建表执行异常!");
|
||
|
try {
|
||
|
WebUtils.printAsJSON(res,new JSONObject().put("status","fail").put("errorText","表创建失败:" + e.getLocalizedMessage()));
|
||
|
} catch (Exception e1) {
|
||
|
e1.printStackTrace();
|
||
|
}
|
||
|
} finally {
|
||
|
closeConn(conn, null, smt);
|
||
|
}
|
||
|
|
||
|
return line;
|
||
|
}
|
||
|
|
||
|
public static void closeConn(Connection conn, PreparedStatement psts, Statement smt){
|
||
|
if(conn != null){
|
||
|
DBUtils.closeConnection(conn);
|
||
|
}
|
||
|
if(psts != null){
|
||
|
DBUtils.close(psts);
|
||
|
}
|
||
|
if(smt != null){
|
||
|
DBUtils.close(smt);
|
||
|
}
|
||
|
}
|
||
|
|
||
|
public static boolean isHive(Connection conn){
|
||
|
try {
|
||
|
String DatabaseProductName = conn.getMetaData().getDatabaseProductName().trim().toUpperCase();
|
||
|
FineLoggerFactory.getLogger().debug("isHive:" + DatabaseProductName);
|
||
|
if (StringUtils.contains(DatabaseProductName,"HIVE")){
|
||
|
return true;
|
||
|
}
|
||
|
} catch (SQLException e) {
|
||
|
e.printStackTrace();
|
||
|
}
|
||
|
return false;
|
||
|
}
|
||
|
}
|