Conversation
mnkiefer
commented
Feb 6, 2026
- Introduces a new custom remark plugin by stripping emojis from text, code blocks, image metadata, etc. to ensure a more professional appearance.
There was a problem hiding this comment.
Pull request overview
This PR introduces a custom remark plugin to strip emoji characters from rendered documentation, aiming for a more professional appearance. The plugin recursively traverses the markdown AST and removes emojis from text nodes, code blocks, image/link metadata, and MDX JSX attributes.
Changes:
- Added a new remark plugin at
docs/src/lib/remark/stripEmojis.jsthat implements tree traversal and emoji stripping logic - Integrated the plugin into the Astro markdown pipeline via
astro.config.mjs
Reviewed changes
Copilot reviewed 2 out of 2 changed files in this pull request and generated 3 comments.
| File | Description |
|---|---|
| docs/src/lib/remark/stripEmojis.js | New remark plugin that recursively visits AST nodes and strips emojis using a replacement map and Unicode property escapes |
| docs/astro.config.mjs | Registers the stripEmojis plugin in the markdown.remarkPlugins configuration array |
💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.
| if (node.type === 'inlineCode' && typeof node.value === 'string') { | ||
| node.value = stripEmojis(node.value); | ||
| } | ||
|
|
||
| if (node.type === 'code' && typeof node.value === 'string') { | ||
| node.value = stripEmojis(node.value); | ||
| } |
There was a problem hiding this comment.
Stripping emojis from code blocks and inline code could break code examples that intentionally include emoji characters. For example, string literals, test cases, or documentation examples that demonstrate emoji handling would be modified. Consider whether code should be excluded from emoji stripping to preserve code examples as written.
| * @param {string} input | ||
| */ | ||
| function stripEmojis(input) { | ||
| let output = input; | ||
|
|
||
| for (const [from, to] of replacements.entries()) { | ||
| if (output.includes(from)) output = output.split(from).join(to); | ||
| } | ||
|
|
There was a problem hiding this comment.
The string replacement approach using split().join() is inefficient for multiple replacements on the same string. Each replacement iterates through the entire string, resulting in O(n*m) complexity where n is string length and m is number of replacements. Consider using a single pass with a regex combining all patterns, or use replaceAll() which is more efficient and clearer in intent.
| * @param {string} input | |
| */ | |
| function stripEmojis(input) { | |
| let output = input; | |
| for (const [from, to] of replacements.entries()) { | |
| if (output.includes(from)) output = output.split(from).join(to); | |
| } | |
| * Escape special characters in a string for use in a RegExp. | |
| * @param {string} value | |
| * @returns {string} | |
| */ | |
| function escapeRegex(value) { | |
| return value.replace(/[.*+?^${}()|[\]\\]/g, '\\$&'); | |
| } | |
| // Build a single regex that matches any of the replacement keys. | |
| const replacementPattern = Array.from(replacements.keys()) | |
| .sort((a, b) => b.length - a.length) // longer first to prefer longer matches | |
| .map((key) => escapeRegex(key)) | |
| .join('|'); | |
| const replacementsRegex = new RegExp(replacementPattern, 'gu'); | |
| /** | |
| * @param {string} input | |
| */ | |
| function stripEmojis(input) { | |
| let output = input.replace( | |
| replacementsRegex, | |
| (match) => replacements.get(match) ?? match, | |
| ); |
| */ | ||
| export default function remarkStripEmojis() { | ||
| return function transform(tree) { | ||
| visit(tree); |
There was a problem hiding this comment.
The transform function should return the tree after modifications. While remark plugins that mutate the tree in-place may work without an explicit return, it's a best practice to return the tree to follow the unified plugin specification and ensure compatibility with the remark ecosystem. Add return tree; after the visit call.
| visit(tree); | |
| visit(tree); | |
| return tree; |