Skip to content

Commit 1610baf

Browse files
committed
fix(knowledge): repair CI and apply cleanup passes
- Bump the chart version for the member-sync cron and secret - Pass an access scope to getDocuments in the list-convention test and resolve a knowledge scope only for knowledge-base file reads - Drop memoisation nothing observes, read the enrollment error from the mutation, hoist the empty connector list, use the default Cancel variant, let Badge own its gap, and keep the sidebar lit on the Search tab
1 parent b4201fc commit 1610baf

8 files changed

Lines changed: 50 additions & 57 deletions

File tree

apps/sim/app/workspace/[workspaceId]/knowledge/[id]/components/connectors-section/connectors-section.tsx

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -444,7 +444,7 @@ function ConnectorCard({
444444
{syncsPerMember && (
445445
<Tooltip.Root>
446446
<Tooltip.Trigger asChild>
447-
<Badge variant='gray' size='sm' className='flex-shrink-0 gap-1'>
447+
<Badge variant='gray' size='sm' className='flex-shrink-0'>
448448
<Users className='size-3' />
449449
Per member
450450
</Badge>

apps/sim/app/workspace/[workspaceId]/knowledge/[id]/components/edit-connector-modal/edit-connector-modal.tsx

Lines changed: 6 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -242,8 +242,7 @@ export function EditConnectorModal({
242242

243243
const hasMaxAccess = hasWorkspaceMaxConnectorAccess(ownerBilling)
244244

245-
const persistedAccess = useMemo(() => currentAccess(connector), [connector])
246-
const accessDirty = accessChanged(persistedAccess, access)
245+
const accessDirty = accessChanged(currentAccess(connector), access)
247246
const groupOptions = useConnectorMemberGroupOptions({
248247
workspaceId,
249248
connectorConfig,
@@ -260,14 +259,10 @@ export function EditConnectorModal({
260259
/** A disabled member sync is re-enabled by applying the current binding again. */
261260
const canReenableMemberSync =
262261
!accessDirty && connector.accessMode === 'members' && connector.memberSyncStatus === 'disabled'
263-
const memberCapFieldIds = useMemo(
264-
() =>
265-
new Set(
266-
access.accessMode === 'members'
267-
? (connectorConfig?.permissionScopedListing?.capFieldIds ?? [])
268-
: []
269-
),
270-
[access.accessMode, connectorConfig]
262+
const memberCapFieldIds = new Set(
263+
access.accessMode === 'members'
264+
? (connectorConfig?.permissionScopedListing?.capFieldIds ?? [])
265+
: []
271266
)
272267

273268
const persistedCanonicalModes = useMemo(
@@ -590,7 +585,7 @@ function SettingsTab({
590585
? 'Switch to per-member access'
591586
: 'Switch to workspace access'}
592587
</Button>
593-
<Button variant='ghost' size='sm' onClick={onResetAccess} disabled={isSaving}>
588+
<Button variant='default' size='sm' onClick={onResetAccess} disabled={isSaving}>
594589
Cancel
595590
</Button>
596591
</div>

apps/sim/app/workspace/[workspaceId]/search/components/member-connectors-section/member-connectors-section.tsx

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -15,6 +15,7 @@ import {
1515
import { useMemberEnrollment } from '@/hooks/use-member-enrollment'
1616

1717
const SHARED_WITH_YOU_LABEL = 'Shared with you'
18+
const EMPTY_CONNECTORS: WorkspaceMemberConnector[] = []
1819

1920
/** Memberships the viewer can act on themselves. */
2021
const CONNECTABLE: ReadonlySet<ViewerConnectorMembership> = new Set([
@@ -54,7 +55,7 @@ interface MemberConnectorsSectionProps {
5455
* page offers, so a person can do it from whichever surface they are on.
5556
*/
5657
export function MemberConnectorsSection({ workspaceId, search }: MemberConnectorsSectionProps) {
57-
const { data: connectors = [] } = useWorkspaceMemberConnectors(workspaceId)
58+
const { data: connectors = EMPTY_CONNECTORS } = useWorkspaceMemberConnectors(workspaceId)
5859
const connectedConnectorIds = useMemo(
5960
() =>
6061
new Set(

apps/sim/app/workspace/[workspaceId]/w/components/sidebar/sidebar.tsx

Lines changed: 6 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -793,9 +793,12 @@ export const Sidebar = memo(function Sidebar({
793793
label: 'Integrations',
794794
icon: Integration,
795795
href: `/workspace/${workspaceId}/integrations`,
796-
/* Skills is a tab of this surface, not its own nav item — keep the entry
797-
lit while the user is on it. */
798-
additionalActivePaths: [`/workspace/${workspaceId}/skills`],
796+
/* Skills and Search are tabs of this surface, not their own nav items —
797+
keep the entry lit while the user is on either. */
798+
additionalActivePaths: [
799+
`/workspace/${workspaceId}/skills`,
800+
`/workspace/${workspaceId}/search`,
801+
],
799802
hidden: permissionConfig.hideIntegrationsTab,
800803
},
801804
].filter((item) => !item.hidden),

apps/sim/hooks/use-member-enrollment.ts

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

3-
import { useCallback, useEffect, useState } from 'react'
3+
import { useEffect, useState } from 'react'
44
import { createLogger } from '@sim/logger'
55
import { type QueryKey, useQueryClient } from '@tanstack/react-query'
66
import { useStartConnectorMemberEnrollment } from '@/hooks/queries/kb/connectors'
@@ -34,9 +34,8 @@ export function useMemberEnrollment({
3434
connectedConnectorIds,
3535
}: UseMemberEnrollmentProps) {
3636
const queryClient = useQueryClient()
37-
const { mutate: startEnrollment, isPending } = useStartConnectorMemberEnrollment()
37+
const { mutate: startEnrollment, isPending, error } = useStartConnectorMemberEnrollment()
3838
const [awaitingSince, setAwaitingSince] = useState<ReadonlyMap<string, number>>(() => new Map())
39-
const [error, setError] = useState<string | null>(null)
4039

4140
const awaiting = [...awaitingSince.keys()].some((id) => !connectedConnectorIds.has(id))
4241
useEffect(() => {
@@ -59,39 +58,31 @@ export function useMemberEnrollment({
5958
return () => clearInterval(timer)
6059
}, [awaiting, connectedConnectorIds, membershipQueryKeys, queryClient])
6160

62-
const connect = useCallback(
63-
(knowledgeBaseId: string, connectorId: string) => {
64-
setError(null)
65-
const tab = window.open('about:blank', '_blank')
66-
if (tab) tab.opener = null
67-
startEnrollment(
68-
{ knowledgeBaseId, connectorId },
69-
{
70-
onSuccess: ({ url }) => {
71-
if (tab && !tab.closed) {
72-
tab.location.href = url
73-
} else {
74-
window.location.assign(url)
75-
return
76-
}
77-
setAwaitingSince((current) => new Map(current).set(connectorId, Date.now()))
78-
},
79-
onError: (err) => {
80-
tab?.close()
81-
logger.error('Failed to start member enrollment', { error: err.message })
82-
setError(err.message)
83-
},
84-
}
85-
)
86-
},
87-
[startEnrollment]
88-
)
61+
const connect = (knowledgeBaseId: string, connectorId: string) => {
62+
const tab = window.open('about:blank', '_blank')
63+
if (tab) tab.opener = null
64+
startEnrollment(
65+
{ knowledgeBaseId, connectorId },
66+
{
67+
onSuccess: ({ url }) => {
68+
if (tab && !tab.closed) {
69+
tab.location.href = url
70+
} else {
71+
window.location.assign(url)
72+
return
73+
}
74+
setAwaitingSince((current) => new Map(current).set(connectorId, Date.now()))
75+
},
76+
onError: (err) => {
77+
tab?.close()
78+
logger.error('Failed to start member enrollment', { error: err.message })
79+
},
80+
}
81+
)
82+
}
8983

90-
const isAwaiting = useCallback(
91-
(connectorId: string) =>
92-
awaitingSince.has(connectorId) && !connectedConnectorIds.has(connectorId),
93-
[awaitingSince, connectedConnectorIds]
94-
)
84+
const isAwaiting = (connectorId: string) =>
85+
awaitingSince.has(connectorId) && !connectedConnectorIds.has(connectorId)
9586

96-
return { connect, isAwaiting, isPending, error }
87+
return { connect, isAwaiting, isPending, error: error?.message ?? null }
9788
}

apps/sim/lib/api/list-convention.test.ts

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -56,6 +56,7 @@ vi.mock('@/lib/workflows/skills/builtin-skills', () => ({
5656

5757
import { listVisibleWorkspaceCredentials } from '@/lib/credentials/queries'
5858
import { listFoldersForWorkspace } from '@/lib/folders/queries'
59+
import { WORKSPACE_ACCESS_SCOPE } from '@/lib/knowledge/access/scope'
5960
import { getDocuments } from '@/lib/knowledge/documents/service'
6061
import { getWorkspaceKnowledgeBases } from '@/lib/knowledge/service'
6162
import { listWorkspaceMcpServers } from '@/lib/mcp/queries'
@@ -182,7 +183,8 @@ const CASES: ListCase[] = [
182183
getDocuments(
183184
'knowledge-1',
184185
{ search, sortBy: sortBy as never, sortOrder: sortOrder as never },
185-
'request-1'
186+
'request-1',
187+
WORKSPACE_ACCESS_SCOPE
186188
),
187189
sort: {
188190
sortBy: 'fileSize',

apps/sim/lib/execution/payloads/materialization.server.ts

Lines changed: 4 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -319,9 +319,10 @@ export async function assertUserFileContentAccess(
319319
* is one; `options.userId` alone may be the workflow owner standing in for an
320320
* actorless run and must not widen what the run can read.
321321
*/
322-
const knowledgeAccess = options.principal
323-
? await resolveKnowledgeAccessScope(options.principal, { workspaceId: options.workspaceId })
324-
: undefined
322+
const knowledgeAccess =
323+
context === 'knowledge-base' && options.principal
324+
? await resolveKnowledgeAccessScope(options.principal, { workspaceId: options.workspaceId })
325+
: undefined
325326
const hasAccess = await verifyFileAccess(file.key, options.userId, undefined, context, false, {
326327
knowledgeAccess,
327328
})

helm/sim/Chart.yaml

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,7 @@ apiVersion: v2
22
name: sim
33
description: A Helm chart for Sim - the open-source AI workspace where teams build, deploy, and manage AI agents
44
type: application
5-
version: 1.7.0
5+
version: 1.8.0
66
appVersion: "v0.8.18"
77
kubeVersion: ">=1.25.0-0"
88
home: https://sim.ai

0 commit comments

Comments
 (0)