/**
 * Copyright 2008-2009. Chongqing Communications Industry Services Co.,Ltd Information Technology Branch. All rights reserved. <a>http://www.crunii.com</a>
 */
package com.crunii.micro.ds.single.druid;

import com.alibaba.druid.pool.DruidDataSource;
import com.alibaba.druid.spring.boot.autoconfigure.DruidDataSourceBuilder;
import com.alibaba.druid.spring.boot.autoconfigure.properties.DruidStatProperties;
import com.alibaba.druid.spring.boot.autoconfigure.stat.DruidFilterConfiguration;
import com.alibaba.druid.spring.boot.autoconfigure.stat.DruidSpringAopConfiguration;
import com.alibaba.druid.spring.boot.autoconfigure.stat.DruidStatViewServletConfiguration;
import com.alibaba.druid.spring.boot.autoconfigure.stat.DruidWebStatFilterConfiguration;
import com.crunii.micro.common.constants.DSConstants;
import com.crunii.micro.domain.common.jdbc.BaseJdbcTemplate;
import com.crunii.micro.domain.common.jdbc.BaseNPJdbcTemplate;
import com.crunii.micro.ds.single.druid.filter.ExecSqlFilter;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Qualifier;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.boot.autoconfigure.condition.ConditionalOnExpression;
import org.springframework.boot.autoconfigure.condition.ConditionalOnProperty;
import org.springframework.boot.autoconfigure.jdbc.DataSourceProperties;
import org.springframework.boot.context.properties.ConfigurationProperties;
import org.springframework.boot.context.properties.EnableConfigurationProperties;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.context.annotation.Import;

import javax.sql.DataSource;

/**
 * <pre>
 *  #数据库类型暂时支持PostgreSQL和MySQL(TeleDB)
 *  com.crunii.micro.common.constants.DSConstants
 * 	DATABASE_MYSQL = "MySQL";
 * 	DATABASE_POSTGRESQL = "PostgreSQL";
 * 	DATABASE_ORACLE = "Oracle";
 * 	DATABASE_INFORMIX = "Informix";
 *  DATABASE_UNKNOWN = "UNKNOWN";
 * </pre>
 *
 * @author 田平 create 2018年5月29日下午3:04:37
 */
@Configuration
@EnableConfigurationProperties({ DruidStatProperties.class, DataSourceProperties.class })
@Import({ DruidSpringAopConfiguration.class,
		DruidStatViewServletConfiguration.class,
		DruidWebStatFilterConfiguration.class,
		DruidFilterConfiguration.class })
@ConditionalOnProperty(name = "dbtype.main", havingValue = DSConstants.DATABASE_POSTGRESQL)
@ConditionalOnExpression("#{'${druid." + DSConstants.DB_MAIN + ".postgresql.username:null}'!='null'}")
@Slf4j
public class MainDSPostgresqlConfiguration {

	@Value("${spring.enableSqlLog:false}")
	private boolean globalEnableSqlLog;

	@Value("${druid." + DSConstants.DB_MAIN + ".enableSqlLog:false}")
	private boolean enableSqlLog;

	@Value("${spring.enableEncryptCol:false}")
	private boolean enableEncryptColGlobal;

	@Value("${druid." + DSConstants.DB_MAIN + ".enableEncryptCol:false}")
	private boolean enableEncryptCol;

	@Autowired(required = false)
	private ExecSqlFilter execSqlFilter;

	@Bean(name = DSConstants.DB_MAIN + "DS")
	@ConfigurationProperties("druid." + DSConstants.DB_MAIN + ".postgresql")
	public DataSource regDS() {
		DruidDataSource dataSource = DruidDataSourceBuilder.create().build();
		//全量sql日志记录
		if (globalEnableSqlLog && enableSqlLog) {
			dataSource.getProxyFilters().add(execSqlFilter);
		}
		dataSource.setName(DSConstants.DB_MAIN + DSConstants.POOL_NAME_SUFFIX);
		return dataSource;
	}

	@Bean(DSConstants.DB_MAIN + "JT")
	@Qualifier(DSConstants.DB_MAIN + "JT")
	public BaseJdbcTemplate regBaseJdbcTemplate() {
		BaseJdbcTemplate template = new BaseJdbcTemplate(regDS(), DSConstants.DATABASE_POSTGRESQL);
		if (enableEncryptColGlobal && enableEncryptCol) {
			template.setEnableEncrypt(true);
		}
		return template;
	}

	@Bean(DSConstants.DB_MAIN + "NPJT")
	@Qualifier(DSConstants.DB_MAIN + "NPJT")
	public BaseNPJdbcTemplate regBaseNPJdbcTemplate() {
		BaseNPJdbcTemplate template = new BaseNPJdbcTemplate(regDS(), DSConstants.DATABASE_POSTGRESQL);
		if (enableEncryptColGlobal && enableEncryptCol) {
			template.setEnableEncrypt(true);
		}
		return template;
	}

}
