/* This Source Code Form is subject to the terms of the Mozilla Public
 * License, v. 2.0. If a copy of the MPL was not distributed with this
 * file, You can obtain one at http://mozilla.org/MPL/2.0/.
 */
package fr.hhdev.ocelot.messaging;

import fr.hhdev.ocelot.Constants;
import java.io.IOException;
import java.io.StringReader;
import java.util.Arrays;
import java.util.Collections;
import java.util.Objects;
import javax.json.Json;
import javax.json.JsonObject;
import javax.json.JsonReader;

/**
 *
 * @author hhfrancois
 */
public class Fault {

	private final Throwable throwable;
	final private int stacktracelength;
	protected String message = null;
	protected String classname = null;

	public Fault(Throwable t, int stacktracelength) {
		this.throwable = t;
		if (t != null) {
			this.message = t.getMessage();
			this.classname = t.getClass().getName();
		}
		this.stacktracelength = stacktracelength;
	}

	public String getMessage() {
		return message;
	}

	public String getClassname() {
		return classname;
	}

	public StackTraceElement[] getStacktrace() {
		if (throwable != null && stacktracelength > 0) {
			StackTraceElement[] stackTraces = throwable.getStackTrace();
			return Arrays.copyOf(stackTraces, Math.min(stackTraces.length, stacktracelength));
		}
		return new StackTraceElement[]{};
	}

	public Throwable getThrowable() {
		return throwable;
	}

	/**
	 * Fault json format : {"message":"","classname":"","stacktrace":["","",""]}
	 *
	 * @param json
	 * @return
	 * @throws IOException
	 */
	public static Fault createFromJson(String json) throws IOException {
		Fault fault = new Fault(null, 0);
		try (JsonReader reader = Json.createReader(new StringReader(json))) {
			JsonObject root = reader.readObject();
			fault.message = root.getString(Constants.Message.Fault.MESSAGE);
			fault.classname = root.getString(Constants.Message.Fault.CLASSNAME);
		}
		return fault;
	}

	public String toJson() {
		StackTraceElement[] stacktraceElt = getStacktrace();
		String stacktrace = String.format(Arrays.toString(Collections.nCopies(stacktraceElt.length, "\"%s\"").toArray()), (Object[]) stacktraceElt);
		String json = String.format("{\"%s\":\"%s\",\"%s\":\"%s\",\"%s\":%s}",
				  Constants.Message.Fault.CLASSNAME, this.classname,
				  Constants.Message.Fault.MESSAGE, this.message,
				  Constants.Message.Fault.STACKTRACE, stacktrace);
		return json;
	}

	@Override
	public String toString() {
		return toJson();
	}

	@Override
	public int hashCode() {
		int hash = 5;
		hash = 29 * hash + Objects.hashCode(this.message);
		hash = 29 * hash + Objects.hashCode(this.classname);
		return hash;
	}

	@Override
	public boolean equals(Object obj) {
		if (obj == null) {
			return false;
		}
		if (getClass() != obj.getClass()) {
			return false;
		}
		final Fault other = (Fault) obj;
		return Objects.equals(this.classname, other.classname);
	}

}

@@ -1071,31 +1071,21 @@
 %0D%0A%09p
-ublic StackTraceElement
+rivate String
 %5B%5D g
@@ -1226,41 +1226,16 @@
 %0A%09%09%09
-return Arrays.copyOf(stackTraces,
+int nb =
  Mat
@@ -1281,96 +1281,135 @@
 gth)
-)
 ;%0D%0A%09%09
-%7D%0D%0A%09%09return new StackTraceElement%5B%5D%7B%7D;%0D%0A%09%7D%0D%0A%0D%0A%09public Throwable getThrowable() %7B
+%09String%5B%5D result = new String%5Bnb%5D;%0D%0A%09%09%09for (int i = 0; i %3C nb; i++) %7B%0D%0A%09%09%09%09result%5Bi%5D = stackTraces%5Bi%5D.toString();%0D%0A%09%09%09%7D
 %0D%0A
+%09
 %09%09re
@@ -1413,25 +1413,53 @@
 %09return 
-throwable
+result;%0D%0A%09%09%7D%0D%0A%09%09return new String%5B%5D%7B%7D
 ;%0D%0A%09%7D%0D%0A%0D
@@ -2031,39 +2031,28 @@
 on() %7B%0D%0A%09%09St
-ackTraceElement
+ring
 %5B%5D stacktrac
@@ -2080,152 +2080,8 @@
 );%0D%0A
-%09%09String stacktrace = String.format(Arrays.toString(Collections.nCopies(stacktraceElt.length, %22%5C%22%25s%5C%22%22).toArray()), (Object%5B%5D) stacktraceElt);%0D%0A
 %09%09St
@@ -2304,26 +2304,135 @@
 KTRACE, 
-stacktrace
+String.format(Arrays.toString(Collections.nCopies(stacktraceElt.length, %22%5C%22%25s%5C%22%22).toArray()), (Object%5B%5D) stacktraceElt)
 );%0D%0A%09%09re

fix bug stacktrace