fix(connectors): harden 10 KB connectors after audit#4410
fix(connectors): harden 10 KB connectors after audit#4410waleedlatif1 merged 20 commits intostagingfrom
Conversation
Validated each issue against provider docs before fixing.
- jira: migrate from deprecated /rest/api/3/search (Atlassian sunset
May 2025) to /rest/api/3/search/jql with nextPageToken pagination
- confluence: unify stub hash across v1 CQL (`when`) and v2
(`createdAt`) paths via shared pageToStub helper using version.number
- salesforce: replace hardcoded login.salesforce.com userinfo with
host fallback so sandbox-issued tokens (test.salesforce.com) work
- servicenow: validate sys_id against /^[a-f0-9]{32}$/ and switch
getDocument to path-based /api/now/table/{table}/{sys_id} to close
encoded-query injection; reject `^` in kbCategory filter
- zendesk: URL-encode Search API query via URLSearchParams; whitelist
ticket statuses; encode locale path segment
- github: add 10MB cap and /git/blobs/{sha} fallback for files >1MB
that /contents/ returns with encoding:"none"
- slack: replace SHA-256 over formatted-message window with metadata
hash slack:{channelId}:{latestTs}:{count} so list and getDocument
agree; cache auth.test team_id on syncContext
- obsidian: drop syncRunId from stub hash (Local REST API has no
HEAD/Last-Modified per OpenAPI spec); fall back to path-only stub
so engine two-stage check short-circuits unchanged notes
- evernote: title fallback for attachments-only notes — breaks
infinite hydration loop where empty plaintext returned null
- google-docs: drop residual `error instanceof Error` pattern
Confluence and Slack hash format changes self-heal with a one-time
re-sync; no data loss.
Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
… edits
Audit caught that the metadata hash slack:{channel}:{latestTs}:{count}
misses edits to the oldest message in the rolling window — count and
latestTs both stay constant. Adding oldestTs catches window-shift
when a new message arrives and pushes the oldest out without changing
the newest.
Also drop residual error instanceof Error pattern in validateConfig.
Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
|
The latest updates on your projects. Learn more about Vercel for GitHub. |
PR SummaryMedium Risk Overview Key changes: Confluence now generates a canonical stub via Hardening + correctness: GitHub skips >10MB files, detects binary blobs, and falls back to the Blobs API when Reviewed by Cursor Bugbot for commit 75f0b1a. Configure here. |
Greptile SummaryThis PR hardens 10 connector implementations after an audit, addressing a Jira API deprecation (sunset May 2025), injection risks in ServiceNow queries, sandbox token failures in Salesforce, hash instability in Confluence/Slack, large-file handling in GitHub, and several smaller content/validation fixes across Evernote, Zendesk, Obsidian, and Google Docs. All changes are well-documented and include defensive logging; Confluence and Slack content hashes will change on first deploy, triggering a one-time re-sync as noted in the PR description. Confidence Score: 5/5Safe to merge — no P0 or P1 bugs found; all fixes are well-reasoned and include defensive logging. All 11 files were reviewed in depth. Jira cursor logic correctly uses lastIndexOf to handle tokens containing the separator character. Obsidian auth validation correctly reads the authenticated body field inside an outer try-catch. ServiceNow injection prevention is sound. Slack hash change and Confluence cursor restart are intentional, documented, and self-healing. No regressions identified. No files require special attention. The Confluence and Slack contentHash format changes will trigger a one-time full re-sync on first deploy, which is expected and noted in the PR description. Important Files Changed
Reviews (13): Last reviewed commit: "fix(slack): align validateConfig channel..." | Re-trigger Greptile |
- jira: thread VALIDATE_RETRY_OPTIONS through getJiraCloudId so the validate path uses the tighter retry budget - confluence: thread VALIDATE_RETRY_OPTIONS through getConfluenceCloudId; drop residual error instanceof Error pattern - zendesk: log a warning when statusFilter is set and limit exceeds the Search API 1000-result cap; add priority to tagDefinitions and mapTags so the metadata isn't orphaned Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
- github: skip blob fetch for empty 0-byte files - salesforce: add fallback message for empty error - zendesk: warn on invalid statusFilter instead of silent fallthrough - evernote: remove dead content.trim() guard
|
Also addressed greptile's Evernote |
|
@greptile |
|
@cursor review |
|
@greptile |
|
@cursor review |
- servicenow: case-insensitive sys_id pattern; validate workflowState/incidentState/incidentPriority as numeric, kbCategory via allowlist - salesforce: include 400 in userinfo host fallthrough for sandbox tokens - zendesk: add missing 'new' and 'hold' options to ticketStatus dropdown
|
@greptile |
|
@cursor review |
|
@greptile |
Switch from a \w-based allowlist (ASCII only) to a denylist that rejects only encoded-query-meaningful characters (^, control chars, quotes). International category names like 'Général' or 'Ação' are now accepted.
|
@greptile |
|
@cursor review |
Wiki-template KB articles populate the wiki field and leave text empty; HTML-template articles do the opposite. Removing wiki caused wiki-format articles to resolve to empty content and be silently skipped.
|
@greptile |
|
@cursor review |
- jira: rely solely on absence of nextPageToken for end-of-results; data.isLast on /rest/api/3/search/jql is unreliable (JRACLOUD-95477) and the OR-with-isLast logic could truncate pagination early - google-docs: strip trailing newline from each paragraph before joining so heading->body produces a single newline, not two
data.isLast on /rest/api/3/search/jql is unreliable (JRACLOUD-95477) and the previous OR-with-isLast logic could truncate pagination early if Jira ever returned isLast=true alongside a valid nextPageToken.
|
@greptile |
|
@cursor review |
There was a problem hiding this comment.
✅ Bugbot reviewed your changes and found no new issues!
Comment @cursor review or bugbot run to trigger another review on this PR
Reviewed by Cursor Bugbot for commit 71f6256. Configure here.
DM (D...) channel IDs require im:*/mpim:* OAuth scopes, which the connector does not request. The regex now matches only public (C) and private (G) channel IDs to fail fast with a clearer error instead of hitting missing_scope from Slack.
|
@greptile |
|
@cursor review |
The previous fix narrowed the regex in resolveChannel to [CG] but missed the duplicate in validateConfig, which still admitted DM IDs and would fall through to a name-based search returning 'Channel not found.'
|
@greptile |
|
@cursor review |
There was a problem hiding this comment.
✅ Bugbot reviewed your changes and found no new issues!
Comment @cursor review or bugbot run to trigger another review on this PR
Reviewed by Cursor Bugbot for commit 75f0b1a. Configure here.
Summary
/rest/api/3/search(Atlassian sunset May 2025) to/rest/api/3/search/jqlwithnextPageTokenpaginationwhen) and v2 (createdAt) paths via sharedpageToStubhelper usingversion.numberlogin.salesforce.comuserinfo with host fallback so sandbox-issued tokens (test.salesforce.com) worksys_idagainst/^[a-f0-9]{32}$/and switchgetDocumentto path-based/api/now/table/{table}/{sys_id}to close encoded-query injection; reject^inkbCategoryURLSearchParams; whitelist ticket statuses; encode locale path segment/git/blobs/{sha}fallback for files >1MB that/contents/returns withencoding:"none"slack:{channelId}:{oldestTs}:{latestTs}:{count}so list and getDocument agree; cacheauth.testteam_idonsyncContextsyncRunIdfrom stub hash (Local REST API has no HEAD/Last-Modified per OpenAPI spec); fall back to path-only stuberror instanceof ErrorpatternEach fix was validated against the provider API docs by an independent subagent before applying. Confluence and Slack hash format changes self-heal with a one-time re-sync; no data loss.
Type of Change
Testing
Tested manually. Lint and typecheck pass.
Checklist