Merge "Switch from pegdown to flexmark-java"
diff --git a/Documentation/dev-plugins.txt b/Documentation/dev-plugins.txt
index 5c008c7..6517262 100644
--- a/Documentation/dev-plugins.txt
+++ b/Documentation/dev-plugins.txt
@@ -2534,7 +2534,7 @@
attribute.
Documentation may be written in the Markdown flavor
-link:https://github.com/sirthias/pegdown[pegdown]
+link:https://github.com/vsch/flexmark-java[flexmark-java]
if the file name ends with `.md`. Gerrit will automatically convert
Markdown to HTML if accessed with extension `.html`.
diff --git a/WORKSPACE b/WORKSPACE
index e4d62e8..3e0fdbc 100644
--- a/WORKSPACE
+++ b/WORKSPACE
@@ -351,22 +351,163 @@
sha1 = "959a0c62f9a5c2309e0ad0b0589c74d69e101241",
)
+FLEXMARK_VERS = "0.32.4"
+
maven_jar(
- name = "pegdown",
- artifact = "org.pegdown:pegdown:1.6.0",
- sha1 = "231ae49d913467deb2027d0b8a0b68b231deef4f",
+ name = "flexmark",
+ artifact = "com.vladsch.flexmark:flexmark:" + FLEXMARK_VERS,
+ sha1 = "61323e756ebaf1936d143afdd70277251206005e",
)
maven_jar(
- name = "grappa",
- artifact = "com.github.parboiled1:grappa:1.0.4",
- sha1 = "ad4b44b9c305dad7aa1e680d4b5c8eec9c4fd6f5",
+ name = "flexmark-ext-abbreviation",
+ artifact = "com.vladsch.flexmark:flexmark-ext-abbreviation:" + FLEXMARK_VERS,
+ sha1 = "726e5978edc68403286a88f9366f572af6a76506",
)
maven_jar(
- name = "jitescript",
- artifact = "me.qmx.jitescript:jitescript:0.4.0",
- sha1 = "2e35862b0435c1b027a21f3d6eecbe50e6e08d54",
+ name = "flexmark-ext-anchorlink",
+ artifact = "com.vladsch.flexmark:flexmark-ext-anchorlink:" + FLEXMARK_VERS,
+ sha1 = "ec3bcf718dae98eec2829e351eda59d63eeac94b",
+)
+
+maven_jar(
+ name = "flexmark-ext-autolink",
+ artifact = "com.vladsch.flexmark:flexmark-ext-autolink:" + FLEXMARK_VERS,
+ sha1 = "2103b77836f266775d20e5fe2a6ba51d5c8b63c8",
+)
+
+maven_jar(
+ name = "flexmark-ext-definition",
+ artifact = "com.vladsch.flexmark:flexmark-ext-definition:" + FLEXMARK_VERS,
+ sha1 = "c896f2291ad2b9b253ee2949865598a1e9454c55",
+)
+
+maven_jar(
+ name = "flexmark-ext-emoji",
+ artifact = "com.vladsch.flexmark:flexmark-ext-emoji:" + FLEXMARK_VERS,
+ sha1 = "f167c3073b7bb5ced944c4837ae655b2e5ea7a1c",
+)
+
+maven_jar(
+ name = "flexmark-ext-escaped-character",
+ artifact = "com.vladsch.flexmark:flexmark-ext-escaped-character:" + FLEXMARK_VERS,
+ sha1 = "23004d741824f0c564de2c72e579ca67b01a4623",
+)
+
+maven_jar(
+ name = "flexmark-ext-footnotes",
+ artifact = "com.vladsch.flexmark:flexmark-ext-footnotes:" + FLEXMARK_VERS,
+ sha1 = "c9b98778b94fee2efd886e47317944f7fcb8a037",
+)
+
+maven_jar(
+ name = "flexmark-ext-gfm-issues",
+ artifact = "com.vladsch.flexmark:flexmark-ext-gfm-issues:" + FLEXMARK_VERS,
+ sha1 = "0d543c46a6025c1b8342f0e99155208276c86966",
+)
+
+maven_jar(
+ name = "flexmark-ext-gfm-strikethrough",
+ artifact = "com.vladsch.flexmark:flexmark-ext-gfm-strikethrough:" + FLEXMARK_VERS,
+ sha1 = "95414bb07c8429389374b66dd42a9da2e17c693b",
+)
+
+maven_jar(
+ name = "flexmark-ext-gfm-tables",
+ artifact = "com.vladsch.flexmark:flexmark-ext-gfm-tables:" + FLEXMARK_VERS,
+ sha1 = "1cbc2bc4de374b75d9dff812054d51aa84a61d5d",
+)
+
+maven_jar(
+ name = "flexmark-ext-gfm-tasklist",
+ artifact = "com.vladsch.flexmark:flexmark-ext-gfm-tasklist:" + FLEXMARK_VERS,
+ sha1 = "c93ed560ff2047a4c0cdbfe563a3873574404477",
+)
+
+maven_jar(
+ name = "flexmark-ext-gfm-users",
+ artifact = "com.vladsch.flexmark:flexmark-ext-gfm-users:" + FLEXMARK_VERS,
+ sha1 = "c58c74ba4a51c2376760f2c011a6bbf21c39455d",
+)
+
+maven_jar(
+ name = "flexmark-ext-ins",
+ artifact = "com.vladsch.flexmark:flexmark-ext-ins:" + FLEXMARK_VERS,
+ sha1 = "76d712a244df71f875f66244407d3c51596712ae",
+)
+
+maven_jar(
+ name = "flexmark-ext-jekyll-front-matter",
+ artifact = "com.vladsch.flexmark:flexmark-ext-jekyll-front-matter:" + FLEXMARK_VERS,
+ sha1 = "8603af459c0215c58f0a6debd903201941f7d9e9",
+)
+
+maven_jar(
+ name = "flexmark-ext-superscript",
+ artifact = "com.vladsch.flexmark:flexmark-ext-superscript:" + FLEXMARK_VERS,
+ sha1 = "9ad131c9f6bec18e357c9238e78211d88a4474b9",
+)
+
+maven_jar(
+ name = "flexmark-ext-tables",
+ artifact = "com.vladsch.flexmark:flexmark-ext-tables:" + FLEXMARK_VERS,
+ sha1 = "4410446d9e77761331e474f7b920d975342cd9a1",
+)
+
+maven_jar(
+ name = "flexmark-ext-toc",
+ artifact = "com.vladsch.flexmark:flexmark-ext-toc:" + FLEXMARK_VERS,
+ sha1 = "3ad7c7ec4f7a5cce181a710ba5f689eeec8a3e52",
+)
+
+maven_jar(
+ name = "flexmark-ext-typographic",
+ artifact = "com.vladsch.flexmark:flexmark-ext-typographic:" + FLEXMARK_VERS,
+ sha1 = "c9df5e7631471120e67bd3cde827af1770d583c7",
+)
+
+maven_jar(
+ name = "flexmark-ext-wikilink",
+ artifact = "com.vladsch.flexmark:flexmark-ext-wikilink:" + FLEXMARK_VERS,
+ sha1 = "dc3a988dcd9055c226845cd332f8838096aed32b",
+)
+
+maven_jar(
+ name = "flexmark-ext-yaml-front-matter",
+ artifact = "com.vladsch.flexmark:flexmark-ext-yaml-front-matter:" + FLEXMARK_VERS,
+ sha1 = "588c6233cb11fa1395ab58fec8034bfa9893a3d9",
+)
+
+maven_jar(
+ name = "flexmark-formatter",
+ artifact = "com.vladsch.flexmark:flexmark-formatter:" + FLEXMARK_VERS,
+ sha1 = "6c0869ee52ab22202c52dd1674da821e6a579a65",
+)
+
+maven_jar(
+ name = "flexmark-html-parser",
+ artifact = "com.vladsch.flexmark:flexmark-html-parser:" + FLEXMARK_VERS,
+ sha1 = "95a3a8a68e536f916df8a7a4988ef4aacf9a573f",
+)
+
+maven_jar(
+ name = "flexmark-profile-pegdown",
+ artifact = "com.vladsch.flexmark:flexmark-profile-pegdown:" + FLEXMARK_VERS,
+ sha1 = "a760923a1f03780b2e947a4e8e9b50785e0204e5",
+)
+
+maven_jar(
+ name = "flexmark-util",
+ artifact = "com.vladsch.flexmark:flexmark-util:" + FLEXMARK_VERS,
+ sha1 = "1f6fce06245c0e1660c56db2af0a1ec0b023a164",
+)
+
+# Transitive dependency of flexmark
+maven_jar(
+ name = "autolink",
+ artifact = "org.nibor.autolink:autolink:0.7.0",
+ sha1 = "649f9f13422cf50c926febe6035662ae25dc89b2",
)
GREENMAIL_VERS = "1.5.5"
diff --git a/java/com/google/gerrit/server/BUILD b/java/com/google/gerrit/server/BUILD
index 4002a4f..96fcd39 100644
--- a/java/com/google/gerrit/server/BUILD
+++ b/java/com/google/gerrit/server/BUILD
@@ -48,9 +48,34 @@
"//java/org/apache/commons/net",
"//java/org/eclipse/jgit:server",
"//lib:args4j",
+ "//lib:autolink",
"//lib:automaton",
"//lib:blame-cache",
- "//lib:grappa",
+ "//lib:flexmark",
+ "//lib:flexmark-ext-abbreviation",
+ "//lib:flexmark-ext-anchorlink",
+ "//lib:flexmark-ext-autolink",
+ "//lib:flexmark-ext-definition",
+ "//lib:flexmark-ext-emoji",
+ "//lib:flexmark-ext-escaped-character",
+ "//lib:flexmark-ext-footnotes",
+ "//lib:flexmark-ext-gfm-issues",
+ "//lib:flexmark-ext-gfm-strikethrough",
+ "//lib:flexmark-ext-gfm-tables",
+ "//lib:flexmark-ext-gfm-tasklist",
+ "//lib:flexmark-ext-gfm-users",
+ "//lib:flexmark-ext-ins",
+ "//lib:flexmark-ext-jekyll-front-matter",
+ "//lib:flexmark-ext-superscript",
+ "//lib:flexmark-ext-tables",
+ "//lib:flexmark-ext-toc",
+ "//lib:flexmark-ext-typographic",
+ "//lib:flexmark-ext-wikilink",
+ "//lib:flexmark-ext-yaml-front-matter",
+ "//lib:flexmark-formatter",
+ "//lib:flexmark-html-parser",
+ "//lib:flexmark-profile-pegdown",
+ "//lib:flexmark-util",
"//lib:gson",
"//lib:guava",
"//lib:guava-retrying",
@@ -59,7 +84,6 @@
"//lib:jsch",
"//lib:juniversalchardet",
"//lib:mime-util",
- "//lib:pegdown",
"//lib:protobuf",
"//lib:servlet-api-3_1",
"//lib:soy",
diff --git a/java/com/google/gerrit/server/audit/BUILD b/java/com/google/gerrit/server/audit/BUILD
index 5efdc5a..d85668e 100644
--- a/java/com/google/gerrit/server/audit/BUILD
+++ b/java/com/google/gerrit/server/audit/BUILD
@@ -24,9 +24,34 @@
"//java/org/apache/commons/net",
"//java/org/eclipse/jgit:server",
"//lib:args4j",
+ "//lib:autolink",
"//lib:automaton",
"//lib:blame-cache",
- "//lib:grappa",
+ "//lib:flexmark",
+ "//lib:flexmark-ext-abbreviation",
+ "//lib:flexmark-ext-anchorlink",
+ "//lib:flexmark-ext-autolink",
+ "//lib:flexmark-ext-definition",
+ "//lib:flexmark-ext-emoji",
+ "//lib:flexmark-ext-escaped-character",
+ "//lib:flexmark-ext-footnotes",
+ "//lib:flexmark-ext-gfm-issues",
+ "//lib:flexmark-ext-gfm-strikethrough",
+ "//lib:flexmark-ext-gfm-tables",
+ "//lib:flexmark-ext-gfm-tasklist",
+ "//lib:flexmark-ext-gfm-users",
+ "//lib:flexmark-ext-ins",
+ "//lib:flexmark-ext-jekyll-front-matter",
+ "//lib:flexmark-ext-superscript",
+ "//lib:flexmark-ext-tables",
+ "//lib:flexmark-ext-toc",
+ "//lib:flexmark-ext-typographic",
+ "//lib:flexmark-ext-wikilink",
+ "//lib:flexmark-ext-yaml-front-matter",
+ "//lib:flexmark-formatter",
+ "//lib:flexmark-html-parser",
+ "//lib:flexmark-profile-pegdown",
+ "//lib:flexmark-util",
"//lib:gson",
"//lib:guava",
"//lib:guava-retrying",
@@ -35,7 +60,6 @@
"//lib:jsch",
"//lib:juniversalchardet",
"//lib:mime-util",
- "//lib:pegdown",
"//lib:protobuf",
"//lib:servlet-api-3_1",
"//lib:soy",
diff --git a/java/com/google/gerrit/server/documentation/MarkdownFormatter.java b/java/com/google/gerrit/server/documentation/MarkdownFormatter.java
index a7f9a05..2eb46f1 100644
--- a/java/com/google/gerrit/server/documentation/MarkdownFormatter.java
+++ b/java/com/google/gerrit/server/documentation/MarkdownFormatter.java
@@ -14,30 +14,33 @@
package com.google.gerrit.server.documentation;
+import static com.vladsch.flexmark.profiles.pegdown.Extensions.ALL;
+import static com.vladsch.flexmark.profiles.pegdown.Extensions.HARDWRAPS;
+import static com.vladsch.flexmark.profiles.pegdown.Extensions.SUPPRESS_ALL_HTML;
import static java.nio.charset.StandardCharsets.UTF_8;
-import static org.pegdown.Extensions.ALL;
-import static org.pegdown.Extensions.HARDWRAPS;
-import static org.pegdown.Extensions.SUPPRESS_ALL_HTML;
import com.google.common.base.Strings;
import com.google.common.flogger.FluentLogger;
+import com.vladsch.flexmark.Extension;
+import com.vladsch.flexmark.ast.Block;
+import com.vladsch.flexmark.ast.Heading;
+import com.vladsch.flexmark.ast.Node;
+import com.vladsch.flexmark.ast.util.TextCollectingVisitor;
+import com.vladsch.flexmark.html.HtmlRenderer;
+import com.vladsch.flexmark.parser.Parser;
+import com.vladsch.flexmark.profiles.pegdown.PegdownOptionsAdapter;
+import com.vladsch.flexmark.util.options.MutableDataHolder;
import java.io.FileNotFoundException;
import java.io.IOException;
import java.io.InputStream;
import java.io.UnsupportedEncodingException;
import java.net.URL;
import java.nio.charset.Charset;
+import java.util.ArrayList;
import java.util.concurrent.atomic.AtomicBoolean;
import org.apache.commons.lang.StringEscapeUtils;
import org.eclipse.jgit.util.RawParseUtils;
import org.eclipse.jgit.util.TemporaryBuffer;
-import org.pegdown.LinkRenderer;
-import org.pegdown.PegDownProcessor;
-import org.pegdown.ToHtmlSerializer;
-import org.pegdown.ast.HeaderNode;
-import org.pegdown.ast.Node;
-import org.pegdown.ast.RootNode;
-import org.pegdown.ast.TextNode;
public class MarkdownFormatter {
private static final FluentLogger logger = FluentLogger.forEnclosingClass();
@@ -48,9 +51,9 @@
AtomicBoolean file = new AtomicBoolean();
String src;
try {
- src = readPegdownCss(file);
+ src = readFlexMarkJavaCss(file);
} catch (IOException err) {
- logger.atWarning().withCause(err).log("Cannot load pegdown.css");
+ logger.atWarning().withCause(err).log("Cannot load flexmark-java.css");
src = "";
}
defaultCss = file.get() ? null : src;
@@ -61,9 +64,9 @@
return defaultCss;
}
try {
- return readPegdownCss(new AtomicBoolean());
+ return readFlexMarkJavaCss(new AtomicBoolean());
} catch (IOException err) {
- logger.atWarning().withCause(err).log("Cannot load pegdown.css");
+ logger.atWarning().withCause(err).log("Cannot load flexmark-java.css");
return "";
}
}
@@ -81,8 +84,28 @@
return this;
}
+ private MutableDataHolder markDownOptions() {
+ int options = ALL & ~(HARDWRAPS);
+ if (suppressHtml) {
+ options |= SUPPRESS_ALL_HTML;
+ }
+
+ MutableDataHolder optionsExt =
+ PegdownOptionsAdapter.flexmarkOptions(
+ options, MarkdownFormatterHeader.HeadingExtension.create())
+ .toMutable();
+
+ ArrayList<Extension> extensions = new ArrayList<>();
+ for (Extension extension : optionsExt.get(com.vladsch.flexmark.parser.Parser.EXTENSIONS)) {
+ extensions.add(extension);
+ }
+
+ return optionsExt;
+ }
+
public byte[] markdownToDocHtml(String md, String charEnc) throws UnsupportedEncodingException {
- RootNode root = parseMarkdown(md);
+ Node root = parseMarkdown(md);
+ HtmlRenderer renderer = HtmlRenderer.builder(markDownOptions()).build();
String title = findTitle(root);
StringBuilder html = new StringBuilder();
@@ -100,7 +123,7 @@
html.append("\n</style>");
html.append("</head>");
html.append("<body>\n");
- html.append(new ToHtmlSerializer(new LinkRenderer()).toHtml(root));
+ html.append(renderer.render(root));
html.append("\n</body></html>");
return html.toString().getBytes(charEnc);
}
@@ -111,38 +134,36 @@
}
private String findTitle(Node root) {
- if (root instanceof HeaderNode) {
- HeaderNode h = (HeaderNode) root;
- if (h.getLevel() == 1 && h.getChildren() != null && !h.getChildren().isEmpty()) {
- StringBuilder b = new StringBuilder();
- for (Node n : root.getChildren()) {
- if (n instanceof TextNode) {
- b.append(((TextNode) n).getText());
- }
- }
- return b.toString();
+ if (root instanceof Heading) {
+ Heading h = (Heading) root;
+ if (h.getLevel() == 1 && h.hasChildren()) {
+ TextCollectingVisitor collectingVisitor = new TextCollectingVisitor();
+ return collectingVisitor.collectAndGetText(h);
}
}
- for (Node n : root.getChildren()) {
- String title = findTitle(n);
- if (title != null) {
- return title;
+ if (root instanceof Block && root.hasChildren()) {
+ Node child = root.getFirstChild();
+ while (child != null) {
+ String title = findTitle(child);
+ if (title != null) {
+ return title;
+ }
+ child = child.getNext();
}
}
+
return null;
}
- private RootNode parseMarkdown(String md) {
- int options = ALL & ~(HARDWRAPS);
- if (suppressHtml) {
- options |= SUPPRESS_ALL_HTML;
- }
- return new PegDownProcessor(options).parseMarkdown(md.toCharArray());
+ private Node parseMarkdown(String md) {
+ Parser parser = Parser.builder(markDownOptions()).build();
+ Node document = parser.parse(md);
+ return document;
}
- private static String readPegdownCss(AtomicBoolean file) throws IOException {
- String name = "pegdown.css";
+ private static String readFlexMarkJavaCss(AtomicBoolean file) throws IOException {
+ String name = "flexmark-java.css";
URL url = MarkdownFormatter.class.getResource(name);
if (url == null) {
throw new FileNotFoundException("Resource " + name);
diff --git a/java/com/google/gerrit/server/documentation/MarkdownFormatterHeader.java b/java/com/google/gerrit/server/documentation/MarkdownFormatterHeader.java
new file mode 100644
index 0000000..482b058
--- /dev/null
+++ b/java/com/google/gerrit/server/documentation/MarkdownFormatterHeader.java
@@ -0,0 +1,162 @@
+// Copyright (C) 2018 The Android Open Source Project
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+package com.google.gerrit.server.documentation;
+
+import com.google.common.flogger.FluentLogger;
+import com.vladsch.flexmark.ast.Heading;
+import com.vladsch.flexmark.ast.Node;
+import com.vladsch.flexmark.ext.anchorlink.AnchorLink;
+import com.vladsch.flexmark.ext.anchorlink.internal.AnchorLinkNodeRenderer;
+import com.vladsch.flexmark.html.CustomNodeRenderer;
+import com.vladsch.flexmark.html.HtmlRenderer;
+import com.vladsch.flexmark.html.HtmlRenderer.HtmlRendererExtension;
+import com.vladsch.flexmark.html.HtmlWriter;
+import com.vladsch.flexmark.html.renderer.DelegatingNodeRendererFactory;
+import com.vladsch.flexmark.html.renderer.NodeRenderer;
+import com.vladsch.flexmark.html.renderer.NodeRendererContext;
+import com.vladsch.flexmark.html.renderer.NodeRendererFactory;
+import com.vladsch.flexmark.html.renderer.NodeRenderingHandler;
+import com.vladsch.flexmark.profiles.pegdown.Extensions;
+import com.vladsch.flexmark.profiles.pegdown.PegdownOptionsAdapter;
+import com.vladsch.flexmark.util.options.DataHolder;
+import com.vladsch.flexmark.util.options.MutableDataHolder;
+import java.util.Arrays;
+import java.util.HashSet;
+import java.util.Set;
+
+public class MarkdownFormatterHeader {
+ private static final FluentLogger logger = FluentLogger.forEnclosingClass();
+
+ static class HeadingExtension implements HtmlRendererExtension {
+ @Override
+ public void rendererOptions(final MutableDataHolder options) {
+ // add any configuration settings to options you want to apply to everything, here
+ }
+
+ @Override
+ public void extend(final HtmlRenderer.Builder rendererBuilder, final String rendererType) {
+ rendererBuilder.nodeRendererFactory(new HeadingNodeRenderer.Factory());
+ }
+
+ static HeadingExtension create() {
+ return new HeadingExtension();
+ }
+ }
+
+ static class HeadingNodeRenderer implements NodeRenderer {
+ public HeadingNodeRenderer(DataHolder options) {}
+
+ @Override
+ public Set<NodeRenderingHandler<?>> getNodeRenderingHandlers() {
+ return new HashSet<NodeRenderingHandler<? extends Node>>(
+ Arrays.asList(
+ new NodeRenderingHandler<AnchorLink>(
+ AnchorLink.class,
+ new CustomNodeRenderer<AnchorLink>() {
+ @Override
+ public void render(
+ AnchorLink node, NodeRendererContext context, HtmlWriter html) {
+ HeadingNodeRenderer.this.render(node, context, html);
+ }
+ }),
+ new NodeRenderingHandler<Heading>(
+ Heading.class,
+ new CustomNodeRenderer<Heading>() {
+ @Override
+ public void render(Heading node, NodeRendererContext context, HtmlWriter html) {
+ HeadingNodeRenderer.this.render(node, context, html);
+ }
+ })));
+ }
+
+ void render(final AnchorLink node, final NodeRendererContext context, final HtmlWriter html) {
+ Node parent = node.getParent();
+
+ if (parent instanceof Heading && ((Heading) parent).getLevel() == 1) {
+ // render without anchor link
+ context.renderChildren(node);
+ } else {
+ context.delegateRender();
+ }
+ }
+
+ static boolean haveExtension(int extensions, int flags) {
+ return (extensions & flags) != 0;
+ }
+
+ static boolean haveAllExtensions(int extensions, int flags) {
+ return (extensions & flags) == flags;
+ }
+
+ void render(final Heading node, final NodeRendererContext context, final HtmlWriter html) {
+ if (node.getLevel() == 1) {
+ // render without anchor link
+ final int extensions = context.getOptions().get(PegdownOptionsAdapter.PEGDOWN_EXTENSIONS);
+ if (context.getHtmlOptions().renderHeaderId
+ || haveExtension(extensions, Extensions.ANCHORLINKS)
+ || haveAllExtensions(
+ extensions, Extensions.EXTANCHORLINKS | Extensions.EXTANCHORLINKS_WRAP)) {
+ String id = context.getNodeId(node);
+ if (id != null) {
+ html.attr("id", id);
+ }
+ }
+
+ if (context.getHtmlOptions().sourcePositionParagraphLines) {
+ html.srcPos(node.getChars())
+ .withAttr()
+ .tagLine(
+ "h" + node.getLevel(),
+ new Runnable() {
+ @Override
+ public void run() {
+ html.srcPos(node.getText()).withAttr().tag("span");
+ context.renderChildren(node);
+ html.tag("/span");
+ }
+ });
+ } else {
+ html.srcPos(node.getText())
+ .withAttr()
+ .tagLine(
+ "h" + node.getLevel(),
+ new Runnable() {
+ @Override
+ public void run() {
+ context.renderChildren(node);
+ }
+ });
+ }
+ } else {
+ context.delegateRender();
+ }
+ }
+
+ public static class Factory implements DelegatingNodeRendererFactory {
+ @Override
+ public NodeRenderer create(final DataHolder options) {
+ return new HeadingNodeRenderer(options);
+ }
+
+ @Override
+ public Set<Class<? extends NodeRendererFactory>> getDelegates() {
+ Set<Class<? extends NodeRendererFactory>> delegates =
+ new HashSet<Class<? extends NodeRendererFactory>>();
+ delegates.add(AnchorLinkNodeRenderer.Factory.class);
+ return delegates;
+ }
+ }
+ }
+}
diff --git a/javatests/com/google/gerrit/mail/BUILD b/javatests/com/google/gerrit/mail/BUILD
index 488bbcc..2fd8f24 100644
--- a/javatests/com/google/gerrit/mail/BUILD
+++ b/javatests/com/google/gerrit/mail/BUILD
@@ -22,7 +22,6 @@
"//java/com/google/gerrit/server/project/testing:project-test-util",
"//java/com/google/gerrit/testing:gerrit-test-util",
"//java/org/eclipse/jgit:server",
- "//lib:grappa",
"//lib:gson",
"//lib:guava-retrying",
"//lib:gwtorm",
diff --git a/javatests/com/google/gerrit/server/BUILD b/javatests/com/google/gerrit/server/BUILD
index b413481..29e9a0b 100644
--- a/javatests/com/google/gerrit/server/BUILD
+++ b/javatests/com/google/gerrit/server/BUILD
@@ -55,7 +55,6 @@
"//java/com/google/gerrit/testing:gerrit-test-util",
"//java/com/google/gerrit/truth",
"//java/org/eclipse/jgit:server",
- "//lib:grappa",
"//lib:gson",
"//lib:guava",
"//lib:guava-retrying",
diff --git a/javatests/com/google/gerrit/server/util/ParboiledTest.java b/javatests/com/google/gerrit/server/util/ParboiledTest.java
deleted file mode 100644
index 3bcfb56..0000000
--- a/javatests/com/google/gerrit/server/util/ParboiledTest.java
+++ /dev/null
@@ -1,74 +0,0 @@
-// Copyright (C) 2014 The Android Open Source Project
-//
-// Licensed under the Apache License, Version 2.0 (the "License");
-// you may not use this file except in compliance with the License.
-// You may obtain a copy of the License at
-//
-// http://www.apache.org/licenses/LICENSE-2.0
-//
-// Unless required by applicable law or agreed to in writing, software
-// distributed under the License is distributed on an "AS IS" BASIS,
-// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-// See the License for the specific language governing permissions and
-// limitations under the License.
-
-package com.google.gerrit.server.util;
-
-import static com.google.common.truth.Truth.assertThat;
-
-import org.junit.Before;
-import org.junit.Test;
-import org.parboiled.BaseParser;
-import org.parboiled.Parboiled;
-import org.parboiled.Rule;
-import org.parboiled.annotations.BuildParseTree;
-import org.parboiled.parserunners.ReportingParseRunner;
-import org.parboiled.support.ParseTreeUtils;
-import org.parboiled.support.ParsingResult;
-
-public class ParboiledTest {
-
- private static final String EXPECTED =
- "[Expression] '42'\n"
- + " [Term] '42'\n"
- + " [Factor] '42'\n"
- + " [Number] '42'\n"
- + " [0..9] '4'\n"
- + " [0..9] '2'\n"
- + " [zeroOrMore]\n"
- + " [zeroOrMore]\n";
-
- private CalculatorParser parser;
-
- @Before
- public void setUp() {
- parser = Parboiled.createParser(CalculatorParser.class);
- }
-
- @Test
- public void test() {
- ParsingResult<String> result = new ReportingParseRunner<String>(parser.Expression()).run("42");
- assertThat(result.isSuccess()).isTrue();
- // next test is optional; we could stop here.
- assertThat(ParseTreeUtils.printNodeTree(result)).isEqualTo(EXPECTED);
- }
-
- @BuildParseTree
- static class CalculatorParser extends BaseParser<Object> {
- Rule Expression() {
- return sequence(Term(), zeroOrMore(anyOf("+-"), Term()));
- }
-
- Rule Term() {
- return sequence(Factor(), zeroOrMore(anyOf("*/"), Factor()));
- }
-
- Rule Factor() {
- return firstOf(Number(), sequence('(', Expression(), ')'));
- }
-
- Rule Number() {
- return oneOrMore(charRange('0', '9'));
- }
- }
-}
diff --git a/javatests/com/google/gerrit/server/util/git/BUILD b/javatests/com/google/gerrit/server/util/git/BUILD
index 928705c..61a776fa 100644
--- a/javatests/com/google/gerrit/server/util/git/BUILD
+++ b/javatests/com/google/gerrit/server/util/git/BUILD
@@ -12,7 +12,6 @@
"//java/com/google/gerrit/server/util/git",
"//java/com/google/gerrit/truth",
"//java/org/eclipse/jgit:server",
- "//lib:grappa",
"//lib:gson",
"//lib:guava",
"//lib:guava-retrying",
diff --git a/lib/BUILD b/lib/BUILD
index 38b0b80..e5034c9 100644
--- a/lib/BUILD
+++ b/lib/BUILD
@@ -123,32 +123,257 @@
)
java_library(
- name = "pegdown",
- data = ["//lib:LICENSE-Apache2.0"],
+ name = "flexmark",
+ data = ["//lib:LICENSE-flexmark"],
visibility = ["//visibility:public"],
- exports = ["@pegdown//jar"],
- runtime_deps = [":grappa"],
-)
-
-java_library(
- name = "grappa",
- data = ["//lib:LICENSE-Apache2.0"],
- visibility = ["//visibility:public"],
- exports = ["@grappa//jar"],
+ exports = ["@flexmark//jar"],
runtime_deps = [
- ":jitescript",
- "//lib/ow2:ow2-asm",
- "//lib/ow2:ow2-asm-analysis",
- "//lib/ow2:ow2-asm-tree",
- "//lib/ow2:ow2-asm-util",
+ ":flexmark-ext-abbreviation",
],
)
java_library(
- name = "jitescript",
- data = ["//lib:LICENSE-Apache2.0"],
+ name = "flexmark-ext-abbreviation",
+ data = ["//lib:LICENSE-flexmark"],
visibility = ["//visibility:public"],
- exports = ["@jitescript//jar"],
+ exports = ["@flexmark-ext-abbreviation//jar"],
+ runtime_deps = [
+ ":flexmark-ext-anchorlink",
+ ],
+)
+
+java_library(
+ name = "flexmark-ext-anchorlink",
+ data = ["//lib:LICENSE-flexmark"],
+ visibility = ["//visibility:public"],
+ exports = ["@flexmark-ext-anchorlink//jar"],
+ runtime_deps = [
+ ":flexmark-ext-autolink",
+ ],
+)
+
+java_library(
+ name = "flexmark-ext-autolink",
+ data = ["//lib:LICENSE-flexmark"],
+ visibility = ["//visibility:public"],
+ exports = ["@flexmark-ext-autolink//jar"],
+ runtime_deps = [
+ ":flexmark-ext-definition",
+ ],
+)
+
+java_library(
+ name = "flexmark-ext-definition",
+ data = ["//lib:LICENSE-flexmark"],
+ visibility = ["//visibility:public"],
+ exports = ["@flexmark-ext-definition//jar"],
+ runtime_deps = [
+ ":flexmark-ext-emoji",
+ ],
+)
+
+java_library(
+ name = "flexmark-ext-emoji",
+ data = ["//lib:LICENSE-flexmark"],
+ visibility = ["//visibility:public"],
+ exports = ["@flexmark-ext-emoji//jar"],
+ runtime_deps = [
+ ":flexmark-ext-escaped-character",
+ ],
+)
+
+java_library(
+ name = "flexmark-ext-escaped-character",
+ data = ["//lib:LICENSE-flexmark"],
+ visibility = ["//visibility:public"],
+ exports = ["@flexmark-ext-escaped-character//jar"],
+ runtime_deps = [
+ ":flexmark-ext-footnotes",
+ ],
+)
+
+java_library(
+ name = "flexmark-ext-footnotes",
+ data = ["//lib:LICENSE-flexmark"],
+ visibility = ["//visibility:public"],
+ exports = ["@flexmark-ext-footnotes//jar"],
+ runtime_deps = [
+ ":flexmark-ext-gfm-issues",
+ ],
+)
+
+java_library(
+ name = "flexmark-ext-gfm-issues",
+ data = ["//lib:LICENSE-flexmark"],
+ visibility = ["//visibility:public"],
+ exports = ["@flexmark-ext-gfm-issues//jar"],
+ runtime_deps = [
+ ":flexmark-ext-gfm-strikethrough",
+ ],
+)
+
+java_library(
+ name = "flexmark-ext-gfm-strikethrough",
+ data = ["//lib:LICENSE-flexmark"],
+ visibility = ["//visibility:public"],
+ exports = ["@flexmark-ext-gfm-strikethrough//jar"],
+ runtime_deps = [
+ ":flexmark-ext-gfm-tables",
+ ],
+)
+
+java_library(
+ name = "flexmark-ext-gfm-tables",
+ data = ["//lib:LICENSE-flexmark"],
+ visibility = ["//visibility:public"],
+ exports = ["@flexmark-ext-gfm-tables//jar"],
+ runtime_deps = [
+ ":flexmark-ext-gfm-tasklist",
+ ],
+)
+
+java_library(
+ name = "flexmark-ext-gfm-tasklist",
+ data = ["//lib:LICENSE-flexmark"],
+ visibility = ["//visibility:public"],
+ exports = ["@flexmark-ext-gfm-tasklist//jar"],
+ runtime_deps = [
+ ":flexmark-ext-gfm-users",
+ ],
+)
+
+java_library(
+ name = "flexmark-ext-gfm-users",
+ data = ["//lib:LICENSE-flexmark"],
+ visibility = ["//visibility:public"],
+ exports = ["@flexmark-ext-gfm-users//jar"],
+ runtime_deps = [
+ ":flexmark-ext-ins",
+ ],
+)
+
+java_library(
+ name = "flexmark-ext-ins",
+ data = ["//lib:LICENSE-flexmark"],
+ visibility = ["//visibility:public"],
+ exports = ["@flexmark-ext-ins//jar"],
+ runtime_deps = [
+ ":flexmark-ext-jekyll-front-matter",
+ ],
+)
+
+java_library(
+ name = "flexmark-ext-jekyll-front-matter",
+ data = ["//lib:LICENSE-flexmark"],
+ visibility = ["//visibility:public"],
+ exports = ["@flexmark-ext-jekyll-front-matter//jar"],
+ runtime_deps = [
+ ":flexmark-ext-superscript",
+ ],
+)
+
+java_library(
+ name = "flexmark-ext-superscript",
+ data = ["//lib:LICENSE-flexmark"],
+ visibility = ["//visibility:public"],
+ exports = ["@flexmark-ext-superscript//jar"],
+ runtime_deps = [
+ ":flexmark-ext-tables",
+ ],
+)
+
+java_library(
+ name = "flexmark-ext-tables",
+ data = ["//lib:LICENSE-flexmark"],
+ visibility = ["//visibility:public"],
+ exports = ["@flexmark-ext-tables//jar"],
+ runtime_deps = [
+ ":flexmark-ext-toc",
+ ],
+)
+
+java_library(
+ name = "flexmark-ext-toc",
+ data = ["//lib:LICENSE-flexmark"],
+ visibility = ["//visibility:public"],
+ exports = ["@flexmark-ext-toc//jar"],
+ runtime_deps = [
+ ":flexmark-ext-typographic",
+ ],
+)
+
+java_library(
+ name = "flexmark-ext-typographic",
+ data = ["//lib:LICENSE-flexmark"],
+ visibility = ["//visibility:public"],
+ exports = ["@flexmark-ext-typographic//jar"],
+ runtime_deps = [
+ ":flexmark-ext-wikilink",
+ ],
+)
+
+java_library(
+ name = "flexmark-ext-wikilink",
+ data = ["//lib:LICENSE-flexmark"],
+ visibility = ["//visibility:public"],
+ exports = ["@flexmark-ext-wikilink//jar"],
+ runtime_deps = [
+ ":flexmark-ext-yaml-front-matter",
+ ],
+)
+
+java_library(
+ name = "flexmark-ext-yaml-front-matter",
+ data = ["//lib:LICENSE-flexmark"],
+ visibility = ["//visibility:public"],
+ exports = ["@flexmark-ext-yaml-front-matter//jar"],
+ runtime_deps = [
+ ":flexmark-formatter",
+ ],
+)
+
+java_library(
+ name = "flexmark-formatter",
+ data = ["//lib:LICENSE-flexmark"],
+ visibility = ["//visibility:public"],
+ exports = ["@flexmark-formatter//jar"],
+ runtime_deps = [
+ ":flexmark-html-parser",
+ ],
+)
+
+java_library(
+ name = "flexmark-html-parser",
+ data = ["//lib:LICENSE-flexmark"],
+ visibility = ["//visibility:public"],
+ exports = ["@flexmark-html-parser//jar"],
+ runtime_deps = [
+ ":flexmark-profile-pegdown",
+ ],
+)
+
+java_library(
+ name = "flexmark-profile-pegdown",
+ data = ["//lib:LICENSE-flexmark"],
+ visibility = ["//visibility:public"],
+ exports = ["@flexmark-profile-pegdown//jar"],
+ runtime_deps = [
+ ":flexmark-util",
+ ],
+)
+
+java_library(
+ name = "flexmark-util",
+ data = ["//lib:LICENSE-flexmark"],
+ visibility = ["//visibility:public"],
+ exports = ["@flexmark-util//jar"],
+)
+
+java_library(
+ name = "autolink",
+ data = ["//lib:LICENSE-autolink"],
+ visibility = ["//visibility:public"],
+ exports = ["@autolink//jar"],
)
java_library(
diff --git a/lib/LICENSE-autolink b/lib/LICENSE-autolink
new file mode 100644
index 0000000..565820a
--- /dev/null
+++ b/lib/LICENSE-autolink
@@ -0,0 +1,21 @@
+The MIT License (MIT)
+
+Copyright (c) 2015 Robin Stocker
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in all
+copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
+SOFTWARE.
diff --git a/lib/LICENSE-flexmark b/lib/LICENSE-flexmark
new file mode 100644
index 0000000..c5e6ce0
--- /dev/null
+++ b/lib/LICENSE-flexmark
@@ -0,0 +1,26 @@
+Copyright (c) 2015-2016, Atlassian Pty Ltd
+All rights reserved.
+
+Copyright (c) 2016, Vladimir Schneider,
+All rights reserved.
+
+Redistribution and use in source and binary forms, with or without
+modification, are permitted provided that the following conditions are met:
+
+* Redistributions of source code must retain the above copyright notice, this
+ list of conditions and the following disclaimer.
+
+* Redistributions in binary form must reproduce the above copyright notice,
+ this list of conditions and the following disclaimer in the documentation
+ and/or other materials provided with the distribution.
+
+THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE
+FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
+SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
+CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
+OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
diff --git a/resources/com/google/gerrit/server/documentation/pegdown.css b/resources/com/google/gerrit/server/documentation/flexmark-java.css
similarity index 100%
rename from resources/com/google/gerrit/server/documentation/pegdown.css
rename to resources/com/google/gerrit/server/documentation/flexmark-java.css