package com.oracle.poco.bbhelper.log;

import java.io.IOException;
import java.io.InputStream;
import java.util.logging.ConsoleHandler;
import java.util.logging.Level;
import java.util.logging.LogManager;
import java.util.logging.Logger;

import com.oracle.poco.bbhelper.exception.BbhelperException;

/**
 * このアプリケーションのために構成されたロガーを提供するためのユーティリティ・
 * クラスです。
 *
 * このアプリケーションで実装されるログ出力は、すべて本クラスを使用することを
 * 想定しています。
 *
 * @author hhayakaw
 *
 */
public class BbhelperLogger {

    /**
     * ロガーのプロパティファイルのパス
     */
    private static final String FILE_PATH_LOGGING_PROPERTIES =
            "logging.properties";
    /**
     * ロガーの名前: システムログ
     */
    private static final String LOGGER_NAME_SYSTEM =
            "com.oracle.bbhelper.log.system";
    /**
     * ロガーの名前: アクセスログ
     */
    private static final String LOGGER_NAME_ACCESS =
            "com.oracle.bbhelper.log.access";
    /**
     * ロガーの名前: デバッグログ
     */
    private static final String LOGGER_NAME_DEBUG =
            "com.oracle.bbhelper.log.debug";
    /**
     * ロガー本体: システムログ
     */
    private Logger SystemLogger;
    /**
     * ロガー本体: アクセスログ
     */
    private Logger AccessLogger;
    /**
     * ロガー本体: デバッグログ
     */
    private Logger DebugLogger;
    /**
     * 
     */
    private static BbhelperLogger instance = null;

    // uninstanciable
    private BbhelperLogger() {
        initInternal();
    }

    private void initInternal() {
        // TODO Logの出力先フォルダを作成する
        final InputStream in = this.getClass().getClassLoader().
                getResourceAsStream(FILE_PATH_LOGGING_PROPERTIES);
        if (in == null) {
            throw new IllegalStateException("Failed to load logging.properties.");
        }
        try {
            LogManager.getLogManager().readConfiguration(in);
            SystemLogger = Logger.getLogger(LOGGER_NAME_SYSTEM);
            SystemLogger.addHandler(new ConsoleHandler());
            SystemLogger.addHandler(new SystemLogFileHandler());
            AccessLogger = Logger.getLogger(LOGGER_NAME_ACCESS);
            AccessLogger.addHandler(new ConsoleHandler());
            AccessLogger.addHandler(new AccessLogFileHandler());
            DebugLogger = Logger.getLogger(LOGGER_NAME_DEBUG);
            DebugLogger.addHandler(new ConsoleHandler());
            DebugLogger.addHandler(new DebugLogFileHandler());
        } catch (SecurityException | IOException e) {
            throw new IllegalStateException(e);
        }
    }

    /**
     * ロガーを取得します。
     *
     * @return ロガー
     */
    public static BbhelperLogger getInstance() {
        if (instance == null) {
            instance = new BbhelperLogger();
        }
        return instance;
    }

    /**
     * @param sessionId
     */
    public void request(String sessionId) {
        // TODO: implement
        if (sessionId == null || sessionId.length() == 0) {
            return;
        }
        AccessLogger.info(sessionId);
    }

    /**
     * @param message
     */
    public void response(String message) {
        // TODO: implement
        if (message == null || message.length() == 0) {
            return;
        }
        AccessLogger.info(message);
    }

    /**
     * @param message
     */
    public void info(String message) {
        if (message == null || message.length() == 0) {
            // do nothing.
            return;
        }
        SystemLogger.info(message);
    }

    /**
     * @param message
     */
    public void severe(String message) {
        if (message == null || message.length() == 0) {
            // do nothing.
            return;
        }
        SystemLogger.severe(message);
    }

    /**
     * @param e
     */
    public void logBbhelperException(BbhelperException e) {
        if (e == null) {
            return;
        }
        logThrowable(e.getErrorDescription().getFullDescription(), e);
    }

    /**
     * @param t
     */
    public void logThrowable(String message, Throwable t) {
        if (t == null) {
            // do nothing.
            return;
        }
        SystemLogger.severe(message);
        DebugLogger.log(Level.SEVERE, message, t);
    }

    /**
     * @param message
     */
    public void debug(String message) {
        if (message == null || message.length() == 0) {
            // do nothing.
            return;
        }
        DebugLogger.fine(message);
    }

//    private String getStrackTraceString(Throwable t) {
//        StackTraceElement[] elements = t.getStackTrace();
//        StringBuffer buf = new StringBuffer();
//        Arrays.stream(elements).forEach(e -> {
//            buf.append(e.toString());
//            buf.append("\n");
//            });
//        return buf.toString();
//    }

}

@@ -32,16 +32,37 @@
 r.log;%0A%0A
+import java.io.File;%0A
 import j
@@ -1457,24 +1457,294 @@
 ODO 
-Log%E3%81%AE%E5%87%BA%E5%8A%9B%E5%85%88%E3%83%95%E3%82%A9%E3%83%AB%E3%83%80%E3%82%92%E4%BD%9C%E6%88%90%E3%81%99%E3%82%8B
+%E3%81%93%E3%81%AE%E5%88%9D%E6%9C%9F%E5%8C%96%E5%87%A6%E7%90%86%E3%81%AF%E3%80%81%E8%B5%B7%E5%8B%95%E6%99%82%E3%81%AB%E8%A1%8C%E3%81%AA%E3%82%8F%E3%82%8C%E3%82%8B%E3%82%88%E3%81%86%E3%81%AB%E3%81%99%E3%81%B9%E3%81%8D%0A        File logdir = new File(%22logs%22);%0A        if (!logdir.exists() %7C%7C !logdir.isDirectory()) %7B%0A            if (!logdir.mkdir()) %7B%0A                System.out.println(%22ERROR! : Can't make log directory.%22);%0A                System.exit(1);%0A            %7D%0A        %7D
 %0A   

Improve logging.