feat(alert): add alert CRUD commands#579
Merged
Merged
Conversation
Adds two new list commands under `sentry alert`: - `sentry alert issues list` — list issue alert rules for one or more projects, with full multi-target resolution (DSN auto-detect, org-all, project-search, explicit org/project), compound cursor pagination, Phase 1 + Phase 2 budget redistribution, and graceful partial failure handling - `sentry alert metrics list` — list metric alert rules for an org Both commands support --json, --limit, --web, and -c next/prev pagination.
…ed lib Moves duplicated code from issue/list.ts and alert/issues/list.ts into shared modules so both commands use the same implementation: - lib/db/pagination.ts: exports CURSOR_SEP, encodeCompoundCursor, decodeCompoundCursor, buildMultiTargetContextKey - lib/resolve-target.ts: exports resolveTargetsFromParsedArg — handles all four target modes (auto-detect, explicit, org-all, project-search) with options for enrichProjectIds and checkIssueShortId (issue-list-specific) issue/list.ts drops ~260 lines of local duplicates; alert/issues/list.ts never needs to define them in the first place.
Contributor
Semver Impact of This PR🟡 Minor (new features) 📋 Changelog PreviewThis is how your changes will appear in the changelog. New Features ✨Dashboard
Init
Other
Bug Fixes 🐛Dashboard
Event
Other
Documentation 📚
Internal Changes 🔧Coverage
Event
Other
Other
🤖 This preview updates automatically when you update the PR. |
Contributor
|
Contributor
Codecov Results 📊✅ Patch coverage is 84.52%. Project has 4551 uncovered lines. Files with missing lines (22)
Coverage diff@@ Coverage Diff @@
## main #PR +/-##
==========================================
+ Coverage 81.85% 81.99% +0.14%
==========================================
Files 341 361 +20
Lines 24359 25275 +916
Branches 15915 16595 +680
==========================================
+ Hits 19939 20724 +785
- Misses 4420 4551 +131
- Partials 1663 1745 +82Generated by Codecov Action |
…List Both alert/issues/list and alert/metrics/list were implementing their own 4-mode target dispatch and compound cursor machinery from scratch, bypassing the shared dispatchOrgScopedList infrastructure every other list command uses. Replace with the standard pattern: - dispatchOrgScopedList with ListCommandMeta + 4 mode handler overrides - Simple parallel fetch-all for auto-detect/explicit/project-search modes (no compound cursor — alert rule lists are small datasets) - Single-cursor pagination for org-all mode (metrics: listMetricAlertsPaginated with cursor; issues: resolveTargetsFromParsedArg for project list + fetch all) Removes ~320 lines of custom dispatch and compound cursor logic. Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
…ucture - Use jsonTransformListResult (shared) instead of custom JSON transforms - Separate raw rules into items (for JSON) and displayRows (for human output) - Add --query/-q flag for client-side name filtering on both alert commands - Restore api-client.ts alerts export to original shape Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
…ssue list Full structural alignment with sentry issue list: - FetchResult success/failure wrapping per target - fetchWithBudget with two-phase surplus redistribution - Compound cursor pagination (encodeCompoundCursor/decodeCompoundCursor) - buildProjectAliasMap with buildOrgAwareAliases + setProjectAliases - trimWithProjectGuarantee for per-project representation - One handleResolvedTargets for all 4 modes (alert issues have no org-level API) - allowCursorInModes for all modes including org-all - parseCursorFlag explicitly in cursor flag definition - logger.warn for partial failures - IssueAlertListResult with title/footerMode/moreHint/footer - jsonTransformListResult (shared JSON transform) Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
…issue list Full structural alignment with sentry issue list and alert issues list: - FetchResult success/failure wrapping per org with withAuthGuard - fetchWithBudget with two-phase surplus redistribution (per-org) - Compound cursor pagination across multiple orgs (auto-detect/explicit/project-search) - trimWithOrgGuarantee for per-org representation - handleResolvedOrgs for multi-org modes; handleOrgAllMetricAlerts for single-org cursor - allowCursorInModes for auto-detect/explicit/project-search - parseCursorFlag explicitly in cursor flag definition - logger.warn for partial org failures - MetricAlertListResult with title/footerMode/moreHint/footer - jsonTransformListResult (shared JSON transform) - buildMultiOrgContextKey isolates cursors per unique org set + query Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
…list Removes the separate handleOrgAllMetricAlerts handler and routes all 4 modes (including org-all) through handleResolvedOrgs. org-all resolves all projects in the specified org, deduplicates to unique orgs (just the one), then uses fetchWithBudget with compound cursor — same path as auto-detect/explicit/project-search. This makes the structure identical to alert issues list and supports multi-org results from DSN detection consistently across all modes. Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Extract FetchResult<T>, trimWithGroupGuarantee<T>, buildProjectAliasMap<T>, and buildMultiOrgContextKey into lib/ so all three list commands (issue, alert issues, alert metrics) share the same implementations. Each command retains a thin domain-specific wrapper where needed. Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
For metric alerts (org-scoped), explicit and org-all modes already provide the org slug in the parsed arg. Routing them through resolveTargetsFromParsedArg caused an unnecessary listProjects API call just to re-derive the org slug. Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Made-with: Cursor # Conflicts: # docs/public/.well-known/skills/index.json # plugins/sentry-cli/skills/sentry-cli/SKILL.md # src/commands/issue/list.ts # src/lib/sentry-urls.ts
Correct hasMore computation in alert issue/metric list flows so exact-limit pages without a next cursor don't report false positives, and filtered-empty pages still retain next-page availability. Add regression tests for both commands and clean up a leftover issue list merge marker/imports that blocked command loading. Made-with: Cursor
Add alert rule detail fetch endpoints and new `alert issues view` / `alert metrics view` commands with ID-or-name resolution across resolved targets, plus docs/skill reference updates for the new subcommands. Made-with: Cursor
Switch alert route wiring to the telemetry-aware route-map wrapper and add the missing alert command fragment so generated docs validation passes in CI. Made-with: Cursor
- View: fail fast on malformed org/project, suppress only 404 in numeric lookup, name match exact then suggestions (no auto fuzzy pick) - List: preserve hasMore from phase-1 when phase-2 is skipped; drop dead footerMode; remove unused isMultiOrg - Add view tests and phase1HasMore list regression test Made-with: Cursor
- API: delete/put helpers, apiRequestToRegionNoContent for empty responses - Shared rule-resolve modules for view/delete/edit (parse + resolve) - issues|metrics delete: buildDeleteCommand, type org/project/id to confirm - issues|metrics edit: --name and --status (active|disabled) - Fix project-structure doc: dedupe subcommand label for nested routes (alert) - Regenerate SKILL + references/alert only; other skill refs left at HEAD to avoid unrelated example-date churn from generate:skill Made-with: Cursor
- Add isNotFoundApiError in lib/api/error-guards (re-exported from api-client) - DRY fetchIssueAlertRuleJson / fetchMetricAlertRuleJson for get*Rule and get*Document - Re-exported from api-client, used by both rule-resolve modules Made-with: Cursor
Implement full alert CRUD coverage for issue and metric rules by adding create commands, broadening merge-based edit support, and updating API helpers, tests, and generated command docs. Made-with: Cursor
Tighten alert create/edit typing to satisfy strict TypeScript and lint checks, and regenerate related skill reference docs so CI passes consistently. Made-with: Cursor
Compute month-boundary period examples in UTC so generated skill/docs output does not drift between local environments and CI. Made-with: Cursor
Resolve conflicts: - contributing.md: keep both main's new commands (local, replay, archive, import, revisions, restore) and branch's alert entry - api-client.ts: keep both discover exports (main) and error-guards + apiRequestToRegionNoContent exports (branch) - infrastructure.ts: keep main's throwRawApiError refactor and branch's apiRequestToRegionNoContent (updated to use throwRawApiError) - resolve-target.ts: keep both branch's resolveTargetsFromParsedArg and main's resolveOrgOptionalProjectTarget
The '0:0:0' sentinel causes an infinite pagination loop when a target persistently fails — it's never treated as exhausted by decodeCompoundCursor, so the target keeps retrying with the same sentinel on every -c next invocation. Using null marks the target as exhausted after a first-page failure, which is the safer default.
…runcation - Switch metrics create from resolveTargetsFromParsedArg (requires projects) to resolveOrgOptionalProjectFromArg (org-only), matching view/edit/delete - Add log.warn when listAllMetricRulesForOrg and listAllIssueRulesForTarget hit MAX_PAGINATION_PAGES, so truncated results are visible in debug output - Update metrics create test to mock the new resolver
…rule parsing - Move --web check before resolveIssueAlertRule/resolveMetricAlertRule in view commands to avoid unnecessary API calls when opening browser - Extend issue list --web to handle org-all mode (open org alerts page) - Add comments explaining --web fallthrough for auto-detect/project-search - Reject 2+ slashes in parseMetricRuleArg with clear error (metric alerts are org-scoped, not org/project/rule) - Make buildIssueAlertsUrl accept optional projectSlug - Add test for 2+ slash rejection
# Conflicts: # docs/src/content/docs/contributing.md
Contributor
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.
Reviewed by Cursor Bugbot for commit b57c161. Configure here.
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.

Closes #578
Adds full
sentry alertCRUD coverage for both issue alerts (project-scoped) and metric alerts (org-scoped), with pagination correctness fixes, resolver/API helpers, and generated docs/skill references.What this PR includes
Alert list commands
sentry alert issues listfor project-scoped issue alert rules.sentry alert metrics listfor org-scoped metric alert rules.Both support target resolution, pagination,
--json,--web, and query filtering.Alert view commands
sentry alert issues view <org/project/rule-id-or-name>sentry alert metrics view <org/rule-id-or-name>Both support ID-or-name lookup and
--web.Alert create commands
sentry alert issues create <target>accepts an explicit target, auto-detected single project, or bare project search that resolves to exactly one project.sentry alert metrics create <org>creates org-scoped metric alert rules with optional project filters.Both support
--dry-runpreview.Alert edit commands
sentry alert issues edit <org/project/rule-id-or-name>supports merge-based updates for name/status and advanced issue-rule fields.sentry alert metrics edit <org/rule-id-or-name>supports merge-based updates for query/aggregate/dataset/window/triggers/projects/environment/owner.Both edit flows resolve by ID-or-name, fetch the current rule, merge only provided flags, validate the merged payload, and PUT the full document.
Alert delete commands
sentry alert issues delete <org/project/rule-id-or-name>sentry alert metrics delete <org/rule-id-or-name>Both use interactive confirmation by default, with
--yes/--forcebypass and--dry-runpreview.Review follow-ups
1/"1"as disabled; omitted/unknown/zero values render as active.<target>metadata.Test plan