Description: Migrate away from deprecated json-simple 1.x classes
 See json-simple 2.0.0 changelog:
 > * Deprecated JSONParse and JSONValue in favor of Jsoner.
 > * Deprecated JSONStreamAware and JSONAware in favor of Jsonable.
 > * Deprecated JSONObject in favor of JsonObject.
 > * Deprecated JSONArray in favor of JsonArray.
 .
 This patch uses the new json-simple Json* classes. It is compatible with
 both 2.x and 3.x json-simple releases, with a few ajustments regarding
 backward incompatible changes in json-simple 3.x:
 - The package name, changed to com.github.cliftonlabs.json_simple
 - The exception DeserializationExcetpion renamed as JsonException
 These two changes are handled using place-holders @JSON_SIMPLE_PACKAGE@
 and @JSON_EXCETPION@ which are substituted at build time by debian/rules.
 .
 With these tricks the package is compatible with json-simple 2.x and 3.x.
Author: Gilles Filippini <pini@debian.org>
---
 src/plm/core/model/User.java                  |   21 ++++++++++++++-----
 src/plm/core/model/Users.java                 |   15 +++++++------
 src/plm/core/model/session/SessionDB.java     |   26 ++++++++++++------------
 src/plm/core/model/session/ZipSessionKit.java |   28 +++++++++++++-------------
 src/plm/core/model/tracking/GitSpy.java       |   16 +++++++-------
 src/plm/core/ui/action/HelpMe.java            |   15 ++++++-------
 6 files changed, 66 insertions(+), 55 deletions(-)

Index: b/src/plm/core/model/session/SessionDB.java
===================================================================
--- a/src/plm/core/model/session/SessionDB.java
+++ b/src/plm/core/model/session/SessionDB.java
@@ -3,10 +3,11 @@ package plm.core.model.session;
 import java.util.HashMap;
 import java.util.Map;
 import java.util.Set;
+import java.math.BigDecimal;
 
-import org.json.simple.JSONObject;
-import org.json.simple.parser.JSONParser;
-import org.json.simple.parser.ParseException;
+import @JSON_SIMPLE_PACKAGE@.JsonObject;
+import @JSON_SIMPLE_PACKAGE@.Jsoner;
+import @JSON_SIMPLE_PACKAGE@.@JSON_EXCEPTION@;
 
 import plm.core.lang.ProgrammingLanguage;
 import plm.core.model.Game;
@@ -154,7 +155,7 @@ public class SessionDB {
 	
 	
 	public String lessonSummary(String lesson) {
-		JSONObject result = new JSONObject();
+		JsonObject result = new JsonObject();
 
 		Map<ProgrammingLanguage, Integer> possibleL = possibleExercises.get(lesson);
 		for (ProgrammingLanguage pl: possibleL.keySet()) 
@@ -166,15 +167,14 @@ public class SessionDB {
 			if (passedL.get(pl)!=0)
 				result.put("passed"+pl.getLang(), passedL.get(pl));
 		
-		return result.toJSONString();
+		return result.toJson();
 	}
 	
 	public void lessonSummaryParse(String lesson, String JSONString) {
-		JSONParser parser = new JSONParser();
-		JSONObject data;
+		JsonObject data;
 		try {
-			data = (JSONObject) parser.parse(JSONString);
-		} catch (ParseException e) {
+			data = (JsonObject) Jsoner.deserialize(JSONString);
+		} catch (@JSON_EXCEPTION@ e) {
 			System.out.println("Ignoring invalid lesson summary (parse error: "+e.getLocalizedMessage()+").");
 			return;
 		}
@@ -186,12 +186,12 @@ public class SessionDB {
 		
 		for (ProgrammingLanguage pl: Game.getProgrammingLanguages()) {
 			if (data.containsKey("possible"+pl.getLang())) {
-				Long v = (Long) data.get("possible"+pl.getLang());
-				possibleL.put(pl, v.intValue());				
+				Integer v = ((BigDecimal) data.get("possible"+pl.getLang())).intValue();
+				possibleL.put(pl, v);
 			}
 			if (data.containsKey("passed"+pl.getLang())) {
-				Long v = (Long) data.get("passed"+pl.getLang()); // damn, damn java casting madness
-				passedL.put(pl, v.intValue());
+				Integer v = ((BigDecimal) data.get("passed"+pl.getLang())).intValue(); // damn, damn java casting madness
+				passedL.put(pl, v);
 			}
 		}
 	}
Index: b/src/plm/core/model/session/ZipSessionKit.java
===================================================================
--- a/src/plm/core/model/session/ZipSessionKit.java
+++ b/src/plm/core/model/session/ZipSessionKit.java
@@ -13,9 +13,9 @@ import java.util.zip.ZipOutputStream;
 
 import javax.swing.JOptionPane;
 
-import org.json.simple.JSONObject;
-import org.json.simple.JSONValue;
-import org.json.simple.parser.ParseException;
+import @JSON_SIMPLE_PACKAGE@.JsonObject;
+import @JSON_SIMPLE_PACKAGE@.Jsoner;
+import @JSON_SIMPLE_PACKAGE@.@JSON_EXCEPTION@;
 
 import plm.core.lang.ProgrammingLanguage;
 import plm.core.model.Game;
@@ -50,15 +50,15 @@ public class ZipSessionKit implements IS
 			storeLesson(path, lesson);
 			
 		/* Save the per lesson summaries */
-		JSONObject allLessons = new JSONObject();
+		JsonObject allLessons = new JsonObject();
 		for (String lessonName : this.game.studentWork.getLessonsNames()) {
-			JSONObject allLangs = new JSONObject();
+			JsonObject allLangs = new JsonObject();
 			for (ProgrammingLanguage lang: Game.getProgrammingLanguages()) {
 				int possible = Game.getInstance().studentWork.getPossibleExercises(lessonName, lang);
 				int passed = Game.getInstance().studentWork.getPassedExercises(lessonName, lang);
 
 				if (possible>0) {
-					JSONObject oneLang = new JSONObject();
+					JsonObject oneLang = new JsonObject();
 					oneLang.put("possible",possible);
 					oneLang.put("passed",passed);
 					allLangs.put(lang.getLang(),oneLang);
@@ -77,7 +77,7 @@ public class ZipSessionKit implements IS
 			zos.setLevel(Deflater.BEST_COMPRESSION);
 
 			zos.putNextEntry(new ZipEntry("passed"));
-			zos.write(allLessons.toJSONString().getBytes());
+			zos.write(allLessons.toJson().getBytes());
 			zos.closeEntry();
 		} catch (IOException ex) { // FileNotFoundException or IOException
 			// It's ok to loose this data as it will be recomputed when the lessons are actually loaded
@@ -142,25 +142,25 @@ public class ZipSessionKit implements IS
 		// now parse it
 		Object value = null;
 		try {
-			value = JSONValue.parseWithException(content);
-		} catch (ParseException e) {
+			value = Jsoner.deserialize(content);
+		} catch (@JSON_EXCEPTION@ e) {
 			System.err.println("Parse error while reading the scores from disk:");
 			e.printStackTrace();
 		}
-		if (! (value instanceof JSONObject)) {
-			System.err.println("Retrieved passed-values is not a JSONObject: "+value);
+		if (! (value instanceof JsonObject)) {
+			System.err.println("Retrieved passed-values is not a JsonObject: "+value);
 			return;
 		}
-		JSONObject allLessons = (JSONObject) value; 
+		JsonObject allLessons = (JsonObject) value; 
 		for (Object lessonName: allLessons.keySet()) {
-			JSONObject allLangs = (JSONObject) allLessons.get(lessonName);
+			JsonObject allLangs = (JsonObject) allLessons.get(lessonName);
 			for (Object langName: allLangs.keySet()) {
 				ProgrammingLanguage lang = null;
 				for (ProgrammingLanguage l:Game.getProgrammingLanguages())
 					if (l.getLang().equals(langName))
 						lang = l;
 				
-				JSONObject oneLang = (JSONObject) allLangs.get(langName);
+				JsonObject oneLang = (JsonObject) allLangs.get(langName);
 				int possible = Integer.parseInt(""+oneLang.get("possible"));
 				int passed = Integer.parseInt(""+oneLang.get("passed"));
 				Game.getInstance().studentWork.setPossibleExercises((String) lessonName, lang, possible);
Index: b/src/plm/core/model/tracking/GitSpy.java
===================================================================
--- a/src/plm/core/model/tracking/GitSpy.java
+++ b/src/plm/core/model/tracking/GitSpy.java
@@ -10,7 +10,7 @@ import java.util.List;
 import org.eclipse.jgit.api.errors.GitAPIException;
 import org.eclipse.jgit.lib.NullProgressMonitor;
 import org.eclipse.jgit.lib.ProgressMonitor;
-import org.json.simple.JSONObject;
+import @JSON_SIMPLE_PACKAGE@.JsonObject;
 
 import plm.core.UserSwitchesListener;
 import plm.core.lang.ProgrammingLanguage;
@@ -105,7 +105,7 @@ public class GitSpy implements ProgressS
 			createFiles(exo);
 			checkSuccess(exo);
 			
-			String commitMsg = writeCommitMessage(exo, null, "executed", new JSONObject());
+			String commitMsg = writeCommitMessage(exo, null, "executed", new JsonObject());
 			String userUUID = Game.getInstance().getUsers().getCurrentUser().getUserUUIDasString();
 			String userBranch = "PLM"+GitUtils.sha1(userUUID);
 		
@@ -126,7 +126,7 @@ public class GitSpy implements ProgressS
 			createFiles(lastExo);
 
 			try {
-				String commitMsg = writeCommitMessage(lastExo, exo, "switched", new JSONObject());
+				String commitMsg = writeCommitMessage(lastExo, exo, "switched", new JsonObject());
 				String userUUID = Game.getInstance().getUsers().getCurrentUser().getUserUUIDasString();
 				String userBranch = "PLM"+GitUtils.sha1(userUUID);
 			
@@ -142,7 +142,7 @@ public class GitSpy implements ProgressS
 		try {
 			deleteFiles(exo);
 
-			String commitMsg = writeCommitMessage(exo, null, "reverted", new JSONObject());
+			String commitMsg = writeCommitMessage(exo, null, "reverted", new JsonObject());
 			String userUUID = Game.getInstance().getUsers().getCurrentUser().getUserUUIDasString();
 			String userBranch = "PLM"+GitUtils.sha1(userUUID);
 		
@@ -189,7 +189,7 @@ public class GitSpy implements ProgressS
 	 * Helper methods
 	 */
 	@SuppressWarnings("unchecked")
-	private String writeCommitMessage(Exercise exoFrom, Exercise exoTo, String evt_type, JSONObject logmsg) {
+	private String writeCommitMessage(Exercise exoFrom, Exercise exoTo, String evt_type, JsonObject logmsg) {
 
 		ExecutionProgress lastResult = exoFrom.lastResult;
 
@@ -233,7 +233,7 @@ public class GitSpy implements ProgressS
 	 */
 	@SuppressWarnings("unchecked")
 	private String writePLMStartedOrLeavedCommitMessage(String kind) {
-		JSONObject jsonObject = new JSONObject();
+		JsonObject jsonObject = new JsonObject();
 
 		// Retrieve the feedback informations
 		jsonObject.put("java", System.getProperty("java.version") + " (VM: " + System.getProperty("java.vm.name") + "; version: " + System.getProperty("java.vm.version") + ")");
@@ -366,7 +366,7 @@ public class GitSpy implements ProgressS
 			e.printStackTrace();
 		}
 			
-		JSONObject msg = new JSONObject();
+		JsonObject msg = new JsonObject();
 		msg.put("studentInput", studentInput);
 		String commitMsg = writeCommitMessage(lastExo, null, evt_type, msg);
 		String userUUID = Game.getInstance().getUsers().getCurrentUser().getUserUUIDasString();
@@ -399,7 +399,7 @@ public class GitSpy implements ProgressS
 			e.printStackTrace();
 		}
 		
-		JSONObject msg = new JSONObject();
+		JsonObject msg = new JsonObject();
 		msg.put("id", id);
 		String commitMsg = writeCommitMessage(lastExo, null, "readTip", msg);
 		String userUUID = Game.getInstance().getUsers().getCurrentUser().getUserUUIDasString();
Index: b/src/plm/core/model/User.java
===================================================================
--- a/src/plm/core/model/User.java
+++ b/src/plm/core/model/User.java
@@ -3,15 +3,16 @@ package plm.core.model;
 import java.io.IOException;
 import java.io.File;
 import java.io.Writer;
+import java.io.StringWriter;
 import java.util.HashMap;
 import java.util.LinkedHashMap;
 import java.util.Objects;
 import java.util.UUID;
 
-import org.json.simple.JSONStreamAware;
-import org.json.simple.JSONValue;
+import @JSON_SIMPLE_PACKAGE@.Jsonable;
+import @JSON_SIMPLE_PACKAGE@.Jsoner;
 
-public class User implements JSONStreamAware {
+public class User implements Jsonable {
 	static final String DEFAULT_EXERCISE = "plm://lessons.welcome/";
 	
 	private String username;
@@ -64,13 +65,23 @@ public class User implements JSONStreamA
 	}
 
 	@SuppressWarnings({ "unchecked", "rawtypes" })
-	public void writeJSONString(Writer out) throws IOException {
+	public void toJson(Writer out) throws IOException {
 		LinkedHashMap obj = new LinkedHashMap();
 		obj.put("username", username);
 		obj.put("lastUsed", lastUsed);
 		obj.put("userUUID", String.valueOf(userUUID));
 		obj.put("exercise", currentExo);
-		JSONValue.writeJSONString(obj, out);
+		Jsoner.serialize(obj, out);
+	}
+	public String toJson() {
+		StringWriter writer = new StringWriter();
+		try {
+			toJson(writer);
+			return writer.toString();
+		}
+		catch (IOException e) {
+			return "";
+		}
 	}
 
 	@Override
Index: b/src/plm/core/model/Users.java
===================================================================
--- a/src/plm/core/model/Users.java
+++ b/src/plm/core/model/Users.java
@@ -12,8 +12,10 @@ import java.util.Iterator;
 import java.util.List;
 import java.util.Vector;
 
-import org.json.simple.parser.JSONParser;
-import org.json.simple.parser.ParseException;
+import @JSON_SIMPLE_PACKAGE@.JsonArray;
+import @JSON_SIMPLE_PACKAGE@.JsonObject;
+import @JSON_SIMPLE_PACKAGE@.Jsoner;
+import @JSON_SIMPLE_PACKAGE@.@JSON_EXCEPTION@;
 
 import plm.core.UserSwitchesListener;
 import plm.core.utils.FileUtils;
@@ -155,9 +157,8 @@ public class Users {
 				this.usersList.add(new User());
 				flushUsersToFile();
 			} else {
-				JSONParser parser = new JSONParser();
 				try {
-					List json = (List) parser.parse(new FileReader(userDBFile));
+					JsonArray json = (JsonArray) Jsoner.deserialize(new FileReader(userDBFile));
 					Iterator iter = json.iterator();
 
 					while (iter.hasNext()) {
@@ -166,7 +167,7 @@ public class Users {
 						usersList.add(new User(entry));
 					}
 
-				} catch (ParseException | IOException pe) {
+				} catch (@JSON_EXCEPTION@ | IOException pe) {
 					System.out.println(pe);
 				}
 			}
@@ -174,7 +175,7 @@ public class Users {
 	}
 
 	/**
-	 * Write the ArrayList of User in the JSONArray users. Doing so means that we update the plm.users file with the
+	 * Write the ArrayList of User in the JsonArray users. Doing so means that we update the plm.users file with the
 	 * latest changes. This method should always be called after using a Setter from User.
 	 */
 	public void flushUsersToFile() {
@@ -189,7 +190,7 @@ public class Users {
 				out.append("[\n");
 				for (int rank = 0 ; rank < usersList.size(); rank++) {
 					out.append("  ");
-					usersList.get(rank).writeJSONString(out);
+					usersList.get(rank).toJson(out);
 					if (rank < usersList.size()-1)
 						out.append(",");
 					out.append("\n");
Index: b/src/plm/core/ui/action/HelpMe.java
===================================================================
--- a/src/plm/core/ui/action/HelpMe.java
+++ b/src/plm/core/ui/action/HelpMe.java
@@ -19,9 +19,9 @@ import javax.swing.ImageIcon;
 import javax.swing.JOptionPane;
 import javax.swing.JToggleButton;
 
-import org.json.simple.JSONValue;
-import org.json.simple.parser.JSONParser;
-import org.json.simple.parser.ParseException;
+import @JSON_SIMPLE_PACKAGE@.JsonObject;
+import @JSON_SIMPLE_PACKAGE@.Jsoner;
+import @JSON_SIMPLE_PACKAGE@.@JSON_EXCEPTION@;
 import org.xnap.commons.i18n.I18n;
 import org.xnap.commons.i18n.I18nFactory;
 
@@ -49,7 +49,7 @@ public class HelpMe extends AbstractGame
 	public void actionPerformed(ActionEvent e) {
 		isRequestingHelp = !isRequestingHelp;
 
-		LinkedHashMap<String,String> obj = new LinkedHashMap<String,String>();
+		JsonObject obj = new JsonObject();
 		obj.put("uuid", Game.getInstance().getUsers().getCurrentUser().getUserUUIDasString());
 		try {
 			obj.put("hostname", InetAddress.getLocalHost().getHostName());
@@ -81,7 +81,7 @@ public class HelpMe extends AbstractGame
 		if (!isRequestingHelp) {
 			obj.put("callID", lastCallID + "");
 		}
-		String payload = JSONValue.toJSONString(obj);
+		String payload = obj.toJson();
 		String urlStr = Game.getProperty("plm.play.server.url") + "callHelp";
 
 		String line;
@@ -106,8 +106,7 @@ public class HelpMe extends AbstractGame
 			br.close();
 			connection.disconnect();
 
-			JSONParser parser = new JSONParser();
-			Object objResponse = parser.parse(jsonString.toString());
+			Object objResponse = Jsoner.deserialize(jsonString.toString());
 			@SuppressWarnings("unchecked")
 			Map<String,String> map = (Map<String,String>) objResponse;
 
@@ -138,7 +137,7 @@ public class HelpMe extends AbstractGame
 					break;
 			}
 
-		} catch (IOException | ParseException ex) {
+		} catch (IOException | @JSON_EXCEPTION@ ex) {
 			isRequestingHelp = false;
 			((JToggleButton) e.getSource()).setText(isRequestingHelp ? i18n.tr("Cancel call") : i18n.tr("Call for Help"));
 			((JToggleButton) e.getSource()).setIcon(ResourcesCache.getIcon("img/btn-alert-" + (isRequestingHelp ? "on" : "off") + ".png"));
