Skip to content

Reject emoji-parsing if the slice ends with ** - #947

Merged
xoofx merged 5 commits into
xoofx:mainfrom
bstordrup:fix/issue946_WrongEmojiRendering
Sep 20, 2026
Merged

xoofx merged 5 commits into
xoofx:mainfrom
bstordrup:fix/issue946_WrongEmojiRendering

Conversation

@bstordrup

Copy link
Copy Markdown
Contributor

This pull request introduces an additional validation step in the emoji parsing logic to prevent false positives. Specifically, it ensures that emoji candidates ending with two asterisks (**) are not matched as valid emojis.

Emoji parsing improvement:

  • Updated the Match method in EmojiParser.cs to return false if an emoji candidate ends with two asterisks, preventing incorrect emoji matches in such cases.

A sample markdown is provided on the #946 issue.

Closing #946

@bstordrup

Copy link
Copy Markdown
Contributor Author

@xoofx, will you have a look?

@xoofx

xoofx commented Aug 25, 2026

Copy link
Copy Markdown
Owner

@xoofx, will you have a look?

Yes, I'm on holidays, but will check when I'm back

@MihaZupan MihaZupan left a comment

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Please add tests for any such behavior changes

{
// Only look at the following char if the emoji ends with a '*', otherwise it is not needed.
var followingChar = slice.PeekChar(match.Key.Length);
if (lastEmojiChar == '*' && followingChar == '*')

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

lastEmojiChar == '*' is already checked above

return false;
}

// If the found emoji ends with a ´*´, the following char must not be a '*'.

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Your current example is
**Non-goals (explicitly out of scope for this plan):**
but why would we treat that differently for emoji compared to italic
*Non-goals (explicitly out of scope for this plan):*
or other types of emphasis?

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Which parser detects italic?

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Hmmm. I see the point. The EmphasisDescriptor takes a minumum and maximum count - bold is maximum count and italic is minimum count.

So actually the EmojiParser need to know if an EmphasisParser has open emphasis or not - and reject the emoji ending in ´*´ if there is an open emphasis at the point of it.

@xoofx

xoofx commented Sep 2, 2026

Copy link
Copy Markdown
Owner

We still need to have tests for this PR

@xoofx xoofx added the bug label Sep 2, 2026
@bstordrup

Copy link
Copy Markdown
Contributor Author

I looked a bit more into the code, and started wondering why the Emphasis parser is an inline parser instead of a block parser. Is there anything in Markdown specification that forces it to be inline?

All Emphasis instances are as far as I see it blocks per nature since they have a starting tag/definition and an ending tag/definition (like bold being started and ended with a double *), and it could in theory span several lines - even separated by line breaks - if treated as a block.

If so, it would be a question of finding the ending Emphasis descriptor for the starting Emphasis descriptor found - and then running a new parser set on everything between and not including the Emphasis start and end. This would also parse my example line correctly as the ending Emphasis descriptor would be evaluated prior to evaluating Emojis.

@xoofx

xoofx commented Sep 7, 2026

Copy link
Copy Markdown
Owner

I looked a bit more into the code, and started wondering why the Emphasis parser is an inline parser instead of a block parser. Is there anything in Markdown specification that forces it to be inline?

Yes, block have precedence over inline, and block and inline parsers are quite different in their behavior. See also https://spec.commonmark.org/0.31.2/#blocks-and-inlines

The work for solving such problem (an extension like emoji perturbating core functionalities) should be best effort without causing disruption to the core. Unfortunately, it's not always easy and sometimes it requires to add specific code path to the core to handle plugins cases.

Will check if it can be further improved from your PR.

Resolve trailing emphasis delimiters before converting ambiguous emoji matches. Reuse the existing emphasis parser rather than guessing whether an opener remains active or rejecting only double asterisks.

Cover italics, strong/nested emphasis, custom delimiters, links, images, tables, source positions, renderers, all default mappings, and 2688 emphasis-structure comparisons. Document emphasis and generic-attribute precedence and the named-shortcode escape hatch.
@xoofx
xoofx merged commit 237ef72 into xoofx:main Sep 20, 2026
3 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants