(
props: ComponentProps<"div"> & {
text: string
cacheKey?: string
streaming?: boolean
class?: string
classList?: Record<string, boolean>
},
)
| 353 | } |
| 354 | |
| 355 | export function Markdown( |
| 356 | props: ComponentProps<"div"> & { |
| 357 | text: string |
| 358 | cacheKey?: string |
| 359 | streaming?: boolean |
| 360 | class?: string |
| 361 | classList?: Record<string, boolean> |
| 362 | }, |
| 363 | ) { |
| 364 | const [local, others] = splitProps(props, ["text", "cacheKey", "streaming", "class", "classList"]) |
| 365 | const marked = useMarked() |
| 366 | const i18n = useI18n() |
| 367 | const [root, setRoot] = createSignal<HTMLDivElement>() |
| 368 | const owner = createUniqueId() |
| 369 | const activeCodeKeys = new Set<string>() |
| 370 | const completedCode = new Map<string, Extract<RenderedBlock, { mode: "code" }>>() |
| 371 | const projection = createMemo((previous: Projection | undefined) => |
| 372 | project(previous, local.text, local.streaming ?? false), |
| 373 | ) |
| 374 | const [html] = createResource( |
| 375 | () => { |
| 376 | return { |
| 377 | text: local.text, |
| 378 | key: local.cacheKey, |
| 379 | projection: projection(), |
| 380 | } |
| 381 | }, |
| 382 | async (src) => { |
| 383 | if (isServer) |
| 384 | return { |
| 385 | text: src.text, |
| 386 | blocks: [ |
| 387 | { |
| 388 | key: "server", |
| 389 | mode: "full" as const, |
| 390 | raw: src.text, |
| 391 | hash: checksum(src.text) ?? "", |
| 392 | html: fallback(src.text), |
| 393 | }, |
| 394 | ], |
| 395 | } satisfies RenderResult |
| 396 | if (!src.text) return { text: src.text, blocks: [] } satisfies RenderResult |
| 397 | |
| 398 | const base = src.key ?? checksum(src.text) |
| 399 | return Promise.all( |
| 400 | src.projection.blocks.map(async (block, index) => { |
| 401 | const key = base ? `${base}:${index}:${block.mode}` : undefined |
| 402 | const blockKey = markdownBlockKey(owner, src.key, index, block.mode) |
| 403 | |
| 404 | if (block.mode === "code") { |
| 405 | const cached = completedCode.get(blockKey) |
| 406 | if (block.complete && cached?.raw === block.raw) return cached |
| 407 | const result = await code(block.src, block.language, blockKey, block.complete) |
| 408 | const rendered = { |
| 409 | key: blockKey, |
| 410 | mode: block.mode, |
| 411 | raw: block.raw, |
| 412 | hash: String(block.raw.length), |
nothing calls this directly
no test coverage detected