diff --git a/.gitignore b/.gitignore index e2e5d94..8cdfc1f 100644 --- a/.gitignore +++ b/.gitignore @@ -2,3 +2,4 @@ .idea .qodana build +.intellijPlatform/ diff --git a/src/main/java/com/godwin/jsonparser/ui/forms/ParserWidget.java b/src/main/java/com/godwin/jsonparser/ui/forms/ParserWidget.java index fe7419a..fe56258 100644 --- a/src/main/java/com/godwin/jsonparser/ui/forms/ParserWidget.java +++ b/src/main/java/com/godwin/jsonparser/ui/forms/ParserWidget.java @@ -5,6 +5,7 @@ import com.godwin.jsonparser.ui.IParserWidget; import com.godwin.jsonparser.ui.dialog.OptionDialog; import com.godwin.jsonparser.util.JsonDownloader; +import com.godwin.jsonparser.util.JsonUtils; import com.godwin.jsonparser.util.NotificationUtil; import com.intellij.openapi.Disposable; import com.intellij.openapi.application.ApplicationManager; @@ -120,6 +121,8 @@ private void setEventListeners() { }); parseButton.addActionListener(e -> { String jsonString = mInputEditor.getDocument().getText(); + jsonString = JsonUtils.cleanUpJsonString(jsonString); + showBody(jsonString); NotificationUtil.showDonateNotification(); }); diff --git a/src/main/java/com/godwin/jsonparser/util/JsonUtils.java b/src/main/java/com/godwin/jsonparser/util/JsonUtils.java index cfa5903..1b8d64a 100644 --- a/src/main/java/com/godwin/jsonparser/util/JsonUtils.java +++ b/src/main/java/com/godwin/jsonparser/util/JsonUtils.java @@ -1,5 +1,6 @@ package com.godwin.jsonparser.util; +import com.fasterxml.jackson.core.JsonFactory; import com.fasterxml.jackson.core.JsonParser; import com.fasterxml.jackson.core.JsonProcessingException; import com.fasterxml.jackson.core.util.DefaultIndenter; @@ -63,6 +64,93 @@ public static Object parseJson(String json, ObjectMapper objectMapper) throws Ex } } + /** + * Cleans up the JSON string by applying various cleanup methods. + * For now, it only ensures missing opening and closing braces are fixed. + * Other future methods that can be added are: + * 1. Missing only opening brace + * 2. Missing only closing brace + * 2. Missing comma + * 3. missing '"' + */ + public static String cleanUpJsonString(String jsonString) { + jsonString = jsonString.trim(); + + // If it's already valid, return as is. + if (isValidJson(jsonString)) { + return jsonString; + } + + //attempt to fix json + + // Check if the start or end braces is missing + if (!jsonString.startsWith("{") || !jsonString.endsWith("}")) { + String fixedJsonString = fixMissingBraces(jsonString); + + // Validate after adding missing braces + if (isValidJson(fixedJsonString)) { + return fixedJsonString; + } + } + + //Return the JSON in the original form + return jsonString; + } + + /** + * Checks if the given JSON string is valid. + * @param jsonString The JSON string to validate. + * @return true if the JSON is valid, false otherwise. + */ + private static boolean isValidJson(String jsonString) { + try (JsonParser parser = new JsonFactory().createParser(jsonString)) { + //noinspection StatementWithEmptyBody + while (parser.nextToken() != null) { + // If we can iterate through tokens then it's valid JSON + } + return true; + } catch (Exception e) { + return false; // Invalid JSON + } + } + + /** + * Fixes missing opening and closing braces in the JSON string. + * @param jsonString The JSON string to fix. + * @return A properly wrapped JSON string. + */ + private static String fixMissingBraces(String jsonString) { + jsonString = jsonString.trim(); + + int openBracesCount = 0; + int closeBracesCount = 0; + boolean inString = false; + + // Count `{` and `}` braces outside of string values + for (int i = 0; i < jsonString.length(); i++) { + char ch = jsonString.charAt(i); + + if (ch == '"') { + // Toggle inString when encountering an unescaped quote + boolean isEscaped = i > 0 && jsonString.charAt(i - 1) == '\\'; + if (!isEscaped) { + inString = !inString; + } + } + + if (!inString) { + if (ch == '{') openBracesCount++; + if (ch == '}') closeBracesCount++; + } + } + + if (openBracesCount == closeBracesCount && !jsonString.startsWith("{")) { + jsonString = "{" + jsonString + "}"; + } + + return jsonString; + } + /* public static String minifyJson(String jsonStr) throws JsonProcessingException { Object jsonObject = Holder.MAPPER.readValue(jsonStr, Object.class); return Holder.MAPPER.writeValueAsString(jsonObject); diff --git a/src/test/java/jsonparser/util/JsonUtilsTest.java b/src/test/java/jsonparser/util/JsonUtilsTest.java new file mode 100644 index 0000000..51653d0 --- /dev/null +++ b/src/test/java/jsonparser/util/JsonUtilsTest.java @@ -0,0 +1,52 @@ +package jsonparser.util; + +import com.godwin.jsonparser.util.JsonUtils; +import org.junit.Test; + +import static org.junit.Assert.assertEquals; + +public class JsonUtilsTest { + + @Test + public void testValidJson_remainsUnchanged() { + String json = "{\"first_Name\": \"John\", \"last_Name\": \"Doe\",\"Age\": 20}"; + assertEquals(json, JsonUtils.cleanUpJsonString(json)); + } + + @Test + public void testValidJson_containsBraceInElement_remainsUnchanged() { + String json = "{\"first_Name\": \"Joh}}n\", \"last{_Name\": \"Doe\",\"Age\": 20}"; + assertEquals(json, JsonUtils.cleanUpJsonString(json)); + } + + @Test + public void testMissingBothBraces() { + String json = "\"first_Name\": \"John\", \"last_Name\": \"Doe\",\"Age\": 20"; + String expected = "{\"first_Name\": \"John\", \"last_Name\": \"Doe\",\"Age\": 20}"; + assertEquals(expected, JsonUtils.cleanUpJsonString(json)); + } + + @Test + public void testMissingBothBraces_containsBraceInElement() { + String json = "\"first_N{ame\": \"John\", \"last_N{{ame\": \"Do}e\",\"Age\": 20"; + String expected = "{\"first_N{ame\": \"John\", \"last_N{{ame\": \"Do}e\",\"Age\": 20}"; + assertEquals(expected, JsonUtils.cleanUpJsonString(json)); + } + + // A Brace is present at the closing, but it's not the closing brace + @Test + public void testMissingBothBraces_where_aClosingBraceIsPresent() { + String json = "\"first_Name\":\"John\",\"last_Name\":\"Doe\",\"Age\":20,\"department\":{\"name\":\"sales\"}"; + String expected = "{\"first_Name\":\"John\",\"last_Name\":\"Doe\",\"Age\":20,\"department\":{\"name\":\"sales\"}}"; + assertEquals(expected, JsonUtils.cleanUpJsonString(json)); + } + + // A Brace is present at the closing, but it's not the closing brace + @Test + public void testMissingBothBraces_containsBraceInElement_where_aClosingBraceIsPresent() { + String json = "\"first_Name\":\"John\",\"last_Name\":\"Doe}}\",\"Age{\":20,\"department\":{\"name\":\"sales\"}"; + String expected = "{\"first_Name\":\"John\",\"last_Name\":\"Doe}}\",\"Age{\":20,\"department\":{\"name\":\"sales\"}}"; + assertEquals(expected, JsonUtils.cleanUpJsonString(json)); + } + +}