fix(knowledge): keep Slack searchable while its member crawl runs - #8005
Conversation
|
The latest updates on your projects. Learn more about Vercel for GitHub.
|
|
Members-mode search shows a document only while its member observation is younger than a day, but a full Slack listing re-fetched every thread and so took far longer than a day on a large workspace, leaving most of Slack invisible. Access is now renewed per channel the member can still read, and listings re-read only threads whose root changed, are active, or are due in a rolling 28-day refresh.
A Slack conversation listing that stops at its page cap now reports itself incomplete, and the member's renewal watermark only advances once every reachable channel has been listed and renewed.
c78bd1c to
cef0b6d
Compare
|
@cubic-dev-ai review this PR |
@waleedlatif1 I have started the AI code review. It will take a few minutes to complete. |
There was a problem hiding this comment.
3 issues found across 23 files
Confidence score: 3/5
apps/sim/lib/knowledge/connectors/sync-primitives.ts: A current deferred hash can returnunchangedbeforeforceRehydrateis evaluated, causing a requested forced rehydration to be skipped; checkforceRehydratebefore accepting the matcher result.apps/sim/lib/knowledge/connectors/member-observations.ts: Post-query scope filtering can consume the 10-minute renewal budget on stale observations before accessible rows are reached; push the scope-prefix predicate into SQL or otherwise filter before applying the budget.apps/sim/lib/knowledge/connectors/listing-checkpoint.ts: Resuming an incomplete ordinary Slack listing during an explicit full resync restoresfullSyncasfalse, so resumed pages skip quiet-thread hydration; preserve the explicit full-resync state when resuming.
Prompt for AI agents (unresolved issues)
Check if these issues are valid — if so, understand the root cause of each and fix them. If appropriate, use sub-agents to investigate and fix each issue separately.
<file name="apps/sim/lib/knowledge/connectors/member-observations.ts">
<violation number="1" location="apps/sim/lib/knowledge/connectors/member-observations.ts:194">
P2: When a member has many stale observations outside their current scopes, this post-query filter can exhaust the 10-minute renewal budget before reaching accessible rows. Push the scope-prefix predicate into SQL, or query scopes separately, before applying the page limit so inaccessible observations do not consume renewal work.</violation>
</file>
<file name="apps/sim/lib/knowledge/connectors/sync-primitives.ts">
<violation number="1" location="apps/sim/lib/knowledge/connectors/sync-primitives.ts:291">
P2: When `forceRehydrate` is set and the connector matcher reports the deferred hash as current, this check returns `unchanged` before the force branch runs. Check `forceRehydrate` before accepting a matcher result so full resyncs always rehydrate deferred documents.</violation>
</file>
<file name="apps/sim/lib/knowledge/connectors/listing-checkpoint.ts">
<violation number="1" location="apps/sim/lib/knowledge/connectors/listing-checkpoint.ts:118">
P2: When an explicit full resync resumes an incomplete ordinary Slack listing, this line restores `fullSync` from the old checkpoint, which is `false`. Slack therefore skips quiet-thread hydration on the resumed pages, so the full resync does not reread every thread. Start a new full-sync checkpoint or carry the explicit full-sync request into the resumed generation before setting this context flag.</violation>
</file>
Tip: cubic can generate docs of your entire codebase and keep them up to date. Try it here.
Fix all with cubic | Re-trigger cubic
… identity change A Full resync now starts a new full-sync listing even when the connector does not rehydrate, so Slack rereads every thread instead of resuming an ordinary cursor. A member whose identity changes or whose token is rejected also loses its scope-renewal watermark, so renewal runs for the new identity right away.
|
@cubic-dev-ai review this PR |
@waleedlatif1 I have started the AI code review. It will take a few minutes to complete. |
There was a problem hiding this comment.
All reported issues were addressed across 24 files
Tip: cubic can generate docs of your entire codebase and keep them up to date. Try it here.
Fix all with cubic | Re-trigger cubic
Accessible scopes are now listed page by page, and a renewal that does not finish within its budget stores its channel-listing cursor and start time, so the next run continues from there instead of re-reading the first pages and never reaching channels past them. The watermark records when the whole pass began, and an expired cursor restarts the pass once.
|
@cubic-dev-ai review this PR |
@waleedlatif1 I have started the AI code review. It will take a few minutes to complete. |
There was a problem hiding this comment.
All reported issues were addressed across 24 files
Tip: cubic can generate docs of your entire codebase and keep them up to date. Try it here.
Fix all with cubic | Re-trigger cubic
Scope renewal now gathers container pages into batches before scanning the member's stale observations, so the scan runs once per batch instead of once per source page, and an unfinished batch resumes from where it was read. Content that hydrates unchanged under a new hash also refreshes its source URL, modified time and tags, and the member sync log records how many observations renewal kept fresh.
|
@cubic-dev-ai review this PR |
@waleedlatif1 I have started the AI code review. It will take a few minutes to complete. |
There was a problem hiding this comment.
All reported issues were addressed across 26 files
You've manually re-run cubic several times on this PR. Each manual re-review checks the full PR again and counts toward your usage quota. To preserve your usage limits, we recommend letting cubic automatically review new commits.
Tip: cubic can generate docs of your entire codebase and keep them up to date. Try it here.
Fix all with cubic | Re-trigger cubic
Summary
ConnectorConfig.listAccessibleScopes: before each member's listing, the member engine renews that member's observations under every channel they can still read, about twice a day (newknowledge_connector_member.scope_renewed_atwatermark, expand-only migration). Access no longer depends on re-crawling content, and a channel the member left still lapses within a dayConnectorConfig.matchContentHash: Slack lists a thread under its root version (edit, reply count, latest reply, channel name) and storesversion + text hash, so unchanged threads are not re-fetched. Re-read threads whose text is unchanged, including ones stored under the old text-only hash, only advance the stored hash, so nothing is re-embeddedskippedRetryPolicy: 'source-change'auth.testreturns (chat.getPermalinkonly as a fallback), andconversations.infois fetched once per channel per runType of Change
Testing
lib/knowledge+connectors(5,466 passing); each new behavior fails its test when revertedmember-scope-renewaltest, plusslack-empty-threads(both added to the CI integration list) and the surrounding connector suites, 77 passingbun run lint,check:audits,check:migrations origin/staging, type-checkChecklist