package org.postgresforest.tool.lib;

import java.sql.*;
import org.postgresforest.tool.Logger;
import org.postgresforest.tool.lib.GSCdata;

public class Config {
	private GSCdata gsc = null;

	public static final String DEFAULT_CONFIG_NAME = "FOREST_DEFAULT_CONFIG";

	public static final int PARTMODE_PART   = 0;
	public static final int PARTMODE_NOPART = 1;
	public static final int SYNCMODE_SYNC   = 1;
	public static final int SYNCMODE_NOSYNC = 0;
	public static final int CONN_RR    = 0;
	public static final int CONN_FIXED = 1;

	private String configId           = Config.DEFAULT_CONFIG_NAME;
	private String description        = "Default Configuration";
	private int cacheRefresh          = 30;
	private int retryCount            = 3;
	private int defectTimeout         = 30;
	private int distributedConnection = 1;
	private int partitionMode         = 0;
	private int synchronizeMode       = 1;

	/**
	 * コンストラクタ。
	 *
	 * 指定されたCONFIG IDでGSCから読み込む。
	 * 既存のCONFIGが存在していれば、その設定を読み込み、
	 * 存在していなければデフォルト値で作成する。
	 *
	 * @param gsc GSCdataオブジェクト
	 * @param configId CONFIG名（CONIFIG ID）
	 */
	public Config(GSCdata gsc, String configId)
	{
		this.gsc = gsc;
		this.configId = configId;

		try {
			String sql = "SELECT description,cache_reflesh,retry_count,defect_timeout,distributed_connection,pertition_mode,syncronize_mode,update_date FROM forest_config WHERE configid='" + configId + "'";

			ResultSet rs = gsc.executeQueryGSC(sql);
			if ( rs.next() )
			{
				int j = 1;
				this.description           = rs.getString(j++);
				this.cacheRefresh          = rs.getInt(j++);
				this.retryCount            = rs.getInt(j++);
				this.defectTimeout         = rs.getInt(j++);
				this.distributedConnection = rs.getInt(j++);
				this.partitionMode         = rs.getInt(j++);
				this.synchronizeMode       = rs.getInt(j++);
			}
		}
		catch (Exception e)
		{
			Logger.error(e.getMessage());
		}
	}

	/**
	 * コンストラクタ。
	 *
	 * 指定されたCONFIG ID、設定値でConfigオブジェクトを生成する。
	 *
	 * @param gsc GSCdataオブジェクト
	 * @param configId CONFIG名（CONIFIG ID）
	 * @param desc CONFIG設定についての説明
	 * @param cache_refresh キャッシュのリフレッシュサイクル（秒）
	 * @param retry_count 検索実行時に失敗した場合の最大リトライ回数
	 * @param defect_timeout クエリ処理時のタイムアウト検出時間（秒）
	 * @param distributed_connection 負荷分散時のコネクション振り分け方法（ラウンドロビン：0、固定接続：1）
     * @param partition_mode パーティションモード設定（パーティションモード：1、非パーティションモード：0）
     * @param sync_mode 更新同期モード設定（更新同期モード:1、更新非同期モード：2）
	 */
	public Config(GSCdata gsc, String configId, String desc,
				  int cache_refresh, int retry_count,
				  int defect_timeout, int distributed_connection,
				  int partition_mode, int sync_mode)
	{
		this.gsc                   = gsc;

		this.configId              = configId;
		this.description           = desc;
		this.cacheRefresh          = cache_refresh;
		this.retryCount            = retry_count;
		this.defectTimeout         = defect_timeout;
		this.distributedConnection = distributed_connection;
		this.partitionMode         = partition_mode;
		this.synchronizeMode       = sync_mode;
	}

	public String getId()
	{
		return configId;
	}

	public boolean setId(String configId)
	{
		String oldconfig = this.configId;

		this.configId = configId;

		return updateGSC("configid", configId, oldconfig);
	}

	public String getDescription()
	{
		return description;
	}

	public boolean setDescription(String desc)
	{
		this.description = desc;

		return updateGSC("description", desc);
	}

	public int getCacheRefresh()
	{
		return cacheRefresh;
	}

	public boolean setCacheRefresh(int refresh)
	{
		cacheRefresh = refresh;

		return updateGSC("cache_reflesh", refresh);
	}

	public int getRetryCount()
	{
		return retryCount;
	}

	public boolean setRetryCount(int retry)
	{
		retryCount = retry;

		return updateGSC("retry_count", retry);
	}

	public int getDefectTimeout()
	{
		return defectTimeout;
	}

	public boolean setDefectTimeout(int timeout)
	{
		this.defectTimeout = timeout;

		return updateGSC("defect_timeout", timeout);
	}

	public int getDistributedConnection()
	{
		return distributedConnection;
	}

	public boolean setDistributedConnection(int dist)
	{
		this.distributedConnection = dist;

		return updateGSC("distributed_connection", dist);
	}

	public int getPartitionMode()
	{
		return partitionMode;
	}

	public boolean setPartitionMode(int mode)
	{
		this.partitionMode = mode;

		return updateGSC("pertition_mode", mode);
	}

	public int getSynchronizeMode()
	{
		return synchronizeMode;
	}

	public boolean setSynchronizeMode(int mode)
	{
		this.synchronizeMode = mode;

		return updateGSC("syncronize_mode", mode);
	}

	public Config clone2()
		throws NotImplementedException
	{
		throw new NotImplementedException();
	}

	public boolean equals(Config cmp)
		throws NotImplementedException
	{
		throw new NotImplementedException();		
	}

	/*
	 * GSCを更新
	 */
	private boolean updateGSC(String param, int value)
	{
		return updateGSC(param, ""+value);
	}

	private boolean updateGSC(String param, String value)
	{
		return updateGSC(param, value, this.configId);
	}

	private boolean updateGSC(String param, String value, String configId)
	{
		try {
			gsc.executeUpdateGSC("UPDATE forest_config SET " + param + "='" + value + "',update_date=now() WHERE configid='" + configId + "'");
		}
		catch (Exception e)
		{
			Logger.error(e.getMessage());
			return false;
		}
		return true;
	}

}
