Skip to content

Commit fa63c49

Browse files
committed
Merge remote-tracking branch 'origin/codex/remove-indexed-enterprise-search' into codex/safe-search-data-retirement
2 parents bc0b565 + 47e63e1 commit fa63c49

73 files changed

Lines changed: 3385 additions & 810 deletions

File tree

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

‎.github/workflows/desktop-e2e.yml‎

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -11,6 +11,14 @@ on:
1111
- '.github/workflows/desktop-release.yml'
1212
- 'apps/desktop/**'
1313
- 'apps/sim/app/_shell/desktop-update-*.tsx'
14+
- 'apps/sim/app/workspace/**/home/hooks/use-mothership-resize.ts'
15+
- 'apps/sim/app/workspace/**/home/hooks/use-resource-panel.ts'
16+
- 'apps/sim/app/workspace/**/home/components/chat-panel-layout.tsx'
17+
- 'apps/sim/stores/chat-panel/**'
18+
- 'apps/sim/stores/constants.ts'
19+
- 'apps/sim/lib/browser-agent/transport.ts'
20+
- 'apps/sim/lib/core/utils/separator-keys.ts'
21+
- 'apps/sim/scripts/fixtures/chat-panel.tsx'
1422
- 'apps/sim/app/layout.tsx'
1523
- 'apps/sim/hooks/use-desktop-update-state.ts'
1624
- 'apps/sim/lib/desktop/**'

‎apps/desktop/e2e/chat-panel.spec.ts‎

Lines changed: 429 additions & 0 deletions
Large diffs are not rendered by default.

‎apps/sim/app/o/[organizationId]/home/components/get-started/get-started.tsx‎

Lines changed: 7 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -3,8 +3,8 @@
33
import { useEffect, useState } from 'react'
44
import { cn } from '@sim/emcn'
55
import { ArrowRight } from '@sim/emcn/icons'
6-
import Link from 'next/link'
76
import { HomeSection } from '@/components/home/home-section'
7+
import { SettingsGuardedLink } from '@/components/settings/settings-guarded-link'
88
import { OAUTH_SEARCH_READ_SCOPE, oauthScopeSatisfies } from '@/lib/auth/oauth-provider'
99
import { organizationRoutes } from '@/lib/navigation/paths'
1010
import {
@@ -194,7 +194,11 @@ export function GetStarted() {
194194
{steps.map((step, i) => {
195195
const complete = completed[step.id]
196196
return (
197-
<Link key={step.id} href={hrefs[step.id]} className={cn(ROW_CLASS, i > 0 && 'border-t')}>
197+
<SettingsGuardedLink
198+
key={step.id}
199+
href={hrefs[step.id]}
200+
className={cn(ROW_CLASS, i > 0 && 'border-t')}
201+
>
198202
<StepMark complete={complete} />
199203
<span
200204
className={cn(
@@ -205,7 +209,7 @@ export function GetStarted() {
205209
{step.label}
206210
</span>
207211
<ArrowRight className='size-[16px] shrink-0 text-[var(--text-icon)]' />
208-
</Link>
212+
</SettingsGuardedLink>
209213
)
210214
})}
211215
</HomeSection>

‎apps/sim/app/o/[organizationId]/home/organization-home.tsx‎

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -139,7 +139,7 @@ function OrganizationHomeContent({
139139
const canSelectMode =
140140
!hasChat && mothershipAvailable && canBuild && (searchAccess.memberScoped || planEnabled)
141141
const assistantSearchLevel = 'fast'
142-
const panel = useChatResourcePanel(chat, controller)
142+
const panel = useChatResourcePanel(chat, controller, userId)
143143
const addResource = panel.addResourceFromUser
144144
/** Restore only an explicitly selected results tab on an empty Home; closing it clears the URL. */
145145
useEffect(() => {

‎apps/sim/app/o/[organizationId]/settings/components/integrations/search-source-setup.tsx‎

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -133,7 +133,9 @@ export function SearchSourceSetup({
133133
}
134134
const failedQuery = index.isError ? index : null
135135
const initialMode = (type: string) =>
136-
type === 'github' || type === 'slack' ? ('members' as const) : ('admin' as const)
136+
type === 'github' || type === 'slack' || setup['source-access'] === 'members'
137+
? ('members' as const)
138+
: ('admin' as const)
137139

138140
const selectedAccessMode = selectedType ? initialMode(selectedType) : undefined
139141
const selectedAvailability = selectedMeta

‎apps/sim/app/workspace/[workspaceId]/files/components/file-viewer/rich-markdown-editor/code-block.tsx‎

Lines changed: 38 additions & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
import { useEffect, useState } from 'react'
1+
import { lazy, Suspense, useContext, useEffect, useState } from 'react'
22
import {
33
chipVariants,
44
cn,
@@ -11,11 +11,18 @@ import {
1111
import { Check, ChevronDown, Code, Duplicate, Eye, Wrap } from '@sim/emcn/icons'
1212
import type { ReactNodeViewProps } from '@tiptap/react'
1313
import { NodeViewContent, NodeViewWrapper, ReactNodeViewRenderer } from '@tiptap/react'
14+
import { DASHBOARD_EMBED_LANGUAGE } from '@/lib/dashboards/embed-language'
15+
import { MarkdownStreamingContext } from '@/app/workspace/[workspaceId]/files/components/file-viewer/rich-markdown-editor/markdown-streaming-context'
1416
import { looksLikeMermaid, MermaidDiagram } from '../mermaid-diagram'
1517
import { MarkdownCodeBlock } from './code-block-schema'
1618
import { detectLanguage } from './detect-language'
1719
import { useEditorEditable } from './use-editor-editable'
1820

21+
/** Kept out of every rich-markdown surface's graph until a document actually holds a dashboard. */
22+
const DashboardEmbed = lazy(() =>
23+
import('@/components/dashboards/dashboard-embed').then((m) => ({ default: m.DashboardEmbed }))
24+
)
25+
1926
const PLAIN = 'plain'
2027
const MERMAID = 'mermaid'
2128

@@ -51,7 +58,8 @@ const CONTROL_CLASS =
5158
* whenever the cursor is outside it (and always in read-only), and as editable source while the
5259
* cursor is inside, re-rendering on blur (the Linear/GitHub model). The source `<pre>` stays mounted
5360
* (hidden behind the diagram) so ProseMirror keeps managing its contentDOM, and the node remains an
54-
* ordinary code block, so markdown round-trips unchanged.
61+
* ordinary code block, so markdown round-trips unchanged. A ```dashboard fence renders live
62+
* dashboard panels the same way.
5563
*/
5664
function CodeBlockView({ node, updateAttributes, editor, getPos }: ReactNodeViewProps) {
5765
const [wrap, setWrap] = useState(false)
@@ -60,16 +68,19 @@ function CodeBlockView({ node, updateAttributes, editor, getPos }: ReactNodeView
6068
const [peekSource, setPeekSource] = useState(false)
6169
const { copied, copy } = useCopyToClipboard({ resetMs: 1500 })
6270
const editable = useEditorEditable(editor)
71+
const isStreaming = useContext(MarkdownStreamingContext)
6372

6473
const explicitLanguage = node.attrs.language as string | null
6574
const text = node.textContent
6675
const isMermaid = explicitLanguage === MERMAID || (!explicitLanguage && looksLikeMermaid(text))
76+
const isDashboard = explicitLanguage === DASHBOARD_EMBED_LANGUAGE
77+
const isRendered = isMermaid || isDashboard
6778

6879
// Editable Mermaid shows source while the caret is focused inside the block and re-renders the
6980
// diagram on blur (the Linear/GitHub model). The Show source / Show diagram control drives this by
7081
// focusing into / blurring the block; read-only uses {@link peekSource} since there is no caret.
7182
useEffect(() => {
72-
if (!isMermaid || !editable) {
83+
if (!isRendered || !editable) {
7384
setEditingInline(false)
7485
return
7586
}
@@ -92,13 +103,13 @@ function CodeBlockView({ node, updateAttributes, editor, getPos }: ReactNodeView
92103
editor.off('focus', sync)
93104
editor.off('blur', sync)
94105
}
95-
}, [editor, getPos, isMermaid, editable])
106+
}, [editor, getPos, isRendered, editable])
96107

97108
const showSource = editable ? editingInline : peekSource
98-
const showDiagram = isMermaid && text.trim().length > 0 && !showSource
109+
const showRendered = isRendered && text.trim().length > 0 && !showSource
99110

100-
// Skip language detection on the mermaid path — the picker/label never render there.
101-
const language = explicitLanguage ?? (isMermaid ? null : detectLanguage(text)) ?? PLAIN
111+
// Skip language detection on rendered blocks — the picker/label never render there.
112+
const language = explicitLanguage ?? (isRendered ? null : detectLanguage(text)) ?? PLAIN
102113
const label =
103114
LANGUAGE_OPTIONS.find((option) => option.value === language)?.label ??
104115
explicitLanguage ??
@@ -133,18 +144,20 @@ function CodeBlockView({ node, updateAttributes, editor, getPos }: ReactNodeView
133144
)}
134145
contentEditable={false}
135146
>
136-
{isMermaid && (
147+
{isRendered && (
137148
<button
138149
type='button'
139-
aria-label={showSource ? 'Show diagram' : 'Show source'}
150+
aria-label={
151+
showSource ? (isDashboard ? 'Show dashboard' : 'Show diagram') : 'Show source'
152+
}
140153
onMouseDown={(event) => event.preventDefault()}
141154
onClick={toggleSource}
142155
className={CONTROL_CLASS}
143156
>
144157
{showSource ? <Eye /> : <Code />}
145158
</button>
146159
)}
147-
{!isMermaid &&
160+
{!isRendered &&
148161
(editable ? (
149162
// Editable: a language picker. Read-only: a static label — selecting a language calls
150163
// updateAttributes, which would mutate a doc that must not change.
@@ -180,7 +193,7 @@ function CodeBlockView({ node, updateAttributes, editor, getPos }: ReactNodeView
180193
{label}
181194
</span>
182195
))}
183-
{!isMermaid && editable && (
196+
{!isRendered && editable && (
184197
<button
185198
type='button'
186199
aria-label='Toggle line wrap'
@@ -205,22 +218,30 @@ function CodeBlockView({ node, updateAttributes, editor, getPos }: ReactNodeView
205218
{copied ? <Check /> : <Duplicate />}
206219
</button>
207220
</div>
208-
<pre className={cn('code-editor-theme pr-20', showDiagram && 'hidden')} data-wrap={wrap}>
221+
<pre className={cn('code-editor-theme pr-20', showRendered && 'hidden')} data-wrap={wrap}>
209222
<NodeViewContent<'code'> as='code' />
210223
</pre>
211-
{showDiagram && (
212-
// Clicking the diagram selects the whole node (same selection ring as an image/code block)
213-
// instead of dropping a caret inside — preventDefault stops ProseMirror placing the caret,
214-
// which would otherwise flip to source. Editing is an explicit Show source / blur action.
224+
{showRendered && (
225+
// Select the whole node instead of placing a caret, which would flip the block to source.
215226
<div
216227
contentEditable={false}
228+
className={cn(isDashboard && 'dashboard-embed')}
217229
onMouseDown={(event) => {
230+
const target = event.target
231+
if (!(target instanceof Element) || !event.currentTarget.contains(target)) return
232+
if (target.closest('button, input')) return
218233
event.preventDefault()
219234
const pos = typeof getPos === 'function' ? getPos() : null
220235
if (typeof pos === 'number') editor.commands.setNodeSelection(pos)
221236
}}
222237
>
223-
<MermaidDiagram definition={text} className='mermaid-diagram-frame' />
238+
{isDashboard ? (
239+
<Suspense fallback={null}>
240+
<DashboardEmbed source={text} isStreaming={isStreaming} />
241+
</Suspense>
242+
) : (
243+
<MermaidDiagram definition={text} className='mermaid-diagram-frame' />
244+
)}
224245
</div>
225246
)}
226247
</NodeViewWrapper>
Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,4 @@
1+
import { createContext } from 'react'
2+
3+
/** True while agent output is streaming into the editor, for node views that render its content. */
4+
export const MarkdownStreamingContext = createContext(false)

‎apps/sim/app/workspace/[workspaceId]/files/components/file-viewer/rich-markdown-editor/rich-markdown-editor.css‎

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -391,6 +391,12 @@
391391
margin: 1rem 0;
392392
}
393393

394+
/* A dashboard results table sizes its own columns and sits flush in its panel. */
395+
.rich-markdown-nodes .dashboard-embed table {
396+
table-layout: auto;
397+
margin: 0;
398+
}
399+
394400
.rich-markdown-nodes th > p,
395401
.rich-markdown-nodes td > p {
396402
margin: 0;

‎apps/sim/app/workspace/[workspaceId]/files/components/file-viewer/rich-markdown-editor/rich-markdown-editor.tsx‎

Lines changed: 13 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -68,6 +68,7 @@ import {
6868
} from '@/app/workspace/[workspaceId]/files/components/file-viewer/rich-markdown-editor/markdown-fidelity'
6969
import { parseMarkdownToDoc } from '@/app/workspace/[workspaceId]/files/components/file-viewer/rich-markdown-editor/markdown-parse'
7070
import { isPlainTextPaste } from '@/app/workspace/[workspaceId]/files/components/file-viewer/rich-markdown-editor/markdown-paste'
71+
import { MarkdownStreamingContext } from '@/app/workspace/[workspaceId]/files/components/file-viewer/rich-markdown-editor/markdown-streaming-context'
7172
import { useEditorMentions } from '@/app/workspace/[workspaceId]/files/components/file-viewer/rich-markdown-editor/mention'
7273
import { EditorBubbleMenu } from '@/app/workspace/[workspaceId]/files/components/file-viewer/rich-markdown-editor/menus/bubble-menu'
7374
import { LinkHoverCard } from '@/app/workspace/[workspaceId]/files/components/file-viewer/rich-markdown-editor/menus/link-hover-card'
@@ -1439,17 +1440,19 @@ export function LoadedRichMarkdownEditor({
14391440
void insertImagesRef.current(images, range)
14401441
}}
14411442
/>
1442-
{showPlaceholder && placeholder && (
1443-
<ReadOnlyPlaceholder
1444-
content={placeholder.content}
1445-
file={file}
1446-
workspaceId={workspaceId}
1443+
<MarkdownStreamingContext value={isStreaming}>
1444+
{showPlaceholder && placeholder && (
1445+
<ReadOnlyPlaceholder
1446+
content={placeholder.content}
1447+
file={file}
1448+
workspaceId={workspaceId}
1449+
/>
1450+
)}
1451+
<EditorContent
1452+
editor={editor}
1453+
className={cn(EDITOR_SURFACE_CLASS, showPlaceholder && 'hidden')}
14471454
/>
1448-
)}
1449-
<EditorContent
1450-
editor={editor}
1451-
className={cn(EDITOR_SURFACE_CLASS, showPlaceholder && 'hidden')}
1452-
/>
1455+
</MarkdownStreamingContext>
14531456
</div>
14541457
</div>
14551458
)

‎apps/sim/app/workspace/[workspaceId]/files/components/file-viewer/rich-markdown-editor/rich-markdown-field.tsx‎

Lines changed: 12 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -27,6 +27,7 @@ import {
2727
} from '@/app/workspace/[workspaceId]/files/components/file-viewer/rich-markdown-editor/markdown-fidelity'
2828
import { parseMarkdownToDoc } from '@/app/workspace/[workspaceId]/files/components/file-viewer/rich-markdown-editor/markdown-parse'
2929
import { isPlainTextPaste } from '@/app/workspace/[workspaceId]/files/components/file-viewer/rich-markdown-editor/markdown-paste'
30+
import { MarkdownStreamingContext } from '@/app/workspace/[workspaceId]/files/components/file-viewer/rich-markdown-editor/markdown-streaming-context'
3031
import { useEditorMentions } from '@/app/workspace/[workspaceId]/files/components/file-viewer/rich-markdown-editor/mention'
3132
import { EditorBubbleMenu } from '@/app/workspace/[workspaceId]/files/components/file-viewer/rich-markdown-editor/menus/bubble-menu'
3233
import { LinkHoverCard } from '@/app/workspace/[workspaceId]/files/components/file-viewer/rich-markdown-editor/menus/link-hover-card'
@@ -444,15 +445,17 @@ function LoadedRichMarkdownField({
444445
}}
445446
/>
446447
)}
447-
<EditorContent
448-
editor={editor}
449-
className={cn(
450-
'flex flex-1 flex-col',
451-
isBare
452-
? proseClassName
453-
: 'selection:bg-[var(--selection-bg)] selection:text-[var(--text-primary)] dark:selection:bg-[var(--selection-dark)] dark:selection:text-white'
454-
)}
455-
/>
448+
<MarkdownStreamingContext value={isStreaming}>
449+
<EditorContent
450+
editor={editor}
451+
className={cn(
452+
'flex flex-1 flex-col',
453+
isBare
454+
? proseClassName
455+
: 'selection:bg-[var(--selection-bg)] selection:text-[var(--text-primary)] dark:selection:bg-[var(--selection-dark)] dark:selection:text-white'
456+
)}
457+
/>
458+
</MarkdownStreamingContext>
456459
</div>
457460
)
458461
}

0 commit comments

Comments
 (0)