Skip to content

Markdown mode produces illegal block-in-block Lexical nodes #2862

@Soxasora

Description

@Soxasora

Originally reported by @sir-opti

Is there an existing issue for this?

  • I have searched the existing issues

Describe the bug

Something like this:

> {bt}{bt}{bt}js
> console.log(hello)
> {bt}{bt}{bt}

Gets converted into the following Lexical nodes:

- QuoteNode
  - CodeNode
    - TextNode: console.log(hello)

This is not permitted by Lexical and cannot happen in compose mode, but our MDAST pipeline makes it happen.
Given that it's actually nice to be able to place blocks inside of blocks and many people already use them (quotes in quotes, headings in quotes etc), the real bug here is that in compose mode it's impossible to work with them.

Taking the tree mentioned above, toggling quote via toolbar will just remove the CodeNode, and subsequent quote toggling will not work.

What's happening here is that toggling a block doesn't actually remove it, but swaps it with a ParagraphNode. So while our selection is inside the TextNode child of CodeNode, to the Quote toggle we're actually trying to switch to ParagraphNode because the anchor (toplevel) is QuoteNode.
Per-anchor, we're in a QuoteNode, per block conversion we're in a CodeNode. So what finally happens is that the CodeNode will be converted into a ParagraphNode because the anchor is a QuoteNode and we're trying to toggle-off the QuoteNode.

Let's hope I didn't lose anyone, basically Lexical doesn't like block-in-block but our MDAST does.

Screenshots

quotejail.mp4

Steps To Reproduce

  1. Switch to Markdown mode
  2. Wrap a code block inside a block quote
  3. Switch to compose mode
  4. Toggle quote via toolbar
  5. CodeNode disappears but quote stays (and quote won't go away even on retries)

Expected behavior

To not be placed in a quote jail

Logs

No response

Device information

No response

Additional context

No response

Metadata

Metadata

Assignees

No one assigned

    Labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions