diff --git a/pom.xml b/pom.xml index 585282b..0fc71e5 100644 --- a/pom.xml +++ b/pom.xml @@ -252,7 +252,7 @@ checkstyle.xml UTF-8 true - false + true false false diff --git a/src/main/antlr4/com/chaudhuri/plist/Plist.g4 b/src/main/antlr4/com/chaudhuri/plist/Plist.g4 index ed211fe..62d674e 100644 --- a/src/main/antlr4/com/chaudhuri/plist/Plist.g4 +++ b/src/main/antlr4/com/chaudhuri/plist/Plist.g4 @@ -75,7 +75,7 @@ fragment NameStartChar // parser rules parse: dictionary | list; -dictionary: LBRACE (keyvaluepair (SEMI keyvaluepair?)*)? RBRACE; +dictionary: LBRACE (keyvaluepair (SEMI keyvaluepair)* SEMI?)? RBRACE; keyvaluepair: STRING EQUALS value; value: string | number | list | dictionary; string: STRING; diff --git a/src/main/java/com/chaudhuri/cataloggenerator/ExpansionManifestComparator.java b/src/main/java/com/chaudhuri/cataloggenerator/ExpansionManifestComparator.java index 527288b..90f23f3 100644 --- a/src/main/java/com/chaudhuri/cataloggenerator/ExpansionManifestComparator.java +++ b/src/main/java/com/chaudhuri/cataloggenerator/ExpansionManifestComparator.java @@ -9,8 +9,10 @@ import org.apache.logging.log4j.Logger; /** - * - * @author hiran + * Comparator for expansion manifests. + * Helps sorting expansions. + * + * @author oocube */ public class ExpansionManifestComparator implements Comparator { private static final Logger log = LogManager.getLogger(); diff --git a/src/main/java/com/chaudhuri/cataloggenerator/ExpansionManifestConverter.java b/src/main/java/com/chaudhuri/cataloggenerator/ExpansionManifestConverter.java index a9f859d..67f1321 100644 --- a/src/main/java/com/chaudhuri/cataloggenerator/ExpansionManifestConverter.java +++ b/src/main/java/com/chaudhuri/cataloggenerator/ExpansionManifestConverter.java @@ -14,7 +14,8 @@ /** * Genson converter to serialize ExpansionManifest. - * @author hiran + * + * @author oocube */ public class ExpansionManifestConverter implements Converter { private static final Logger log = LogManager.getLogger(); diff --git a/src/main/java/com/chaudhuri/ooliteaddonscanner2/AddonsUtil.java b/src/main/java/com/chaudhuri/ooliteaddonscanner2/AddonsUtil.java index 819ddf2..33a5113 100644 --- a/src/main/java/com/chaudhuri/ooliteaddonscanner2/AddonsUtil.java +++ b/src/main/java/com/chaudhuri/ooliteaddonscanner2/AddonsUtil.java @@ -68,7 +68,7 @@ /** * Contains utility functions for handling the Oolite addons model. * - * @author hiran + * @author oocube */ public class AddonsUtil { private static final Logger log = LogManager.getLogger(); @@ -241,7 +241,7 @@ public static void readShips(String url, InputStream in, Registry registry, Expa registry.addShipList(expansion, shipList); } else { in.reset(); - PlistParser.DictionaryContext dc = PlistParserUtil.parsePlistDictionary(in, url); + PlistParser.DictionaryContext dc = PlistParserUtil.parsePlistDictionary(in, url, expansion); checkPlistKeys(dc, expansion); registry.addShipList(expansion, dc); } @@ -476,7 +476,7 @@ public static void readOxps(ExpansionCache cache, Registry registry) { for(Expansion oxp: registry.getExpansions()) { i++; - log.info("Reading expansions ({}/{})...", i, total); + log.info("Reading expansions... ({}/{} {})", i, total, oxp.getIdentifier()); readOxp(cache, registry, oxp); } @@ -505,7 +505,13 @@ public static void readOxp(ExpansionCache cache, Registry registry, Expansion ex ZipInputStream zin = new ZipInputStream(new BufferedInputStream(cache.getPluginInputStream(expansion.getDownloadUrl()))); ZipEntry zentry = null; while ((zentry = zin.getNextEntry()) != null) { - readOxpEntry(zin, zentry, registry, expansion); + try { + readOxpEntry(zin, zentry, registry, expansion); + } catch (Exception ex) { + String message = String.format("Could not parse %s!%s", expansion.getDownloadUrl(), zentry.getName()); + log.error(message, ex); + expansion.addWarning(message + "\n" + ex.getMessage()); + } } } catch (EOFException e) { log.warn("Incomplete plugin archive for {}", expansion.getDownloadUrl(), e); diff --git a/src/main/java/com/chaudhuri/ooliteaddonscanner2/Registry.java b/src/main/java/com/chaudhuri/ooliteaddonscanner2/Registry.java index 18757e1..ed41ea4 100644 --- a/src/main/java/com/chaudhuri/ooliteaddonscanner2/Registry.java +++ b/src/main/java/com/chaudhuri/ooliteaddonscanner2/Registry.java @@ -893,6 +893,12 @@ protected void processDependencies() { }); } + /** + * Returns the list of expansions that match the given dependency. + * + * @param dependency the dependency to search for + * @return the list of expansions + */ public List getExpansionsByDependency(Expansion.Dependency dependency) { return expansions.values().stream() .filter((man) -> isMatch(man, dependency)) diff --git a/src/main/java/com/chaudhuri/ooliteaddonscanner2/TemplateUtil.java b/src/main/java/com/chaudhuri/ooliteaddonscanner2/TemplateUtil.java index a2b1a8c..6f45d9a 100644 --- a/src/main/java/com/chaudhuri/ooliteaddonscanner2/TemplateUtil.java +++ b/src/main/java/com/chaudhuri/ooliteaddonscanner2/TemplateUtil.java @@ -4,7 +4,6 @@ import static com.chaudhuri.ooliteaddonscanner2.Scanner.HTML_EXTENSION; import static com.chaudhuri.ooliteaddonscanner2.Scanner.PLANTUML_EXTENSION; -import static com.chaudhuri.ooliteaddonscanner2.Scanner.SVG_EXTENSION; import com.chaudhuri.ooliteaddonscanner2.model.Equipment; import com.chaudhuri.ooliteaddonscanner2.model.Expansion; import com.chaudhuri.ooliteaddonscanner2.model.Ship; @@ -15,8 +14,9 @@ import org.apache.logging.log4j.Logger; /** + * Wrapper methods for the FTL template engine. * - * @author hiran + * @author oocube */ public class TemplateUtil { private static final Logger log = LogManager.getLogger(); diff --git a/src/main/java/com/chaudhuri/ooliteaddonscanner2/model/Expansion.java b/src/main/java/com/chaudhuri/ooliteaddonscanner2/model/Expansion.java index 144c03d..df38545 100644 --- a/src/main/java/com/chaudhuri/ooliteaddonscanner2/model/Expansion.java +++ b/src/main/java/com/chaudhuri/ooliteaddonscanner2/model/Expansion.java @@ -689,10 +689,20 @@ public int compareTo(Expansion other) { return identifier.compareTo(other.getIdentifier()); } + /** + * Adds a dependent OXP to the list. + * + * @param dependent the OXP + */ public void addDependentOxp(Dependency dependent) { dependentOxps.add(dependent); } - + + /** + * Returns the list of dependent OXPs. + * + * @return the list + */ public List getDependentOxps() { return dependentOxps; } diff --git a/src/main/java/com/chaudhuri/ooliteaddonscanner2/plist/PlistParserUtil.java b/src/main/java/com/chaudhuri/ooliteaddonscanner2/plist/PlistParserUtil.java index e65970c..f4d0f92 100644 --- a/src/main/java/com/chaudhuri/ooliteaddonscanner2/plist/PlistParserUtil.java +++ b/src/main/java/com/chaudhuri/ooliteaddonscanner2/plist/PlistParserUtil.java @@ -2,6 +2,7 @@ */ package com.chaudhuri.ooliteaddonscanner2.plist; +import com.chaudhuri.ooliteaddonscanner2.model.Expansion; import com.chaudhuri.plist.PlistLexer; import com.chaudhuri.plist.PlistParser; import java.io.IOException; @@ -17,12 +18,14 @@ import org.antlr.v4.runtime.CharStreams; import org.antlr.v4.runtime.CommonTokenStream; import org.antlr.v4.runtime.tree.ParseTree; +import org.antlr.v4.runtime.tree.ParseTreeWalker; import org.apache.logging.log4j.LogManager; import org.apache.logging.log4j.Logger; /** + * Wrapper for the ANTLR generated plist parser. * - * @author hiran + * @author oocube */ public class PlistParserUtil { private static final Logger log = LogManager.getLogger(); @@ -92,7 +95,34 @@ public static PlistParser.ListContext parsePlistList(InputStream data, String so * @throws IOException something went wrong */ public static PlistParser.DictionaryContext parsePlistDictionary(InputStream data, String source) throws IOException { - return prepareParser(data, source).dictionary(); + PlistParser parser = prepareParser(data, source); + PlistParser.DictionaryContext parseTree = parser.dictionary(); + + return parseTree; + } + + /** + * Parses a plist dictionary from the given inputstream and validates it. + * Warnings will be added to the expansion. + * + * @param data the inputstream to read from + * @param source the source of the data for good error messages + * @param expansion + * @return the parsed dictionary + * @throws IOException something went wrong + */ + public static PlistParser.DictionaryContext parsePlistDictionary(InputStream data, String source, Expansion expansion) throws IOException { + PlistParser.DictionaryContext parseTree = parsePlistDictionary(data, source); + + // validate the dictionary + ValidationListener vl = new ValidationListener(); + ParseTreeWalker walker = new ParseTreeWalker(); + walker.walk(vl, parseTree); + for (String warning: vl.getWarnings()) { + expansion.addWarning(warning); + } + + return parseTree; } /** diff --git a/src/main/java/com/chaudhuri/ooliteaddonscanner2/plist/ValidationListener.java b/src/main/java/com/chaudhuri/ooliteaddonscanner2/plist/ValidationListener.java new file mode 100644 index 0000000..e6d06e3 --- /dev/null +++ b/src/main/java/com/chaudhuri/ooliteaddonscanner2/plist/ValidationListener.java @@ -0,0 +1,77 @@ +/* + */ +package com.chaudhuri.ooliteaddonscanner2.plist; + +import com.chaudhuri.plist.PlistBaseListener; +import com.chaudhuri.plist.PlistParser; +import java.util.ArrayList; +import java.util.List; +import org.antlr.v4.runtime.Token; +import org.antlr.v4.runtime.TokenSource; +import org.antlr.v4.runtime.tree.ParseTree; +import org.apache.logging.log4j.LogManager; +import org.apache.logging.log4j.Logger; + +/** + * Validates a plist Dictionary and collects the warnings. + * Apply this listener via ParseTreeWalker, then retrieve the collected + * warnings. + * + * @author oocube + */ +public class ValidationListener extends PlistBaseListener { + private static final Logger log = LogManager.getLogger(); + + private final List warnings; + + /** + * Creates a new instance. + */ + public ValidationListener() { + warnings = new ArrayList<>(); + } + + /** + * check the last element is a semicolon. + * @param ctx + */ + @Override + public void exitDictionary(PlistParser.DictionaryContext ctx) { + log.debug("exitDictionary({})", ctx); + if (ctx.children == null) { + log.warn("plist dictionary without content?"); + return; + } + if (ctx.children.size()<2) { + log.warn("plist dictionary without braces?"); + return; + } + int posSEMI = ctx.children.size() -2; + ParseTree pt = ctx.children.get(posSEMI); + log.debug("semicolon: {}", pt); + if (pt.getPayload() instanceof Token token) { + if (token.getType() == PlistParser.LBRACE) { + // we are looking at an empty plist. we are good + return; + } + if (token.getType() == PlistParser.SEMI) { + // assumed semicolon found. we are good + return; + } + } + + TokenSource ts = ctx.getStop().getTokenSource(); + String msg = String.format("Expected semicolon in %s after dictionary entry at [%s:%s]", ts.getSourceName(), ts.getLine(), ts.getCharPositionInLine()); + warnings.add(msg); + } + + /** + * Returns the collected warnings. + * + * @return the warnings + */ + public List getWarnings() { + return new ArrayList(warnings); + } + +} diff --git a/src/main/resources/com/chaudhuri/ooliteaddonscanner2/templates/equipment.ftlh b/src/main/resources/com/chaudhuri/ooliteaddonscanner2/templates/equipment.ftlh index 2bbd90b..e411ddb 100644 --- a/src/main/resources/com/chaudhuri/ooliteaddonscanner2/templates/equipment.ftlh +++ b/src/main/resources/com/chaudhuri/ooliteaddonscanner2/templates/equipment.ftlh @@ -6,7 +6,7 @@ - +
Back to IndexBack to Index Page generated: ${.now}
diff --git a/src/main/resources/com/chaudhuri/ooliteaddonscanner2/templates/expansion.ftlh b/src/main/resources/com/chaudhuri/ooliteaddonscanner2/templates/expansion.ftlh index a215b44..9f0f31b 100644 --- a/src/main/resources/com/chaudhuri/ooliteaddonscanner2/templates/expansion.ftlh +++ b/src/main/resources/com/chaudhuri/ooliteaddonscanner2/templates/expansion.ftlh @@ -9,7 +9,7 @@ - +
Back to IndexBack to Index Page generated: ${.now}
diff --git a/src/main/resources/com/chaudhuri/ooliteaddonscanner2/templates/ship.ftlh b/src/main/resources/com/chaudhuri/ooliteaddonscanner2/templates/ship.ftlh index e841e56..3adab35 100644 --- a/src/main/resources/com/chaudhuri/ooliteaddonscanner2/templates/ship.ftlh +++ b/src/main/resources/com/chaudhuri/ooliteaddonscanner2/templates/ship.ftlh @@ -6,7 +6,7 @@ - +
Back to IndexBack to Index Page generated: ${.now}
diff --git a/src/main/resources/log4j2.xml b/src/main/resources/log4j2.xml index 818e6ae..82643f0 100644 --- a/src/main/resources/log4j2.xml +++ b/src/main/resources/log4j2.xml @@ -16,6 +16,7 @@ + diff --git a/src/test/resources/log4j2.xml b/src/test/resources/log4j2.xml index 5631d6b..1b8c681 100644 --- a/src/test/resources/log4j2.xml +++ b/src/test/resources/log4j2.xml @@ -11,7 +11,7 @@ - + @@ -26,6 +26,7 @@ +