package owltools.ontologyrelease;

import java.io.File;
import java.text.DateFormat;
import java.text.SimpleDateFormat;
import java.util.Date;
import java.util.Vector;
import java.util.concurrent.ArrayBlockingQueue;
import java.util.concurrent.BlockingQueue;

import javax.swing.JOptionPane;

import org.apache.log4j.AppenderSkeleton;
import org.apache.log4j.Logger;
import org.apache.log4j.spi.LoggingEvent;
import org.semanticweb.owlapi.model.OWLOntologyFormat;

import owltools.ontologyrelease.gui.OboOntologyReleaseRunnerParameters;
import owltools.ontologyrelease.gui.ReleaseGuiMainFrame;

/**
 * GUI access for ontology release runner.
 */
public class OboOntologyReleaseRunnerGui {

	private final static Logger logger = Logger.getLogger(OboOntologyReleaseRunnerGui.class);
	
	// SimpleDateFormat is NOT thread safe
	// encapsulate as thread local
	private final static ThreadLocal<DateFormat> df = new ThreadLocal<DateFormat>(){

		@Override
		protected DateFormat initialValue() {
			return new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
		}
	};
	
	public static void main(String[] args) {
		
		Logger rootLogger = Logger.getRootLogger();
		final BlockingQueue<String> logQueue =  new ArrayBlockingQueue<String>(100);
		
		rootLogger.addAppender(new AppenderSkeleton() {
			
			public boolean requiresLayout() {
				return false;
			}
			
			public void close() {
				// do nothing
			}
			
			@Override
			protected void append(LoggingEvent event) {
				try {
					StringBuilder sb = new StringBuilder();
					sb.append(df.get().format(new Date(event.timeStamp)));
					sb.append(' ');
					sb.append(event.getLevel());
					sb.append(' ');
					sb.append(event.getRenderedMessage());
					logQueue.put(sb.toString());
				} catch (InterruptedException e) {
					logger.fatal("Interruped during wait for writing to the message panel.", e);
				}
			}
		});
		
		// Start GUI
		new ReleaseGuiMainFrameRunner(logQueue);
	}

	private static final class ReleaseGuiMainFrameRunner extends ReleaseGuiMainFrame {
		
		// generated
		private static final long serialVersionUID = -8690322825608397262L;
		
		private ReleaseGuiMainFrameRunner(BlockingQueue<String> logQueue) {
			super(logQueue);
		}
	
		@Override
		protected void executeRelease(final OboOntologyReleaseRunnerParameters parameters) {
			logger.info("Starting release manager process");
			disableReleaseButton();
			// execute the release in a separate Thread, otherwise the GUI might be blocked.
			Thread t = new Thread() {
				@Override
				public void run() {
					try {
						OWLOntologyFormat format = parameters.getFormat();
						String reasoner = parameters.getReasoner();
						boolean asserted = parameters.isAsserted();
						boolean simple = parameters.isSimple();
						Vector<String> paths = parameters.getPaths();
						File base = parameters.getBase();
						OboOntologyReleaseRunner oorr = new OboOntologyReleaseRunner();
						oorr.createRelease(format, reasoner, asserted, simple, paths, base);
						logger.info("Finished release manager process");
						JOptionPane.showMessageDialog(ReleaseGuiMainFrameRunner.this, "Finished making the release.");
					} catch (Exception e) {
						logger.error("Internal error: "+ e.getMessage(), e);
					} catch (Throwable e) {
						logger.fatal("Internal error: "+ e.getMessage(), e);
					}
					finally {
						enableReleaseButton();
					}
				}
			};
			t.start();
		}
	}
}

@@ -3169,21 +3169,25 @@
 %09%09%09%09
-logger.error(
+String message = 
 %22Int
@@ -3208,35 +3208,177 @@
 + e.getMessage()
-, e
+;%0A%09%09%09%09%09%09logger.error(message, e);%0A%09%09%09%09%09%09JOptionPane.showMessageDialog(ReleaseGuiMainFrameRunner.this, message, %22Error%22, JOptionPane.ERROR_MESSAGE
 );%0A%09%09%09%09%09%7D catch 
@@ -3395,37 +3395,41 @@
  e) %7B%0A%09%09%09%09%09%09
-logger.fatal(
+String message = 
 %22Internal er
@@ -3450,19 +3450,166 @@
 essage()
-, e
+;%0A%09%09%09%09%09%09logger.fatal(message, e);%0A%09%09%09%09%09%09JOptionPane.showMessageDialog(ReleaseGuiMainFrameRunner.this, message, %22FatalError%22, JOptionPane.ERROR_MESSAGE
 );%0A%09%09%09%09%09

add popup for errors