From b3a3843b604625e181b824e1eab4e6ed9f381c8f Mon Sep 17 00:00:00 2001 From: ljacqu Date: Thu, 7 Apr 2016 17:19:52 +0200 Subject: [PATCH] Tools: doc templates - add support for iterating tags - Support iterating tags - Generate (update) all docs --- docs/commands.md | 66 +++++++++---------- docs/hash_algorithms.md | 6 +- docs/permission_nodes.md | 5 +- src/tools/commands/CommandPageCreater.java | 31 ++++----- src/tools/commands/command_entry.tpl.md | 2 - src/tools/commands/commands.tpl.md | 5 +- .../HashAlgorithmsDescriptionTask.java | 22 +++---- src/tools/hashmethods/hash_algorithms.tpl.md | 5 +- .../hashmethods/hash_algorithms_row.tpl.md | 1 - .../permissions/PermissionsListWriter.java | 24 +++---- .../permissions/permission_node_entry.tpl.md | 1 - src/tools/permissions/permission_nodes.tpl.md | 4 +- src/tools/utils/FileUtils.java | 7 +- src/tools/utils/TagReplacer.java | 51 +++++++++++--- src/tools/utils/TagValue.java | 51 ++++++++++++++ src/tools/utils/TagValueHolder.java | 34 ++++++++++ 16 files changed, 209 insertions(+), 106 deletions(-) delete mode 100644 src/tools/commands/command_entry.tpl.md delete mode 100644 src/tools/hashmethods/hash_algorithms_row.tpl.md delete mode 100644 src/tools/permissions/permission_node_entry.tpl.md create mode 100644 src/tools/utils/TagValue.java create mode 100644 src/tools/utils/TagValueHolder.java diff --git a/docs/commands.md b/docs/commands.md index 70a752d3e..ba38674d2 100644 --- a/docs/commands.md +++ b/docs/commands.md @@ -1,5 +1,5 @@ - + ## AuthMe Commands You can use the following commands to use the features of AuthMe. Mandatory arguments are marked with `< >` @@ -7,74 +7,72 @@ brackets; optional arguments are enclosed in square brackets (`[ ]`). - **/authme**: The main AuthMeReloaded command. The root for all admin commands. - **/authme register** <player> <password>: Register the specified player with the specified password. -
Requires `authme.admin.register` +
Requires `authme.admin.register` - **/authme unregister** <player>: Unregister the specified player. -
Requires `authme.admin.unregister` +
Requires `authme.admin.unregister` - **/authme forcelogin** [player]: Enforce the specified player to login. -
Requires `authme.player.canbeforced` +
Requires `authme.admin.forcelogin` - **/authme password** <player> <pwd>: Change the password of a player. -
Requires `authme.admin.changepassword` +
Requires `authme.admin.changepassword` - **/authme lastlogin** [player]: View the date of the specified players last login. -
Requires `authme.admin.lastlogin` +
Requires `authme.admin.lastlogin` - **/authme accounts** [player]: Display all accounts of a player by his player name or IP. -
Requires `authme.admin.accounts` +
Requires `authme.admin.accounts` - **/authme email** [player]: Display the email address of the specified player if set. -
Requires `authme.admin.getemail` +
Requires `authme.admin.getemail` - **/authme setemail** <player> <email>: Change the email address of the specified player. -
Requires `authme.admin.changemail` +
Requires `authme.admin.changemail` - **/authme getip** <player>: Get the IP address of the specified online player. -
Requires `authme.admin.getip` -- **/authme spawn** <player>: Teleport to the spawn. -
Requires `authme.admin.spawn` +
Requires `authme.admin.getip` +- **/authme spawn**: Teleport to the spawn. +
Requires `authme.admin.spawn` - **/authme setspawn**: Change the player's spawn to your current position. -
Requires `authme.admin.setspawn` +
Requires `authme.admin.setspawn` - **/authme firstspawn**: Teleport to the first spawn. -
Requires `authme.admin.firstspawn` +
Requires `authme.admin.firstspawn` - **/authme setfirstspawn**: Change the first player's spawn to your current position. -
Requires `authme.admin.setfirstspawn` +
Requires `authme.admin.setfirstspawn` - **/authme purge** <days>: Purge old AuthMeReloaded data longer than the specified amount of days ago. -
Requires `authme.admin.purge` +
Requires `authme.admin.purge` - **/authme resetpos** <player/*>: Purge the last know position of the specified player or all of them. -
Requires `authme.admin.purgelastpos` +
Requires `authme.admin.purgelastpos` - **/authme purgebannedplayers**: Purge all AuthMeReloaded data for banned players. -
Requires `authme.admin.purgebannedplayers` +
Requires `authme.admin.purgebannedplayers` - **/authme switchantibot** [mode]: Switch or toggle the AntiBot mode to the specified state. -
Requires `authme.admin.switchantibot` +
Requires `authme.admin.switchantibot` - **/authme reload**: Reload the AuthMeReloaded plugin. -
Requires `authme.admin.reload` +
Requires `authme.admin.reload` - **/authme version**: Show detailed information about the installed AuthMeReloaded version, the developers, contributors, and license. +- **/authme converter** <job>: Converter command for AuthMeReloaded. +
Requires `authme.admin.converter` - **/authme help** [query]: View detailed help for /authme commands. - **/login** <password>: Command to log in using AuthMeReloaded. -
Requires `authme.player.login` +
Requires `authme.player.login` - **/login help** [query]: View detailed help for /login commands. - **/logout**: Command to logout using AuthMeReloaded. -
Requires `authme.player.logout` +
Requires `authme.player.logout` - **/logout help** [query]: View detailed help for /logout commands. - **/register** [password] [verifyPassword]: Command to register using AuthMeReloaded. -
Requires `authme.player.register` +
Requires `authme.player.register` - **/register help** [query]: View detailed help for /register commands. - **/unreg** <password>: Command to unregister using AuthMeReloaded. -
Requires `authme.player.unregister` +
Requires `authme.player.unregister` - **/unreg help** [query]: View detailed help for /unreg commands. - **/changepassword** <oldPassword> <newPassword>: Command to change your password using AuthMeReloaded. -
Requires `authme.player.changepassword` +
Requires `authme.player.changepassword` - **/changepassword help** [query]: View detailed help for /changepassword commands. - **/email**: The AuthMeReloaded Email command base. - **/email add** <email> <verifyEmail>: Add a new email address to your account. -
Requires `authme.player.email.add` +
Requires `authme.player.email.add` - **/email change** <oldEmail> <newEmail>: Change an email address of your account. -
Requires `authme.player.email.change` +
Requires `authme.player.email.change` - **/email recover** <email>: Recover your account using an Email address by sending a mail containing a new password. -
Requires `authme.player.email.recover` +
Requires `authme.player.email.recover` - **/email help** [query]: View detailed help for /email commands. - **/captcha** <captcha>: Captcha command for AuthMeReloaded. -
Requires `authme.player.captcha` +
Requires `authme.player.captcha` - **/captcha help** [query]: View detailed help for /captcha commands. -- **/converter** <job>: Converter command for AuthMeReloaded. -
Requires `authme.admin.converter` -- **/converter help** [query]: View detailed help for /converter commands. - --- -This page was automatically generated on the [AuthMe-Team/AuthMeReloaded repository](https://github.com/AuthMe-Team/AuthMeReloaded/tree/master/docs/) on Sun Feb 14 19:00:30 CET 2016 +This page was automatically generated on the [AuthMe-Team/AuthMeReloaded repository](https://github.com/AuthMe-Team/AuthMeReloaded/tree/master/docs/) on Thu Apr 07 17:17:20 CEST 2016 diff --git a/docs/hash_algorithms.md b/docs/hash_algorithms.md index a8ba9c6f7..6bc2a24fc 100644 --- a/docs/hash_algorithms.md +++ b/docs/hash_algorithms.md @@ -1,5 +1,5 @@ - + ## Hash Algorithms AuthMe supports the following hash algorithms for storing your passwords safely. @@ -17,7 +17,7 @@ JOOMLA | Recommended | 65 | | | Text | 32 | MD5 | Do not use | 32 | | | None | | MD5VB | Acceptable | 56 | | | Text | 16 | MYBB | Acceptable | 32 | | | Text | 8 | Y -PBKDF2 | Does not work | 330 | | | Text | 12 | +PBKDF2 | Does not work | 328 | | | Text | 12 | PBKDF2DJANGO | Acceptable | 77 | Y | | Text | 12 | PHPBB | Acceptable | 34 | | | Text | 16 | PHPFUSION | Do not use | 64 | Y | | | | Y @@ -82,4 +82,4 @@ or bad. --- -This page was automatically generated on the [AuthMe-Team/AuthMeReloaded repository](https://github.com/AuthMe-Team/AuthMeReloaded/tree/master/docs/) on Sun Feb 14 19:00:32 CET 2016 +This page was automatically generated on the [AuthMe-Team/AuthMeReloaded repository](https://github.com/AuthMe-Team/AuthMeReloaded/tree/master/docs/) on Thu Apr 07 17:17:22 CEST 2016 diff --git a/docs/permission_nodes.md b/docs/permission_nodes.md index 457f1102d..0591b97a3 100644 --- a/docs/permission_nodes.md +++ b/docs/permission_nodes.md @@ -1,5 +1,5 @@ - + ## AuthMe Permission Nodes The following are the permission nodes that are currently supported by the latest dev builds. @@ -42,7 +42,6 @@ The following are the permission nodes that are currently supported by the lates - **authme.player.unregister** – Command permission to unregister. - **authme.vip** – Permission node to identify VIP users. - --- -This page was automatically generated on the [AuthMe-Team/AuthMeReloaded repository](https://github.com/AuthMe-Team/AuthMeReloaded/tree/master/docs/) on Sun Feb 14 19:00:34 CET 2016 +This page was automatically generated on the [AuthMe-Team/AuthMeReloaded repository](https://github.com/AuthMe-Team/AuthMeReloaded/tree/master/docs/) on Thu Apr 07 17:17:24 CEST 2016 diff --git a/src/tools/commands/CommandPageCreater.java b/src/tools/commands/CommandPageCreater.java index 56d417223..8d92dbfbd 100644 --- a/src/tools/commands/CommandPageCreater.java +++ b/src/tools/commands/CommandPageCreater.java @@ -1,6 +1,5 @@ package commands; -import com.google.common.collect.ImmutableMap; import fr.xephi.authme.command.CommandArgumentDescription; import fr.xephi.authme.command.CommandDescription; import fr.xephi.authme.command.CommandInitializer; @@ -8,12 +7,12 @@ import fr.xephi.authme.command.CommandPermissions; import fr.xephi.authme.command.CommandUtils; import fr.xephi.authme.permission.PermissionNode; import utils.FileUtils; -import utils.TagReplacer; +import utils.TagValue.NestedTagValue; +import utils.TagValueHolder; import utils.ToolTask; import utils.ToolsConstants; import java.util.Collection; -import java.util.Map; import java.util.Scanner; import java.util.Set; @@ -29,31 +28,27 @@ public class CommandPageCreater implements ToolTask { @Override public void execute(Scanner scanner) { final Set baseCommands = CommandInitializer.buildCommands(); - final String template = FileUtils.readFromFile(ToolsConstants.TOOLS_SOURCE_ROOT - + "commands/command_entry.tpl.md"); - - StringBuilder commandsResult = new StringBuilder(); - addCommandsInfo(commandsResult, baseCommands, template); + NestedTagValue commandTags = new NestedTagValue(); + addCommandsInfo(commandTags, baseCommands); FileUtils.generateFileFromTemplate( ToolsConstants.TOOLS_SOURCE_ROOT + "commands/commands.tpl.md", OUTPUT_FILE, - ImmutableMap.of("commands", commandsResult.toString())); + TagValueHolder.create().put("commands", commandTags)); System.out.println("Wrote to '" + OUTPUT_FILE + "' with " + baseCommands.size() + " base commands."); } - private static void addCommandsInfo(StringBuilder sb, Collection commands, - final String template) { + private static void addCommandsInfo(NestedTagValue commandTags, Collection commands) { for (CommandDescription command : commands) { - Map tags = ImmutableMap.of( - "command", CommandUtils.constructCommandPath(command), - "description", command.getDetailedDescription(), - "arguments", formatArguments(command.getArguments()), - "permissions", formatPermissions(command.getCommandPermissions())); - sb.append(TagReplacer.applyReplacements(template, tags)); + TagValueHolder tags = TagValueHolder.create() + .put("command", CommandUtils.constructCommandPath(command)) + .put("description", command.getDetailedDescription()) + .put("arguments", formatArguments(command.getArguments())) + .put("permissions", formatPermissions(command.getCommandPermissions())); + commandTags.add(tags); if (!command.getChildren().isEmpty()) { - addCommandsInfo(sb, command.getChildren(), template); + addCommandsInfo(commandTags, command.getChildren()); } } } diff --git a/src/tools/commands/command_entry.tpl.md b/src/tools/commands/command_entry.tpl.md deleted file mode 100644 index c29784848..000000000 --- a/src/tools/commands/command_entry.tpl.md +++ /dev/null @@ -1,2 +0,0 @@ -- **{command}**{arguments}: {description}[permissions] -
Requires `{permissions}`[/permissions] diff --git a/src/tools/commands/commands.tpl.md b/src/tools/commands/commands.tpl.md index 0815e6ce4..c0f4da120 100644 --- a/src/tools/commands/commands.tpl.md +++ b/src/tools/commands/commands.tpl.md @@ -5,6 +5,9 @@ You can use the following commands to use the features of AuthMe. Mandatory arguments are marked with `< >` brackets; optional arguments are enclosed in square brackets (`[ ]`). -{commands} +[#commands] + - **{command}**{arguments}: {description}[permissions] +
Requires `{permissions}`[/permissions] +[/#commands] {gen_footer} diff --git a/src/tools/hashmethods/HashAlgorithmsDescriptionTask.java b/src/tools/hashmethods/HashAlgorithmsDescriptionTask.java index 129242b38..8c8cecbee 100644 --- a/src/tools/hashmethods/HashAlgorithmsDescriptionTask.java +++ b/src/tools/hashmethods/HashAlgorithmsDescriptionTask.java @@ -1,11 +1,11 @@ package hashmethods; -import com.google.common.collect.ImmutableMap; import fr.xephi.authme.security.HashAlgorithm; import fr.xephi.authme.settings.Settings; import fr.xephi.authme.util.WrapperMock; import utils.FileUtils; -import utils.TagReplacer; +import utils.TagValue.NestedTagValue; +import utils.TagValueHolder; import utils.ToolTask; import utils.ToolsConstants; @@ -33,30 +33,28 @@ public class HashAlgorithmsDescriptionTask implements ToolTask { // Gather info and construct a row for each method EncryptionMethodInfoGatherer infoGatherer = new EncryptionMethodInfoGatherer(); Map descriptions = infoGatherer.getDescriptions(); - final String methodRows = constructMethodRows(descriptions); + final NestedTagValue methodRows = constructMethodRows(descriptions); // Write to the docs file - Map tags = ImmutableMap.of("method_rows", methodRows); + TagValueHolder tags = TagValueHolder.create().put("algorithms", methodRows); FileUtils.generateFileFromTemplate(CUR_FOLDER + "hash_algorithms.tpl.md", OUTPUT_FILE, tags); } - private static String constructMethodRows(Map descriptions) { - final String rowTemplate = FileUtils.readFromFile(CUR_FOLDER + "hash_algorithms_row.tpl.md"); - StringBuilder result = new StringBuilder(); + private static NestedTagValue constructMethodRows(Map descriptions) { + NestedTagValue methodTags = new NestedTagValue(); for (Map.Entry entry : descriptions.entrySet()) { MethodDescription description = entry.getValue(); - Map tags = ImmutableMap.builder() + TagValueHolder tags = TagValueHolder.create() .put("name", asString(entry.getKey())) .put("recommendation", asString(description.getUsage())) .put("hash_length", asString(description.getHashLength())) .put("ascii_restricted", asString(description.isAsciiRestricted())) .put("salt_type", asString(description.getSaltType())) .put("salt_length", asString(description.getSaltLength())) - .put("separate_salt", asString(description.hasSeparateSalt())) - .build(); - result.append(TagReplacer.applyReplacements(rowTemplate, tags)); + .put("separate_salt", asString(description.hasSeparateSalt())); + methodTags.add(tags); } - return result.toString(); + return methodTags; } @Override diff --git a/src/tools/hashmethods/hash_algorithms.tpl.md b/src/tools/hashmethods/hash_algorithms.tpl.md index 883ae3239..73e85ba00 100644 --- a/src/tools/hashmethods/hash_algorithms.tpl.md +++ b/src/tools/hashmethods/hash_algorithms.tpl.md @@ -7,7 +7,10 @@ AuthMe supports the following hash algorithms for storing your passwords safely. Algorithm | Recommendation | Hash length | ASCII | | Salt type | Length | Separate? --------- | -------------- | ----------- | ----- | --- | --------- | ------ | --------- -{method_rows}CUSTOM | | | | | | | | +[#algorithms] +{name} | {recommendation} | {hash_length} | {ascii_restricted} | | {salt_type} | {salt_length} | {separate_salt} +[/#algorithms] +CUSTOM | | | | | | | | diff --git a/src/tools/hashmethods/hash_algorithms_row.tpl.md b/src/tools/hashmethods/hash_algorithms_row.tpl.md deleted file mode 100644 index 411d11271..000000000 --- a/src/tools/hashmethods/hash_algorithms_row.tpl.md +++ /dev/null @@ -1 +0,0 @@ -{name} | {recommendation} | {hash_length} | {ascii_restricted} | | {salt_type} | {salt_length} | {separate_salt} diff --git a/src/tools/permissions/PermissionsListWriter.java b/src/tools/permissions/PermissionsListWriter.java index 7c5999941..dc16cea22 100644 --- a/src/tools/permissions/PermissionsListWriter.java +++ b/src/tools/permissions/PermissionsListWriter.java @@ -1,8 +1,8 @@ package permissions; -import com.google.common.collect.ImmutableMap; import utils.FileUtils; -import utils.TagReplacer; +import utils.TagValue.NestedTagValue; +import utils.TagValueHolder; import utils.ToolTask; import utils.ToolsConstants; @@ -45,29 +45,25 @@ public class PermissionsListWriter implements ToolTask { } private static void generateAndWriteFile() { - final String permissionsTagValue = generatePermissionsList(); + final NestedTagValue permissionsTagValue = generatePermissionsList(); - Map tags = ImmutableMap.of("permissions", permissionsTagValue); + TagValueHolder tags = TagValueHolder.create().put("nodes", permissionsTagValue); FileUtils.generateFileFromTemplate( ToolsConstants.TOOLS_SOURCE_ROOT + "permissions/permission_nodes.tpl.md", PERMISSIONS_OUTPUT_FILE, tags); System.out.println("Wrote to '" + PERMISSIONS_OUTPUT_FILE + "'"); System.out.println("Before committing, please verify the output!"); } - private static String generatePermissionsList() { + private static NestedTagValue generatePermissionsList() { PermissionNodesGatherer gatherer = new PermissionNodesGatherer(); Map permissions = gatherer.gatherNodesWithJavaDoc(); - - final String template = FileUtils.readFromToolsFile("permissions/permission_node_entry.tpl.md"); - StringBuilder sb = new StringBuilder(); - + NestedTagValue permissionTags = new NestedTagValue(); for (Map.Entry entry : permissions.entrySet()) { - Map tags = ImmutableMap.of( - "node", entry.getKey(), - "description", entry.getValue()); - sb.append(TagReplacer.applyReplacements(template, tags)); + permissionTags.add(TagValueHolder.create() + .put("node", entry.getKey()) + .put("description", entry.getValue())); } - return sb.toString(); + return permissionTags; } private static void outputSimpleList() { diff --git a/src/tools/permissions/permission_node_entry.tpl.md b/src/tools/permissions/permission_node_entry.tpl.md deleted file mode 100644 index ab7f06872..000000000 --- a/src/tools/permissions/permission_node_entry.tpl.md +++ /dev/null @@ -1 +0,0 @@ -- **{node}** – {description} diff --git a/src/tools/permissions/permission_nodes.tpl.md b/src/tools/permissions/permission_nodes.tpl.md index 1f4208090..8d2a2b4f4 100644 --- a/src/tools/permissions/permission_nodes.tpl.md +++ b/src/tools/permissions/permission_nodes.tpl.md @@ -4,6 +4,8 @@ ## AuthMe Permission Nodes The following are the permission nodes that are currently supported by the latest dev builds. -{permissions} +[#nodes] + - **{node}** – {description} +[/#nodes] {gen_footer} diff --git a/src/tools/utils/FileUtils.java b/src/tools/utils/FileUtils.java index 02b9edddd..853965e93 100644 --- a/src/tools/utils/FileUtils.java +++ b/src/tools/utils/FileUtils.java @@ -6,7 +6,6 @@ import java.nio.file.Files; import java.nio.file.Paths; import java.nio.file.StandardOpenOption; import java.util.List; -import java.util.Map; /** * Utility class for reading from and writing to files. @@ -18,7 +17,7 @@ public final class FileUtils { private FileUtils() { } - public static void generateFileFromTemplate(String templateFile, String destinationFile, Map tags) { + public static void generateFileFromTemplate(String templateFile, String destinationFile, TagValueHolder tags) { String template = readFromFile(templateFile); String result = TagReplacer.applyReplacements(template, tags); writeToFile(destinationFile, result); @@ -56,8 +55,4 @@ public final class FileUtils { } } - public static String readFromToolsFile(String file) { - return readFromFile(ToolsConstants.TOOLS_SOURCE_ROOT + file); - } - } diff --git a/src/tools/utils/TagReplacer.java b/src/tools/utils/TagReplacer.java index 8e75ecd02..1197e0e73 100644 --- a/src/tools/utils/TagReplacer.java +++ b/src/tools/utils/TagReplacer.java @@ -1,6 +1,7 @@ package utils; -import fr.xephi.authme.util.StringUtils; +import utils.TagValue.NestedTagValue; +import utils.TagValue.TextTagValue; import java.util.Date; import java.util.Map; @@ -26,18 +27,25 @@ public class TagReplacer { * Replace a template with default tags and custom ones supplied by a map. * * @param template The template to process - * @param tags Map with additional tags, e.g. a map entry with key "foo" and value "bar" will replace + * @param tagValues Map with additional tags, e.g. a map entry with key "foo" and value "bar" will replace * any occurrences of "{foo}" to "bar". * @return The filled template */ - public static String applyReplacements(String template, Map tags) { + public static String applyReplacements(String template, TagValueHolder tagValues) { String result = template; - for (Map.Entry tagRule : tags.entrySet()) { + for (Map.Entry> tagRule : tagValues.getValues().entrySet()) { final String name = tagRule.getKey(); - final String value = tagRule.getValue(); - result = replaceOptionalTag(result, name, value) - .replace("{" + name + "}", value); + if (tagRule.getValue() instanceof TextTagValue) { + final TextTagValue value = (TextTagValue) tagRule.getValue(); + result = replaceOptionalTag(result, name, value) + .replace("{" + name + "}", value.getValue()); + } else if (tagRule.getValue() instanceof NestedTagValue) { + final NestedTagValue value = (NestedTagValue) tagRule.getValue(); + result = replaceIterateTag(replaceOptionalTag(result, name, value), name, value); + } else { + throw new IllegalStateException("Unknown tag value type"); + } } return applyReplacements(result); } @@ -58,14 +66,14 @@ public class TagReplacer { + " on " + curDate); } - private static String replaceOptionalTag(String text, String tagName, String tagValue) { + private static String replaceOptionalTag(String text, String tagName, TagValue tagValue) { Pattern regex = Pattern.compile("\\[" + tagName + "](.*?)\\[/" + tagName + "]", Pattern.DOTALL); Matcher matcher = regex.matcher(text); if (!matcher.find()) { // Couldn't find results, so just return text as it is return text; - } else if (StringUtils.isEmpty(tagValue)) { + } else if (tagValue.isEmpty()) { // Tag is empty, replace [tagName]some_text[/tagName] to nothing return matcher.replaceAll(""); } else { @@ -74,5 +82,30 @@ public class TagReplacer { } } + /** + * Replace iterating tags with the value. Tags of the type [#tag]...[/#tag] specify to iterate over the + * entries in {@link NestedTagValue} and to apply any replacements in there. + * + * @param text The file text + * @param tagName The tag name to handle + * @param tagValue The associated value + * @return The text with the applied replacement + */ + private static String replaceIterateTag(String text, String tagName, NestedTagValue tagValue) { + Pattern regex = Pattern.compile("\\[#" + tagName + "](.*?)\\[/#" + tagName + "]\\s?", Pattern.DOTALL); + Matcher matcher = regex.matcher(text); + + if (!matcher.find()) { + return text; + } else if (tagValue.isEmpty()) { + return matcher.replaceAll(""); + } + final String innerTemplate = matcher.group(1).trim() + "\n"; + String result = ""; + for (TagValueHolder entry : tagValue.getValue()) { + result += applyReplacements(innerTemplate, entry); + } + return matcher.replaceAll(result); + } } diff --git a/src/tools/utils/TagValue.java b/src/tools/utils/TagValue.java new file mode 100644 index 000000000..03b34097e --- /dev/null +++ b/src/tools/utils/TagValue.java @@ -0,0 +1,51 @@ +package utils; + +import java.util.ArrayList; +import java.util.List; + + +public abstract class TagValue { + + private final T value; + + public TagValue(T value) { + this.value = value; + } + + public T getValue() { + return value; + } + + public abstract boolean isEmpty(); + + public static final class TextTagValue extends TagValue { + public TextTagValue(String value) { + super(value); + } + + @Override + public boolean isEmpty() { + return getValue().isEmpty(); + } + + @Override + public int hashCode() { + return super.hashCode(); + } + } + + public static final class NestedTagValue extends TagValue> { + public NestedTagValue() { + super(new ArrayList()); + } + + @Override + public boolean isEmpty() { + return getValue().isEmpty(); + } + + public void add(TagValueHolder entry) { + getValue().add(entry); + } + } +} diff --git a/src/tools/utils/TagValueHolder.java b/src/tools/utils/TagValueHolder.java new file mode 100644 index 000000000..e2bd09b09 --- /dev/null +++ b/src/tools/utils/TagValueHolder.java @@ -0,0 +1,34 @@ +package utils; + +import utils.TagValue.TextTagValue; + +import java.util.HashMap; +import java.util.Map; + + +public class TagValueHolder { + + private Map> values; + + private TagValueHolder() { + this.values = new HashMap<>(); + } + + public static TagValueHolder create() { + return new TagValueHolder(); + } + + public TagValueHolder put(String key, TagValue value) { + values.put(key, value); + return this; + } + + public TagValueHolder put(String key, String value) { + values.put(key, new TextTagValue(value)); + return this; + } + + public Map> getValues() { + return values; + } +}