diff --git a/src/JsonInspector/Tree.java b/src/JsonInspector/Tree.java index 690ff34..1ff9af8 100644 --- a/src/JsonInspector/Tree.java +++ b/src/JsonInspector/Tree.java @@ -3,72 +3,158 @@ package JsonInspector; import java.util.ArrayList; public class Tree { - private final Node firstNode; + private Node firstNode; public Tree(String file) { - firstNode = buildAST("", file); + try { + firstNode = parseElement(file); + } catch (JsonSyntaxException e) { + e.printStackTrace(); + //System.err.println("Syntax error while parsing JSON file"); + } } - private Node buildAST(String name, String file) { - char[] chars = file.toCharArray(); - int indentLevel = 0; - boolean inString = false; - Node currentNode = new Node("", Type.NULL); - ArrayList nextFiles = new ArrayList<>(), names = new ArrayList<>(); - String currentFile = "", currentString = ""; + private Node whichType(String element) throws JsonSyntaxException { + String[] keyValue = splitKeyValue(element); - for (char currentChar : chars) { - if (!inString) { - if (currentChar == '{') { - if (indentLevel == 0) { - currentNode = new Node(name, Type.OBJECT); - currentString = ""; - } else { - currentFile += currentChar; - } - indentLevel += 1; + if (keyValue.length == 2) { + String key = keyValue[0], value = keyValue[1]; - } else if (currentChar == '[') { - if (indentLevel == 0) { - currentNode = new Node(name, Type.ARRAY); - currentString = ""; - } else { - currentFile += currentChar; - } - indentLevel += 1; - - } else if (currentChar == '}' || currentChar == ']') { - if (indentLevel == 2) { - nextFiles.add(currentFile); - names.add(currentString); - currentFile = ""; - currentString = ""; - } else if (indentLevel == 1) { - break; - } else { - currentFile += currentChar; - } - indentLevel -= 1; - - } else if (currentChar == '"') { - inString = true; - } else { - //nextFile += chars[i]; - } - } else if (currentChar == '"') { - inString = false; + if (value.charAt(0) == '[' && value.charAt(value.length()-1) == ']') { + return parseArray(key, value); + } else if (value.charAt(0) == '{' && value.charAt(value.length()-1) == '}') { + return parseObject(key, value); } else { - currentString += currentChar; + return parsePair(key, value); + } + + } else if (keyValue[0].equals("")) { + + if (keyValue[0].charAt(0) == '{' && keyValue[0].charAt(keyValue[0].length()-1) == '}') { + return parseElement(keyValue[0]); + } else { + throw new JsonSyntaxException(); + } + + } else { + throw new JsonSyntaxException(); + } + } + + + private Node parseArray(String name, String rawValues) throws JsonSyntaxException { + Node array = new Node(name, Type.ARRAY); + ArrayList elements = splitList(rawValues); + + for (String value : elements) { + + if (value.charAt(0) == '{') { + if (value.charAt(value.length()-1) == '}') { + array.add(parseElement(value)); + } else { + throw new JsonSyntaxException(); + } + + } else { + array.add(value); } } + return array; + } - for (int i = 0; i < nextFiles.size(); i++) { - currentNode.add(buildAST(names.get(i), nextFiles.get(i))); + + private Node parseObject(String name, String rawValues) throws JsonSyntaxException { + Node object = new Node(name, Type.OBJECT); + ArrayList elements = splitList(rawValues); + + for (String value : elements) { + object.add(whichType(value)); } - return currentNode; + + return object; + } + + + private Node parsePair(String name, String value) { + Node pair = new Node(cleanOpeningExpression(name), Type.PAIR); + pair.add(value); + + return pair; + } + + + private Node parseElement(String rawValues) throws JsonSyntaxException { + Node element = new Node("", Type.ELEMENT); + ArrayList elements = splitList(rawValues); + + for (String value : elements) { + element.add(whichType(value)); + } + + return element; + } + + + private String cleanOpeningExpression(String strToClean) { + StringBuilder cleanedString = new StringBuilder(strToClean); + cleanedString.deleteCharAt(0); + cleanedString.deleteCharAt(cleanedString.length()-1); + return cleanedString.toString(); + } + + + private ArrayList splitList(String listToSplit) { + char[] chars = cleanOpeningExpression(listToSplit).toCharArray(); + int depth = 0; + ArrayList elements = new ArrayList<>(); + String buffer = ""; + + for (char currentChar : chars) { + if (currentChar == ',' && depth == 0) { + elements.add(buffer); + buffer = ""; + } else if (currentChar == '{' || currentChar == '[') { + depth += 1; + buffer += currentChar; + } else if (currentChar == '}' || currentChar == ']') { + depth -= 1; + buffer += currentChar; + } else { + buffer += currentChar; + } + } + elements.add(buffer); + return elements; + } + + + private String[] splitKeyValue(String expressionToSplit) { + boolean inKey = true; + char[] chars = expressionToSplit.toCharArray(); + String key = "", value, buffer = ""; + + for (char currentChar : chars) { + if (inKey) { + if (currentChar == '{' || currentChar == ':') { + key = buffer; + buffer = ""; + if (currentChar == '{') { + buffer += currentChar; + } + inKey = false; + } else { + buffer += currentChar; + } + } else { + buffer += currentChar; + } + } + value = buffer; + + return new String[] {key, value}; } @@ -81,20 +167,20 @@ public class Tree { indentation += Parameters.CONSOLE_INDENTATION; } - if (node.getType() != Type.ELEMENT) { + if (!node.isElement()) { line += indentation + "\"" + node.getName() + "\""; } else { line += indentation + node.getName(); } - if (node.getType() == Type.OBJECT || node.getType() == Type.ELEMENT) { + if (node.isObject() || node.isElement()) { line += printObjectElement(node, depth, indentation); - } else if (node.getType() == Type.PAIR){ + } else if (node.isPair()){ line += printPair(node); - } else if (node.getType() == Type.ARRAY){ + } else if (node.isArray()){ line += printArray(node, depth, indentation); } @@ -165,11 +251,14 @@ public class Tree { line += "]"; } else { + // Cette boucle parcours les valeurs du tableau for (int i = 0; i < node.getSize(); i++) { + // si la valeur a l'indice i n'est pas une valeur brute alors + // on appelle de manière récursive la fonction d'affichage de l'arbre if (node.get(i).isNode()) { line += "\n" + printTree((Node) node.get(i).getValue(), depth + 1); } else { - line += indentation + Parameters.CONSOLE_INDENTATION; + line += "\n" + indentation + Parameters.CONSOLE_INDENTATION; if (node.get(i).isString()) { line += "\"" + node.get(i).getValue() + "\""; } else { @@ -177,8 +266,9 @@ public class Tree { } } + // si la valeur n'est pas la dernière alors on lui ajoute une virgule if (i != node.getSize() - 1) { - line += ",\n"; + line += ","; } }