mirror of
https://github.com/pewdiepie-archdaemon/odysseus.git
synced 2026-08-09 10:39:11 +02:00
fix(markdown): restore extracted blocks verbatim so $& and $$ survive (#5768)
The placeholder-restore pass in mdToHtml put code, math, mermaid and allowed-HTML blocks back with a string replacement, so String.replace read `$&`, `` $` ``, `$'` and `$$` in the *replacement* as substitution patterns. A fenced block containing them rendered corrupted: `$&` re-inserted the placeholder (`perl -pe 's/world/$& again/'` became `s/world/___CODE_BLOCK_0___amp; again/`), `` $` `` and `$'` spliced in the surrounding document, and `$$` collapsed to a single `$`. Pass a function replacer at all four sites, matching the inline-code site below them, which was already fixed this way. A function's return value is inserted verbatim with no `$` interpretation. The inline-code comment claimed `echo $1` would be read as a back-reference; with a string search value there are no capture groups, so `$1` is already literal. Reworded to name the four sequences that do corrupt. Fixes #5663
This commit is contained in:
parent
f23221420f
commit
578312200a
2 changed files with 57 additions and 7 deletions
|
|
@ -758,30 +758,36 @@ export function mdToHtml(src, opts) {
|
|||
// Remove empty paragraphs
|
||||
s = s.replace(/<p><\/p>/g, '');
|
||||
|
||||
// Every restore below passes a function replacer rather than the block string
|
||||
// itself. With a string replacement, `String.replace` reads `$&`, `` $` ``,
|
||||
// `$'` and `$$` in the *replacement* as substitution patterns, so a restored
|
||||
// block containing them is corrupted: `$&` re-inserts the placeholder, `` $` ``
|
||||
// and `$'` splice in the surrounding document, and `$$` collapses to `$`. Those
|
||||
// sequences are ordinary content in fenced code (`perl -pe 's/x/$& y/'`,
|
||||
// `echo "$$USD"`). A function replacer inserts its return value verbatim.
|
||||
|
||||
// CRITICAL: Restore allowed HTML blocks first
|
||||
allowedHtmlBlocks.forEach((block, index) => {
|
||||
s = s.replace(`___ALLOWED_HTML_${index}___`, block);
|
||||
s = s.replace(`___ALLOWED_HTML_${index}___`, () => block);
|
||||
});
|
||||
|
||||
// Restore math blocks
|
||||
mathBlocks.forEach((block, index) => {
|
||||
s = s.replace(`___MATH_BLOCK_${index}___`, block);
|
||||
s = s.replace(`___MATH_BLOCK_${index}___`, () => block);
|
||||
});
|
||||
|
||||
// Restore mermaid diagram blocks
|
||||
mermaidBlocks.forEach((block, index) => {
|
||||
s = s.replace(`___MERMAID_BLOCK_${index}___`, block);
|
||||
s = s.replace(`___MERMAID_BLOCK_${index}___`, () => block);
|
||||
});
|
||||
|
||||
// CRITICAL: Restore code blocks at the end
|
||||
codeBlocks.forEach((block, index) => {
|
||||
s = s.replace(`___CODE_BLOCK_${index}___`, block);
|
||||
s = s.replace(`___CODE_BLOCK_${index}___`, () => block);
|
||||
});
|
||||
|
||||
// Restore inline code spans last, so placeholders carried inside restored
|
||||
// <a>/allowed-HTML blocks are resolved too. The function replacer keeps the
|
||||
// escaped code literal — e.g. a shell snippet like `echo $1` is not treated
|
||||
// as a regex back-reference.
|
||||
// <a>/allowed-HTML blocks are resolved too.
|
||||
inlineCodeBlocks.forEach((block, index) => {
|
||||
s = s.replace(`___INLINE_CODE_${index}___`, () => block);
|
||||
});
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue