refactor(list): align all list commands to issue list standards#453
Merged
refactor(list): align all list commands to issue list standards#453
Conversation
issue view with project-search format (e.g., `buybridge-5BS`) was making 5 sequential HTTP calls totaling ~2.4s. The biggest overhead was listOrganizations() (getUserRegions + listOrganizationsInRegion = ~800ms) inside findProjectsBySlug, even when DSN detection already identified the project. Two optimizations: 1. DSN-aware shortcut in resolveProjectSearch: after alias cache miss, check resolveFromDsn() for a matching project before falling back to findProjectsBySlug. Saves ~1200ms on cached runs, ~800ms first run. 2. Cached-orgs fast path in findProjectsBySlug: check org_regions cache before calling listOrganizations(). Saves ~800ms when org data is cached from any previous command. Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
Add two targeted tests proving the performance optimizations work: 1. resolveIssue with project-search format uses DSN shortcut when the DSN-detected project matches, skipping the expensive listOrganizations() fan-out entirely. 2. findProjectsBySlug uses cached org_regions to skip getUserRegions() + listOrganizationsInRegion() when org data is already cached from a previous command. Both tests verify the optimization by tracking HTTP requests and asserting that /users/me/regions/ and /organizations/ are never called. Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
1. Narrow try/catch in resolveProjectSearch to only wrap resolveFromDsn(). Previously getIssueByShortId errors (e.g. 404) were silently caught, causing a fallback to findProjectsBySlug which would duplicate the expensive short ID resolution call before failing with the same error. 2. Add comment explaining why the org_regions cache is expected to be complete when findProjectsBySlug runs: the project-search format's short suffix only comes from `sentry issue list` output, which already called listOrganizations() and populated all orgs. Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
When the cached-orgs fast path finds no projects and falls through to the full listOrganizations() path, avoid re-searching orgs that already returned 404 by filtering them out with a Set lookup. Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
Instead of patching findProjectsBySlug with a per-callsite cache check,
move the caching into listOrganizations() so all 12 callers benefit:
- Add org_name column to org_regions table (schema v9)
- Split listOrganizations into cached + uncached variants:
- listOrganizations() returns from SQLite cache when populated
- listOrganizationsUncached() always hits the API (for org list,
auth status, resolveEffectiveOrg)
- Add getCachedOrganizations() to db/regions.ts
- Simplify findProjectsBySlug back to single-path (no getAllOrgRegions
fast-path needed — listOrganizations handles it)
- Update org list and auth status to use uncached variant
- Update resolveEffectiveOrg to use uncached (it explicitly refreshes)
getCachedOrganizations() now checks updated_at against a 7-day TTL. Stale entries are ignored, forcing a fresh API fetch. This ensures users who join new orgs see them within a bounded window without needing to run --fresh or auth status.
- Self-hosted early return in listOrganizationsUncached now calls setOrgRegions before returning (Seer: cache was skipped) - Add disableOrgCache() to db/regions.ts, called by applyFreshFlag so --fresh bypasses the org listing cache (BugBot: stale data) - getCachedOrganizations returns empty when cache is disabled
- Add isTraceId() non-throwing boolean helper to trace-id.ts
- Rewrite log list: remove --trace flag, accept trace-id as positional
arg (sentry log list <trace-id>, sentry log list <org>/<trace-id>),
add --period/-t flag, JSON envelope { data, hasMore }
- Add withProgress spinner to all list commands: trace list, span list,
trace logs, org list, trial list, project list, and org-list.ts
framework (team/repo list get spinners automatically)
- Align trace logs JSON output to { data, hasMore } envelope
- Fix pre-existing 5s timeout failures in dispatchOrgScopedList tests
by mocking resolveEffectiveOrg and withProgress
Contributor
Semver Impact of This PR🟢 Patch (bug fixes) 📋 Changelog PreviewThis is how your changes will appear in the changelog. Bug Fixes 🐛
Internal Changes 🔧
🤖 This preview updates automatically when you update the PR. |
…ommands # Conflicts: # AGENTS.md # src/commands/org/list.ts # src/lib/api/organizations.ts # src/lib/db/regions.ts # src/lib/db/schema.ts
Contributor
Codecov Results 📊✅ 116 passed | Total: 116 | Pass Rate: 100% | Execution Time: 0ms 📊 Comparison with Base Branch
✨ No test changes detected All tests are passing successfully. ✅ Patch coverage is 100.00%. Project has 1139 uncovered lines. Files with missing lines (1)
Coverage diff@@ Coverage Diff @@
## main #PR +/-##
==========================================
+ Coverage 95.20% 95.23% +0.03%
==========================================
Files 175 175 —
Lines 23729 23854 +125
Branches 0 0 —
==========================================
+ Hits 22590 22715 +125
- Misses 1139 1139 —
- Partials 0 0 —Generated by Codecov Action |
…envelope
- Remove --trace flag usage from e2e tests, use positional trace-id
- Update JSON assertions to expect { data, hasMore } envelope
- Rename describe block from '--trace' to '(trace mode)'
- Make --period flag optional (no default) to fix sentinel-value bug where explicit --period 90d was silently overridden to 14d in trace mode. Now undefined = not set, project mode defaults to 90d, trace mode defaults to 14d. - Add json option to withProgress to suppress spinner in JSON mode, matching poll() behavior. Pass json: flags.json at all 19 call sites.
- parseLogListArgs now checks last arg for trace-id in 2+ arg case (e.g., 'sentry log list my-org <trace-id>') - Move DEFAULT_PROJECT_PERIOD above JSDoc so it attaches correctly to executeSingleFetch
BYK
commented
Mar 18, 2026
…ization - All withProgress messages now show '(up to N)...' matching issue list - Extract normalizeHexId() in hex-id.ts, use in both validateHexId and isTraceId to eliminate duplicated normalization logic - validateTraceId now delegates through isTraceId's normalization path
There was a problem hiding this comment.
Cursor Bugbot has reviewed your changes and found 1 potential issue.
Bugbot Autofix is OFF. To automatically fix reported issues with cloud agents, enable autofix in the Cursor dashboard.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.

Summary
Aligns all
listsubcommands to the standards established bysentry issue list.Key Changes
sentry log list— trace-id as positional arg--traceflag entirelysentry log list <trace-id>,sentry log list <org>/<trace-id>parseLogListArgs()withisTraceId()disambiguation (32-char hex → trace mode, otherwise project mode)--period/-tflag (default90d, trace mode auto-uses14d){ data, hasMore }envelope instead of flat arraywithProgressspinner in all list commandstrace list,span list,trace logs,org list,trial list,project listorg-list.tsframework soteam listandrepo listget spinners automaticallyJSON envelope alignment
trace logsnow returns{ data, hasMore }envelopeTest improvements
dispatchOrgScopedListtests (missingresolveEffectiveOrgmock)log/list.test.ts(49 tests)isTraceId()tests totrace-id.test.tsNew helper
isTraceId(value: string): boolean— non-throwing check extracted fromvalidateTraceIdcore logic. Used bylog listfor positional disambiguation.Files changed (15)
src/lib/trace-id.tsisTraceId()src/commands/log/list.tssrc/commands/trace/list.tssrc/commands/span/list.tssrc/commands/trace/logs.tssrc/commands/org/list.tssrc/commands/trial/list.tssrc/commands/project/list.tssrc/lib/org-list.tstest/files