mirror of
https://gitflic.ru/project/openide/openide.git
synced 2025-12-16 14:23:28 +07:00
fix(jdoc): inline mk structs break detection
GitOrigin-RevId: 0cb1adbd59262523ce59767fee5f33e78234bd9f
This commit is contained in:
committed by
intellij-monorepo-bot
parent
3b13ef3ec1
commit
0cdf89293d
@@ -388,7 +388,7 @@ public final class BasicJavaDocParser {
|
|||||||
while (!builder.eof()) {
|
while (!builder.eof()) {
|
||||||
builder.advanceLexer();
|
builder.advanceLexer();
|
||||||
previousToken = token;
|
previousToken = token;
|
||||||
token = getTokenType(builder);
|
token = getTokenType(builder, false);
|
||||||
if (token == needle) {
|
if (token == needle) {
|
||||||
return token;
|
return token;
|
||||||
}
|
}
|
||||||
@@ -398,7 +398,7 @@ public final class BasicJavaDocParser {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// Markdown specific, check for EOL
|
// Markdown specific, check for EOL
|
||||||
if (token == JavaDocTokenType.DOC_SPACE && previousToken == JavaDocTokenType.DOC_SPACE) {
|
if (token == TokenType.WHITE_SPACE && previousToken == TokenType.WHITE_SPACE) {
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -605,10 +605,15 @@ public final class BasicJavaDocParser {
|
|||||||
|
|
||||||
@Nullable
|
@Nullable
|
||||||
private static IElementType getTokenType(PsiBuilder builder) {
|
private static IElementType getTokenType(PsiBuilder builder) {
|
||||||
|
return getTokenType(builder, true);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Nullable
|
||||||
|
private static IElementType getTokenType(PsiBuilder builder, boolean skipWhitespace) {
|
||||||
IElementType tokenType;
|
IElementType tokenType;
|
||||||
while ((tokenType = builder.getTokenType()) == JavaDocTokenType.DOC_SPACE) {
|
while ((tokenType = builder.getTokenType()) == JavaDocTokenType.DOC_SPACE) {
|
||||||
builder.remapCurrentToken(TokenType.WHITE_SPACE);
|
builder.remapCurrentToken(TokenType.WHITE_SPACE);
|
||||||
builder.advanceLexer();
|
if (skipWhitespace) builder.advanceLexer();
|
||||||
}
|
}
|
||||||
return tokenType;
|
return tokenType;
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -0,0 +1,68 @@
|
|||||||
|
// Copyright 2000-2024 JetBrains s.r.o. and contributors. Use of this source code is governed by the Apache 2.0 license.
|
||||||
|
package com.intellij.codeInsight.javadoc.markdown;
|
||||||
|
|
||||||
|
import com.intellij.openapi.util.text.StringUtil;
|
||||||
|
import kotlin.ranges.IntRange;
|
||||||
|
import org.intellij.markdown.MarkdownTokenTypes;
|
||||||
|
import org.intellij.markdown.parser.sequentialparsers.RangesListBuilder;
|
||||||
|
import org.intellij.markdown.parser.sequentialparsers.SequentialParser;
|
||||||
|
import org.intellij.markdown.parser.sequentialparsers.TokensCache;
|
||||||
|
import org.jetbrains.annotations.NotNull;
|
||||||
|
|
||||||
|
import java.util.List;
|
||||||
|
|
||||||
|
/// Inline parser dedicated to finding `<code>` tags.
|
||||||
|
///
|
||||||
|
/// Only purpose is to exclude the range from further markdown processing
|
||||||
|
public class CodeTagParser implements SequentialParser {
|
||||||
|
@Override
|
||||||
|
public @NotNull ParsingResult parse(@NotNull TokensCache tokens, @NotNull List<IntRange> rangesToGlue) {
|
||||||
|
var result = new SequentialParser.ParsingResultBuilder();
|
||||||
|
var delegateIndices = new RangesListBuilder();
|
||||||
|
TokensCache.Iterator iterator = tokens.new RangesListIterator(rangesToGlue);
|
||||||
|
|
||||||
|
while (iterator.getType() != null) {
|
||||||
|
if (iterator.getType() == MarkdownTokenTypes.HTML_TAG && hasOpeningTag(getText(tokens, iterator), "code")) {
|
||||||
|
int startIndex = iterator.getIndex();
|
||||||
|
var endIterator = findEnd(tokens, iterator.advance());
|
||||||
|
|
||||||
|
if (endIterator != null) {
|
||||||
|
result.withNode(new SequentialParser.Node(new IntRange(startIndex, endIterator.getIndex() + 1), JavaDocMarkdownFlavourDescriptor.RAW_TYPE));
|
||||||
|
iterator = endIterator.advance();
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
delegateIndices.put(iterator.getIndex());
|
||||||
|
iterator = iterator.advance();
|
||||||
|
}
|
||||||
|
|
||||||
|
return result.withFurtherProcessing(delegateIndices.get());
|
||||||
|
}
|
||||||
|
|
||||||
|
/// @return The iterator located at the end tag, or `null` if the end isn't found
|
||||||
|
private static TokensCache.Iterator findEnd(@NotNull TokensCache tokens, TokensCache.Iterator iterator) {
|
||||||
|
while (iterator.getType() != null) {
|
||||||
|
if (iterator.getType() == MarkdownTokenTypes.HTML_TAG) {
|
||||||
|
if (hasClosingTag(getText(tokens, iterator), "code")) {
|
||||||
|
return iterator;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
iterator = iterator.advance();
|
||||||
|
}
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
|
||||||
|
private static String getText(@NotNull TokensCache tokens, TokensCache.Iterator iterator) {
|
||||||
|
return tokens.getOriginalText().subSequence(iterator.getStart(), iterator.getEnd()).toString();
|
||||||
|
}
|
||||||
|
|
||||||
|
private static boolean hasOpeningTag(String tag, String tagName) {
|
||||||
|
return StringUtil.trimEnd(StringUtil.trimStart(tag, "<"), ">").equals(tagName);
|
||||||
|
}
|
||||||
|
|
||||||
|
private static boolean hasClosingTag(String tag, String tagName) {
|
||||||
|
return StringUtil.trimEnd(StringUtil.trimStart(tag, "</"), ">").equals(tagName);
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -6,11 +6,18 @@ import org.intellij.markdown.MarkdownElementTypes;
|
|||||||
import org.intellij.markdown.MarkdownTokenTypes;
|
import org.intellij.markdown.MarkdownTokenTypes;
|
||||||
import org.intellij.markdown.ast.ASTNode;
|
import org.intellij.markdown.ast.ASTNode;
|
||||||
import org.intellij.markdown.flavours.gfm.GFMFlavourDescriptor;
|
import org.intellij.markdown.flavours.gfm.GFMFlavourDescriptor;
|
||||||
|
import org.intellij.markdown.flavours.gfm.GFMTokenTypes;
|
||||||
|
import org.intellij.markdown.flavours.gfm.StrikeThroughDelimiterParser;
|
||||||
import org.intellij.markdown.html.GeneratingProvider;
|
import org.intellij.markdown.html.GeneratingProvider;
|
||||||
import org.intellij.markdown.html.HtmlGenerator;
|
import org.intellij.markdown.html.HtmlGenerator;
|
||||||
|
import org.intellij.markdown.html.TransparentInlineHolderProvider;
|
||||||
import org.intellij.markdown.html.TrimmingInlineHolderProvider;
|
import org.intellij.markdown.html.TrimmingInlineHolderProvider;
|
||||||
import org.intellij.markdown.parser.LinkMap;
|
import org.intellij.markdown.parser.LinkMap;
|
||||||
import org.intellij.markdown.parser.MarkerProcessorFactory;
|
import org.intellij.markdown.parser.MarkerProcessorFactory;
|
||||||
|
import org.intellij.markdown.parser.sequentialparsers.EmphasisLikeParser;
|
||||||
|
import org.intellij.markdown.parser.sequentialparsers.SequentialParser;
|
||||||
|
import org.intellij.markdown.parser.sequentialparsers.SequentialParserManager;
|
||||||
|
import org.intellij.markdown.parser.sequentialparsers.impl.*;
|
||||||
import org.jetbrains.annotations.NotNull;
|
import org.jetbrains.annotations.NotNull;
|
||||||
import org.jetbrains.annotations.Nullable;
|
import org.jetbrains.annotations.Nullable;
|
||||||
|
|
||||||
@@ -23,10 +30,31 @@ import java.util.Map;
|
|||||||
* Flavour descriptor which describes how to generate html text from markdown documentation
|
* Flavour descriptor which describes how to generate html text from markdown documentation
|
||||||
*/
|
*/
|
||||||
public class JavaDocMarkdownFlavourDescriptor extends GFMFlavourDescriptor {
|
public class JavaDocMarkdownFlavourDescriptor extends GFMFlavourDescriptor {
|
||||||
|
public static final IElementType RAW_TYPE = new IElementType("RAW_TYPE");
|
||||||
|
|
||||||
public JavaDocMarkdownFlavourDescriptor() {
|
public JavaDocMarkdownFlavourDescriptor() {
|
||||||
super(true, false, true);
|
super(true, false, true);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public @NotNull SequentialParserManager getSequentialParserManager() {
|
||||||
|
return new SequentialParserManager() {
|
||||||
|
@Override
|
||||||
|
public @NotNull List<SequentialParser> getParserSequence() {
|
||||||
|
return List.of(
|
||||||
|
new AutolinkParser(List.of(MarkdownTokenTypes.AUTOLINK, GFMTokenTypes.GFM_AUTOLINK)),
|
||||||
|
new BacktickParser(),
|
||||||
|
new CodeTagParser(), // Custom parser excluding <code> blocks content to be processed as markdown
|
||||||
|
new MathParser(),
|
||||||
|
new ImageParser(),
|
||||||
|
new InlineLinkParser(),
|
||||||
|
new ReferenceLinkParser(),
|
||||||
|
new EmphasisLikeParser(new EmphStrongDelimiterParser(), new StrikeThroughDelimiterParser())
|
||||||
|
);
|
||||||
|
}
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
@NotNull
|
@NotNull
|
||||||
@Override
|
@Override
|
||||||
public Map<IElementType, GeneratingProvider> createHtmlGeneratingProviders(@NotNull LinkMap linkMap, @Nullable URI baseURI) {
|
public Map<IElementType, GeneratingProvider> createHtmlGeneratingProviders(@NotNull LinkMap linkMap, @Nullable URI baseURI) {
|
||||||
@@ -38,6 +66,9 @@ public class JavaDocMarkdownFlavourDescriptor extends GFMFlavourDescriptor {
|
|||||||
// Paragraphs may need to be inlined
|
// Paragraphs may need to be inlined
|
||||||
result.put(MarkdownElementTypes.PARAGRAPH, new JavaDocParagraphProvider());
|
result.put(MarkdownElementTypes.PARAGRAPH, new JavaDocParagraphProvider());
|
||||||
|
|
||||||
|
// Custom type, no processing
|
||||||
|
result.put(RAW_TYPE, new TransparentInlineHolderProvider());
|
||||||
|
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -1,3 +1,5 @@
|
|||||||
<html><head><base href="placeholder"></head><body><div class='definition'><pre><span style="color:#000080;font-weight:bold;">class</span> <span style="color:#000000;">MarkdownCodeBlock</span></pre></div><div class='content'><p>Single liner code block:
|
<html><head><base href="placeholder"></head><body><div class='definition'><pre><span style="color:#000080;font-weight:bold;">class</span> <span style="color:#000000;">MarkdownCodeBlock</span></pre></div><div class='content'><p>Single liner code block:
|
||||||
<code><span style="">Hello world</span></code></p><p>No tags are interpreted inside them
|
<code><span style="">Hello world</span></code></p><p>No tags are interpreted inside them
|
||||||
<code><span style="">{@link java.lang.String niceLink}</span></code></p></div><table class='sections'><p></table>
|
<code><span style="">{@link java.lang.String niceLink}</span></code></p><p>No markdown markup is interpreted inside them
|
||||||
|
<code><span style="">_Hello_ <code></span></code></p><p>This is a broken inline link
|
||||||
|
`Start of broken link</p>end of broken link`</div><table class='sections'><p></table>
|
||||||
@@ -4,4 +4,12 @@
|
|||||||
///
|
///
|
||||||
/// No tags are interpreted inside them
|
/// No tags are interpreted inside them
|
||||||
/// `{@link java.lang.String niceLink}`
|
/// `{@link java.lang.String niceLink}`
|
||||||
|
///
|
||||||
|
/// No markdown markup is interpreted inside them
|
||||||
|
/// `_Hello_ <code>`
|
||||||
|
///
|
||||||
|
/// This is a broken inline link
|
||||||
|
/// `Start of broken link
|
||||||
|
///
|
||||||
|
/// end of broken link`
|
||||||
class MarkdownCodeBlock {}
|
class MarkdownCodeBlock {}
|
||||||
@@ -3,4 +3,5 @@
|
|||||||
Some text with inline <code><span style="">code</span></code>
|
Some text with inline <code><span style="">code</span></code>
|
||||||
</pre>
|
</pre>
|
||||||
<pre><code><span style="">String fullLine = </span><span style="color:#008000;font-weight:bold;">""</span><span style="">;</span></code></pre> </pre>
|
<pre><code><span style="">String fullLine = </span><span style="color:#008000;font-weight:bold;">""</span><span style="">;</span></code></pre> </pre>
|
||||||
|
<pre><code><span style="">String secondFullLine = </span><span style="color:#008000;font-weight:bold;">""</span><span style="">;</span></code></pre>
|
||||||
</div><table class='sections'><p></table>
|
</div><table class='sections'><p></table>
|
||||||
@@ -7,6 +7,7 @@
|
|||||||
* String fullLine = "";
|
* String fullLine = "";
|
||||||
* }
|
* }
|
||||||
* </pre>
|
* </pre>
|
||||||
|
* <pre> {@code String secondFullLine = ""; }</pre>
|
||||||
*/
|
*/
|
||||||
class Test {
|
class Test {
|
||||||
public String field = null;
|
public String field = null;
|
||||||
|
|||||||
Reference in New Issue
Block a user