/*
 * blancoDb
 * Copyright (C) 2004-2005 Yasuo Nakanishi
 * 
 * This library is free software; you can redistribute it and/or
 * modify it under the terms of the GNU Lesser General Public
 * License as published by the Free Software Foundation; either
 * version 2.1 of the License, or (at your option) any later version.
 */
package blanco.db.collector;

import java.sql.DatabaseMetaData;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.util.ArrayList;
import java.util.Hashtable;
import java.util.List;
import java.util.Map;

import blanco.db.conf.BlancoDbDatabaseConnectionSettingDef;
import blanco.ig.tool.ConsolePrinter;

/**
 * @author Yasuo Nakanishi
 */
public class DatabaseService {
    private BlancoDbDatabaseConnection _connection = null;

    private BlancoDbDatabaseConnectionSettingDef _jdbcSetting = null;

    private DatabaseMetaData _databaseMetadata = null;

    private ConsolePrinter _printer = ConsolePrinter.get();

    public DatabaseService(BlancoDbDatabaseConnectionSettingDef setting,
            BlancoDbDatabaseConnection conn) {
        _jdbcSetting = setting;
        _connection = conn;
    }

    public DatabaseMetaData getDatabaseMetaData() throws SQLException {
        if (_databaseMetadata == null) {
            _databaseMetadata = _connection.getConnection().getMetaData();
        }
        return _databaseMetadata;
    }

    public List getTableNameList() throws SQLException {
        List result = new ArrayList();
        ResultSet resultSet = null;

        try {
            // 2005.04.15 t.iga 変更。
            // Oracleの場合には、ユーザ名をスキーマ名として与える必要がある。
            // これを行わないと、システムテーブルを含む全てのテーブルを取得してしまう。
            resultSet = getDatabaseMetaData().getTables(null,
                    _jdbcSetting.getSchema(), null, null);
            while (resultSet.next()) {
                if (resultSet.getString("TABLE_TYPE").equals("TABLE")) {
                    result.add(resultSet.getString("TABLE_NAME"));
                }
            }
        } finally {
            if (resultSet != null) {
                resultSet.close();
            }
        }
        return result;
    }

    public String getCatalog() throws SQLException {
        return _connection.getConnection().getCatalog();
    }

    public BlancoDbDatabaseConnectionSettingDef getJdbcSetting() {
        return _jdbcSetting;
    }

    public BlancoDbDatabaseConnection getConnection() {
        return _connection;
    }

    public final Map getPrimaryKeyMap(String tableName) throws SQLException {
        //assert _connection != null;

        Map result = new Hashtable();
        String catalog = getCatalog();

        ResultSet resultSet = null;
        String columnName = "";
        Short sequence = null;
        try {
            resultSet = getDatabaseMetaData().getPrimaryKeys(catalog, null,
                    tableName);
            while (resultSet.next()) {
                columnName = resultSet.getString("COLUMN_NAME");
                sequence = new Short(resultSet.getShort("KEY_SEQ"));
                result.put(columnName, sequence);
            }
        } finally {
            if (resultSet != null) {
                resultSet.close();
            }
        }
        return result;
    }

    public void setConnection(BlancoDbDatabaseConnection conn) {
        _connection = conn;
    }

    public PreparedStatement createStatement(String sql) throws SQLException {
        return _connection.getConnection().prepareStatement(sql);
    }
}