react-markdown-preview icon indicating copy to clipboard operation
react-markdown-preview copied to clipboard

Copy button for code block disappears with rehypeSanitize

Open MaxiPigna opened this issue 1 year ago • 1 comments

Given the following code

const MarkdownPresenter: FC<MarkdownPresenterProps> = ({ text }) => {
  const { theme } = useTheme();
  const rehypePlugins = [rehypeSanitize, () => rehypeExternalLinks({ target: '_blank' })];
  return (
    <MarkdownPreview
      source={text}
      rehypePlugins={rehypePlugins}
      style={{
        backgroundColor: 'transparent',
      }}
      wrapperElement={{
        'data-color-mode': theme,
      }}
      components={{
        code: ({ children = [], className, ...props }) => {
          if (typeof children === 'string' && /^\$\$(.*)\$\$/.test(children)) {
            const html = katex.renderToString(children.replace(/^\$\$(.*)\$\$/, '$1'), {
              throwOnError: false,
            });
            return <code dangerouslySetInnerHTML={{ __html: html }} style={{ background: 'transparent' }} />;
          }
          const code = props.node && props.node.children ? getCodeString(props.node.children) : children;
          if (
            typeof code === 'string' &&
            typeof className === 'string' &&
            /^language-katex/.test(className.toLocaleLowerCase())
          ) {
            const html = katex.renderToString(code, {
              throwOnError: false,
            });
            return <code style={{ fontSize: '150%' }} dangerouslySetInnerHTML={{ __html: html }} />;
          }
          return <code className={String(className)}>{children}</code>;
        },
      }}
    />
  );
};

Copy button for code block doesn't appear. image

I found out that the if I remove rehypeSanitize from rehypePlugins, then copy button appears as expected. image

Package version

  • "rehype-sanitize": "^6.0.0",
  • "@uiw/react-markdown-preview": "^5.1.1",

Is there any solution/workaround for this issue? Thanks

MaxiPigna avatar Jul 16 '24 08:07 MaxiPigna

@MaxiPigna

import rehypeSanitize, { defaultSchema } from 'rehype-sanitize';
import MarkdownPreview from '@uiw/react-markdown-preview';

const source = `
## MarkdownPreview

\`\`\`bash
$ npm install @uiw/react-markdown-preview --save
\`\`\`
`;

export default function Demo() {
  return (
    <MarkdownPreview
      source={source}
      rehypePlugins={[
        [
          rehypeSanitize,
          {
            ...defaultSchema,
            attributes: {
              ...defaultSchema.attributes,
              svg: ['className', 'hidden', 'viewBox', 'fill', 'height', 'width'],
              path: ['fill-rule', 'd'],
              div: ['className', 'class', 'data-code', ...(defaultSchema.attributes?.div || [])],
            },
            tagNames: [...(defaultSchema.tagNames || []), 'svg', 'path', 'div'],
          },
        ],
      ]}
      style={{ padding: 16 }}
    />
  );
}

jaywcjlove avatar Aug 02 '24 18:08 jaywcjlove