/* <copyright                                       */
/* notice="cics-lm-source-program"                  */
/* pids="CA0U"                                      */
/* years="2014"                                     */
/* crc="3516110616" >                               */
/* 	Licensed Materials - Property of IBM            */
/* 	CA0U                                            */
/* 	(C) Copyright IBM Corp. 2014 All Rights Reserved. */
/* 	US Government Users Restricted Rights - Use, duplication or disclosure restricted by GSA ADP Schedule Contract with IBM Corp. */
/* </copyright>                                     */
package com.ibm.cics.ucd;

import java.io.PrintWriter;
import java.io.StringWriter;
import java.text.SimpleDateFormat;
import java.util.Arrays;
import java.util.Date;
import java.util.logging.LogRecord;
import java.util.logging.Formatter;

public class Log4jLoggerFormatter extends Formatter {
	
	// <copyright 
	// notice="cics-lm-java-class" 
	// pids="CA0U" 
	// years="2014" 
	// crc="3516110616" > 
	static final String COPYRIGHT = "Licensed Materials - Property of IBM CA0U (c) Copyright IBM Corp. 2014 All Rights Reserved. US Government Users Restricted Rights - Use, duplication or disclosure restricted by GSA ADP Schedule Contract with IBM Corp."; //$NON-NLS-1$
	// </copyright> 

	private final static SimpleDateFormat timeFormat = new SimpleDateFormat("yyyy/MM/dd HH:mm:ss.SSS z");
	private final static String lineSeparator = getLineSeparatorProperty();

	private static String getLineSeparatorProperty () {
		String value;
		try {
			value = System.getProperty("line.separator");
		}
		catch (SecurityException ex) {
			value = "\n";
		}
		return value;
	}

	public String format(LogRecord record) {
		if (record.getThrown() != null) {
			return formatDate(record.getMillis()) + " [" + formatThread(record) + "] ! " + record.getSourceClassName() + "." + record.getSourceMethodName() + "()" + formatThrown(record.getThrown()) + lineSeparator;
		}
		else return formatDate(record.getMillis()) + " [" + formatThread(record) + "] " + record.getMessage() + " " + record.getSourceClassName() + "." + record.getSourceMethodName() + "()" + formatParameters(record.getParameters()) + lineSeparator;
	}

	private static String formatDate (long millis) {
		return timeFormat.format(new Date(millis));
	}
	
	private static String formatThread (LogRecord record) {
		return String.valueOf(record.getThreadID());
	}

	private static String formatParameters(Object[] parameters) {
		if (parameters != null) return " " + Arrays.asList(parameters);
		else return "";
	}

	private static String formatThrown (final Throwable throwable) {
		StringWriter stringWriter = new StringWriter();
		PrintWriter printWriter = new PrintWriter(stringWriter);
		for (Throwable cause = throwable; cause != null; cause = cause.getCause()) {
			cause.printStackTrace(printWriter);
		}
		printWriter.close();
		return " [" + throwable + "]" + lineSeparator + stringWriter;	
	}
}
