import MarkdownIt from "markdown-it"; const markdownRenderer = new MarkdownIt({ html: false, linkify: true, typographer: true, }); type ClipboardMimeType = "text/plain" | "text/html"; export interface MarkdownClipboardContent { plainText: string; html: string; } export interface RichClipboardWriter { supportsHtml: () => boolean; write: (data: Record) => Promise; } export interface MarkdownClipboardEnvironment { richWriter?: RichClipboardWriter | null; writePlainText: (text: string) => Promise; } export function createMarkdownClipboardContent(markdown: string): MarkdownClipboardContent { return { plainText: markdown, html: `${markdownRenderer.render(markdown)}`, }; } export async function writeMarkdownToRichClipboard( markdown: string, environment: MarkdownClipboardEnvironment, ): Promise { if (environment.richWriter?.supportsHtml()) { const content = createMarkdownClipboardContent(markdown); try { await environment.richWriter.write({ "text/plain": new Blob([content.plainText], { type: "text/plain" }), "text/html": new Blob([content.html], { type: "text/html" }), }); return; } catch { // Fall through to the plain-text path. Some webviews expose rich clipboard // APIs but deny writes depending on focus, permissions, or browser policy. } } await environment.writePlainText(markdown); }