Skip to content

Commit 81ac66f

Browse files
committed
fix code block
1 parent 817833c commit 81ac66f

File tree

5 files changed

+66
-43
lines changed

5 files changed

+66
-43
lines changed

apps/sim/app/chat/components/message/components/markdown-renderer.tsx

Lines changed: 1 addition & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,4 @@
11
import React, { type HTMLAttributes, memo, type ReactNode, useMemo } from 'react'
2-
import { code } from '@streamdown/code'
32
import { Streamdown } from 'streamdown'
43
import 'streamdown/styles.css'
54
import { Tooltip } from '@/components/emcn'
@@ -26,8 +25,6 @@ export function LinkWithPreview({ href, children }: { href: string; children: Re
2625
)
2726
}
2827

29-
const STREAMDOWN_PLUGINS = { code }
30-
3128
function createCustomComponents(LinkComponent: typeof LinkWithPreview) {
3229
return {
3330
p: ({ children }: React.HTMLAttributes<HTMLParagraphElement>) => (
@@ -195,7 +192,7 @@ const MarkdownRenderer = memo(function MarkdownRenderer({
195192

196193
return (
197194
<div className='space-y-4 break-words font-sans text-[var(--landing-text)] text-base leading-relaxed'>
198-
<Streamdown mode='static' plugins={STREAMDOWN_PLUGINS} components={components}>
195+
<Streamdown mode='static' components={components}>
199196
{processedContent}
200197
</Streamdown>
201198
</div>

apps/sim/app/workspace/[workspaceId]/files/components/file-viewer/preview-panel.tsx

Lines changed: 0 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,6 @@
11
'use client'
22

33
import { createContext, memo, useCallback, useContext, useEffect, useMemo, useRef } from 'react'
4-
import { code } from '@streamdown/code'
54
import { useRouter } from 'next/navigation'
65
import rehypeSlug from 'rehype-slug'
76
import remarkBreaks from 'remark-breaks'
@@ -77,7 +76,6 @@ export const PreviewPanel = memo(function PreviewPanel({
7776

7877
const REMARK_PLUGINS = [remarkBreaks]
7978
const REHYPE_PLUGINS = [rehypeSlug]
80-
const STREAMDOWN_PLUGINS = { code }
8179

8280
/**
8381
* Carries the contentRef and toggle handler from MarkdownPreview down to the
@@ -380,7 +378,6 @@ const MarkdownPreview = memo(function MarkdownPreview({
380378
mode='static'
381379
remarkPlugins={REMARK_PLUGINS}
382380
rehypePlugins={REHYPE_PLUGINS}
383-
plugins={STREAMDOWN_PLUGINS}
384381
components={MARKDOWN_COMPONENTS}
385382
>
386383
{content}
@@ -398,7 +395,6 @@ const MarkdownPreview = memo(function MarkdownPreview({
398395
mode='static'
399396
remarkPlugins={REMARK_PLUGINS}
400397
rehypePlugins={REHYPE_PLUGINS}
401-
plugins={STREAMDOWN_PLUGINS}
402398
components={MARKDOWN_COMPONENTS}
403399
>
404400
{content}

apps/sim/app/workspace/[workspaceId]/home/components/message-content/components/chat-content/chat-content.tsx

Lines changed: 65 additions & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -1,18 +1,37 @@
11
'use client'
22

33
import { type ComponentPropsWithoutRef, useMemo } from 'react'
4-
import { code } from '@streamdown/code'
54
import { Streamdown } from 'streamdown'
65
import 'streamdown/styles.css'
7-
import { Checkbox } from '@/components/emcn'
6+
import 'prismjs/components/prism-typescript'
7+
import 'prismjs/components/prism-bash'
8+
import 'prismjs/components/prism-css'
9+
import 'prismjs/components/prism-markup'
10+
import '@/components/emcn/components/code/code.css'
11+
import { Checkbox, highlight, languages } from '@/components/emcn'
12+
import { CopyCodeButton } from '@/components/ui/copy-code-button'
813
import { cn } from '@/lib/core/utils/cn'
14+
import { extractTextContent } from '@/lib/core/utils/react-node-text'
915
import {
1016
PendingTagIndicator,
1117
parseSpecialTags,
1218
SpecialTags,
1319
} from '@/app/workspace/[workspaceId]/home/components/message-content/components/special-tags'
1420
import { useStreamingText } from '@/hooks/use-streaming-text'
1521

22+
const LANG_ALIASES: Record<string, string> = {
23+
js: 'javascript',
24+
ts: 'typescript',
25+
tsx: 'typescript',
26+
jsx: 'javascript',
27+
sh: 'bash',
28+
shell: 'bash',
29+
html: 'markup',
30+
xml: 'markup',
31+
yml: 'yaml',
32+
py: 'python',
33+
}
34+
1635
const PROSE_CLASSES = cn(
1736
'prose prose-base dark:prose-invert max-w-none',
1837
'font-[family-name:var(--font-inter)] antialiased break-words font-[430] tracking-[0]',
@@ -24,17 +43,13 @@ const PROSE_CLASSES = cn(
2443
'prose-ul:my-4 prose-ol:my-4',
2544
'prose-strong:font-[600] prose-strong:text-[var(--text-primary)]',
2645
'prose-a:text-[var(--text-primary)] prose-a:underline prose-a:decoration-dashed prose-a:underline-offset-4',
27-
'prose-code:rounded prose-code:bg-[var(--surface-5)] prose-code:px-1.5 prose-code:py-0.5 prose-code:text-small prose-code:font-mono prose-code:font-[400] prose-code:text-[var(--text-primary)]',
28-
'prose-code:before:content-none prose-code:after:content-none',
2946
'prose-hr:border-[var(--divider)] prose-hr:my-6',
3047
'prose-table:my-0'
3148
)
3249

3350
type TdProps = ComponentPropsWithoutRef<'td'>
3451
type ThProps = ComponentPropsWithoutRef<'th'>
3552

36-
const STREAMDOWN_PLUGINS = { code }
37-
3853
const MARKDOWN_COMPONENTS = {
3954
table({ children }: { children?: React.ReactNode }) {
4055
return (
@@ -68,6 +83,41 @@ const MARKDOWN_COMPONENTS = {
6883
</td>
6984
)
7085
},
86+
code({ children, className }: { children?: React.ReactNode; className?: string }) {
87+
const langMatch = className?.match(/language-(\w+)/)
88+
const language = langMatch ? langMatch[1] : ''
89+
const codeString = extractTextContent(children)
90+
91+
if (!codeString) {
92+
return (
93+
<pre className='not-prose my-6 overflow-x-auto rounded-lg bg-[var(--surface-5)] p-4 font-[430] font-mono text-[var(--text-primary)] text-small leading-[21px] dark:bg-[var(--code-bg)]'>
94+
<code>{children}</code>
95+
</pre>
96+
)
97+
}
98+
99+
const resolved = LANG_ALIASES[language] || language || 'javascript'
100+
const grammar = languages[resolved] || languages.javascript
101+
const html = highlight(codeString.trimEnd(), grammar, resolved)
102+
103+
return (
104+
<div className='not-prose my-6 overflow-hidden rounded-lg border border-[var(--divider)]'>
105+
<div className='flex items-center justify-between border-[var(--divider)] border-b bg-[var(--surface-4)] px-4 py-2 dark:bg-[var(--surface-4)]'>
106+
<span className='text-[var(--text-tertiary)] text-xs'>{language || 'code'}</span>
107+
<CopyCodeButton
108+
code={codeString}
109+
className='text-[var(--text-tertiary)] hover:bg-[var(--surface-5)] hover:text-[var(--text-secondary)]'
110+
/>
111+
</div>
112+
<div className='code-editor-theme bg-[var(--surface-5)] dark:bg-[var(--code-bg)]'>
113+
<pre
114+
className='m-0 overflow-x-auto whitespace-pre p-4 font-[430] font-mono text-[var(--text-primary)] text-small leading-[21px]'
115+
dangerouslySetInnerHTML={{ __html: html }}
116+
/>
117+
</div>
118+
</div>
119+
)
120+
},
71121
a({ children, href }: { children?: React.ReactNode; href?: string }) {
72122
return (
73123
<a
@@ -103,6 +153,13 @@ const MARKDOWN_COMPONENTS = {
103153
</li>
104154
)
105155
},
156+
inlineCode({ children }: { children?: React.ReactNode }) {
157+
return (
158+
<code className='rounded bg-[var(--surface-5)] px-1.5 py-0.5 font-mono text-small font-[400] text-[var(--text-primary)] before:content-none after:content-none'>
159+
{children}
160+
</code>
161+
)
162+
},
106163
input({ type, checked }: { type?: string; checked?: boolean }) {
107164
if (type === 'checkbox') {
108165
return <Checkbox checked={checked || false} disabled size='sm' className='mt-1.5 shrink-0' />
@@ -133,11 +190,7 @@ export function ChatContent({ content, isStreaming = false, onOptionSelect }: Ch
133190
key={`${segment.type}-${i}`}
134191
className={cn(PROSE_CLASSES, '[&>:first-child]:mt-0 [&>:last-child]:mb-0')}
135192
>
136-
<Streamdown
137-
mode='static'
138-
plugins={STREAMDOWN_PLUGINS}
139-
components={MARKDOWN_COMPONENTS}
140-
>
193+
<Streamdown mode='static' components={MARKDOWN_COMPONENTS}>
141194
{segment.content}
142195
</Streamdown>
143196
</div>
@@ -154,12 +207,7 @@ export function ChatContent({ content, isStreaming = false, onOptionSelect }: Ch
154207

155208
return (
156209
<div className={cn(PROSE_CLASSES, '[&>:first-child]:mt-0 [&>:last-child]:mb-0')}>
157-
<Streamdown
158-
isAnimating={isStreaming}
159-
animated
160-
plugins={STREAMDOWN_PLUGINS}
161-
components={MARKDOWN_COMPONENTS}
162-
>
210+
<Streamdown isAnimating={isStreaming} animated components={MARKDOWN_COMPONENTS}>
163211
{rendered}
164212
</Streamdown>
165213
</div>

apps/sim/package.json

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -92,7 +92,6 @@
9292
"@react-email/render": "2.0.0",
9393
"@sim/logger": "workspace:*",
9494
"@socket.io/redis-adapter": "8.3.0",
95-
"@streamdown/code": "1.1.1",
9695
"@t3-oss/env-nextjs": "0.13.4",
9796
"@tanstack/react-query": "5.90.8",
9897
"@tanstack/react-query-devtools": "5.90.2",

bun.lock

Lines changed: 0 additions & 17 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

0 commit comments

Comments
 (0)