package com.platform.service;

import java.sql.Connection;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.sql.Statement;

import com.base.Custom4exception;
import com.base.CustomException;
import com.platform.entities.GatherOracleInfo;
import com.platform.entities.OracleConnectorParams;
import com.platform.oracle.OracleConnector;
import com.platform.utils.Configs;
import com.platform.utils.FileOperateHelper;

public class OracleExtractHelper {

	/**
	 * 判断dblink是否已经存在
	 * 
	 * @param conn
	 * @param linkName
	 *            dblink的名称
	 * @return
	 */
	private boolean hasSameNameDBLink(Connection conn, String linkName, String filePath) {
		boolean flag = false;
		String sql = "SELECT * FROM ALL_DB_LINKS WHERE DB_LINK='" + linkName+"'";
		ResultSet rSet = null;
		try {
			rSet = OracleConnector.getSQLExecResultSet(conn, sql, null);
			rSet.last();
			if (rSet.getRow() > 0)
				flag = true;
			FileOperateHelper
			.fileWrite(filePath, sql+ "\r\n"+"OK \r\n");
		} catch (Exception e) {
			FileOperateHelper
			.fileWrite(filePath, sql+ "\r\n"+ e.getMessage() + "\r\n，连接异常！ \r\n");
			new CustomException(Custom4exception.threadVolume_Oracle_Except, e, rSet);
		}
		return flag;
	}

	/**
	 * 创建dblink
	 * 
	 * @param conn 汇总库的连接
	 * @param oc 采集库
	 *            dblink连接参数实体
	 */
	public void createDBLink(Connection conn, OracleConnectorParams oc) {
		String linkName = "LINKTO" + oc.getName();
		String sql = "CREATE PUBLIC DATABASE LINK "
				+ linkName
				+ " CONNECT TO "
				+ oc.getUser()
				+ " IDENTIFIED BY "
				+ oc.getPassword()
				+ " USING \'(DESCRIPTION =(ADDRESS_LIST =(ADDRESS = (PROTOCOL = TCP)(HOST = "
				+ oc.getIp() + ")(PORT = " + oc.getPort()
				+ ")))(CONNECT_DATA =(SERVICE_NAME =" + oc.getDatabaseName()
				+ ")))\'";
		if (null != oc) {
			if (hasSameNameDBLink(conn, linkName, Configs.EXTRACT_LOG_LOCALTION + oc.getName())) { // 如果dblink已经存在,先删除dblink，在创建dblink
				String deleteSql = "DROP PUBLIC DATABASE LINK "
						+ linkName;
//				FileOperateHelper
//						.fileWrite(
//								Configs.EXTRACT_LOG_LOCALTION + oc.getName(),
//								deleteSql+"\r\n");
				if (OracleConnector.execOracleSQL(conn, deleteSql, Configs.EXTRACT_LOG_LOCALTION + oc.getName())) {
//					FileOperateHelper.fileWrite(Configs.EXTRACT_LOG_LOCALTION
//							+ oc.getName(), sql+"\r\n");
					OracleConnector.execOracleSQL(conn, sql, Configs.EXTRACT_LOG_LOCALTION + oc.getName());
				} else {
					Configs.CONSOLE_LOGGER.error("删除已有的DBLink失败,无法创建新的DBLink!");
					FileOperateHelper.fileWrite(Configs.EXTRACT_LOG_LOCALTION
							+ oc.getName(), "删除已有的DBLink失败,无法创建新的DBLink!"+"\r\n");
				}

			} else {
				// 否则，创建dblink
				OracleConnector.execOracleSQL(conn, sql, Configs.EXTRACT_LOG_LOCALTION + oc.getName());
//				FileOperateHelper.fileWrite(
//						Configs.EXTRACT_LOG_LOCALTION + oc.getName(), sql);
			}
		}
	}

	/**
	 * 创建表空间
	 * 
	 * @param conn 汇总库连接
	 * @param collectOracle 
	 * @param oc 汇总库信息
	 * @return
	 */
	public boolean createTableSpace(Connection conn, OracleConnectorParams collectOracle, GatherOracleInfo oc) {
		String tmpSql = "select TABLESPACE_NAME from dba_tablespaces where TABLESPACE_NAME = '"
				+ oc.getTableName() + "'";
		if (OracleConnector.execUpdateOracleSQL(conn, tmpSql, Configs.EXTRACT_LOG_LOCALTION + collectOracle.getName())) {
//			FileOperateHelper
//			.fileWrite(
//					Configs.EXTRACT_LOG_LOCALTION + oc.getName(),
//					tmpSql+"\r\n");
			return true;
		} else {
			String sql = "create tablespace " + oc.getTableName()
					+ " datafile '" + Configs.GATHER_TABLESPACE_PATH
					+ oc.getTableName() + ".dbf"
					+ "' size 512M autoextend on next 512M maxsize unlimited";
//			FileOperateHelper
//			.fileWrite(
//					Configs.EXTRACT_LOG_LOCALTION + oc.getName(),
//					sql+"\r\n");
			return OracleConnector.execOracleSQL(conn, sql, Configs.EXTRACT_LOG_LOCALTION + collectOracle.getName());
		}
	}

	/**
	 * 创建用户并授权
	 * 
	 * @param conn 汇总库连接
	 * @param oc  汇总库信息
	 */
	public void createUser(Connection conn, OracleConnectorParams oc, GatherOracleInfo totalOracle) {
		String strTUser = oc.getName() + totalOracle.getSuffix();
		
		String sql = "Create user " + strTUser + " default tablespace "
				+ totalOracle.getTableName() + " identified by "
				+ Configs.GATHER_TABLE_PASSWORD;
		String grantSql = "grant connect, resource, dba to " + strTUser;
		
		OracleConnector.execOracleSQL(conn, sql, Configs.EXTRACT_LOG_LOCALTION + oc.getName());
//		FileOperateHelper
//		.fileWrite(
//				Configs.EXTRACT_LOG_LOCALTION + oc.getName(),
//				sql+"\r\n");
		
		OracleConnector.execOracleSQL(conn, grantSql, Configs.EXTRACT_LOG_LOCALTION + oc.getName());
//		FileOperateHelper
//		.fileWrite(
//				Configs.EXTRACT_LOG_LOCALTION + oc.getName(),
//				grantSql+"\r\n");
	}

	/**
	 * 执行汇总操作
	 * 
	 * @param conn 汇总库连接
	 * @param oc 采集库
	 */
	public void extractColleDB(Connection conn, OracleConnectorParams oc, GatherOracleInfo totalOracle) {
		String strTUser = oc.getName() + totalOracle.getSuffix();
		String sql = "SELECT 'create table "
				+ strTUser
				+ ".J'|| substr(t.OWNER||'_'||t.TABLE_NAME,0,29)||' as select * from '||t.OWNER||'.'||t.TABLE_NAME||"
				+ "'@LINKTO"
				+ oc.getName()
				+ ";' FROM dba_tables@LINKTO"
				+ oc.getName()
				+ " t WHERE t.TABLESPACE_NAME NOT IN ('SYSTEM','SYSAUX')"
				+ " and t.owner||t.table_name not in (select owner||table_name from dba_tables@LINKTO"
				+ oc.getName() + " where 'data_type'='CLOB')";
		ResultSet rsSet = OracleConnector.getSQLExecResultSet(conn, sql, Configs.EXTRACT_LOG_LOCALTION + oc.getName());
//		FileOperateHelper
//		.fileWrite(
//				Configs.EXTRACT_LOG_LOCALTION + oc.getName(),
//				sql+"\r\n");
			try {
				while (rsSet.next()) {
					try {
						rsSet.getRow();
						String resultSql = rsSet.getString(1).replace(";", "");
						OracleConnector.execUpdateOracleSQL(conn, resultSql, Configs.EXTRACT_LOG_LOCALTION + oc.getName());
					} catch (SQLException e) {
						new CustomException(Custom4exception.threadVolume_Oracle_Except, e, rsSet.getString(1));
					}
				}
			} catch (SQLException e) {
				// TODO Auto-generated catch block
				e.printStackTrace();
			}

	}
	
	/** 测试是否能否连接上？
	 * @return true：能连接上
	 */
	public boolean testConnect(Connection conn) {
		String testSql = "select count(*) from user_tables";
		boolean flag = false;
		try {
			Statement statement = conn.createStatement();
			if(statement.executeUpdate(testSql) > 0)
				flag  = true;
		} catch (SQLException e) {
			flag = false;
			new CustomException(Custom4exception.OracleSQL_Except, e, testSql);
		}
		return flag;
	}
}
