Skip to content

Commit 0d4f82d

Browse files
fix(cli): Silence set-commits repository errors in issue reporting (#2151)
## Summary 0.48.0 made `release set-commits --auto` read the repository from CI variables and match it by name. The failures that are left on 0.48/0.49 are org setup problems, and they are still captured as Sentry issues: - **`repository` field (CLI-17R):** `--auto` finds no repository, for example on a Vercel preview build or a Docker build without `.git` and without CI repository variables. Or the org has not added the matching repository in Sentry. This came to about 440 events on 0.48.0 and 0.49.0 over 30 days. - **`commit.repository` field (CLI-4G3, formerly CLI-2SK):** a `--commit` repository that the org doesn't have in Sentry, or an org with no repositories at all. This came to about 46 events on 0.49.0. The user gets an error that says how to fix it in each case. Most of these runs come through the bundler plugins with `shouldNotThrowOnFailure`, so builds keep going. ### Key Changes - `classifySilenced` treats `ValidationError`s with field `repository` or `commit.repository` as `user_validation`. Other `ValidationError`s and API errors from the same flow are still captured. - `cli.error.silenced` now records `validation_field` for silenced `ValidationError`s. That keeps the volume of each case measurable after it stops creating issues. <!-- junior-request-attribution:start --> via @betegon. <!-- junior-request-attribution:end --> <!-- junior-session-footer:start --> <!-- junior-conversation-id:agent%3A13af9393ba498bf4b925a816a4a5290f --> -- [View Session in Sentry](https://sentry.sentry.io/explore/conversations/agent%3A13af9393ba498bf4b925a816a4a5290f/?project=4510944073809921) <!-- junior-session-footer:end --> Co-authored-by: sentry-junior[bot] <264270552+sentry-junior[bot]@users.noreply.github.com> Co-authored-by: bete <28983162+betegon@users.noreply.github.com>
1 parent 6a68329 commit 0d4f82d

2 files changed

Lines changed: 54 additions & 0 deletions

File tree

‎packages/cli/src/lib/error-reporting.ts‎

Lines changed: 15 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -137,6 +137,18 @@ export function classifySilenced(error: unknown): SilenceReason | null {
137137
) {
138138
return "user_validation";
139139
}
140+
// A ValidationError with field "repository" or "commit.repository" means
141+
// `release set-commits` could not match a Sentry repository: the build has
142+
// no git remote or CI repository variables (Vercel preview, Docker without
143+
// .git), or the org has not added the repository (CLI-17R, CLI-4G3). The
144+
// org's setup has to change, and the user sees how to fix it. The
145+
// `cli.error.silenced` metric keeps the volume, split by `validation_field`.
146+
if (
147+
error instanceof ValidationError &&
148+
(error.field === "repository" || error.field === "commit.repository")
149+
) {
150+
return "user_validation";
151+
}
140152
// A ValidationError with field "input" means the --input file path the user
141153
// supplied does not exist on disk. Pure user-input noise, not a CLI bug —
142154
// the user sees a clear "File not found" message (CLI-1JY).
@@ -198,6 +210,9 @@ function recordSilencedError(error: unknown, reason: SilenceReason): void {
198210
if (error instanceof SeerError) {
199211
attributes.seer_reason = error.reason;
200212
}
213+
if (error instanceof ValidationError && error.field) {
214+
attributes.validation_field = error.field;
215+
}
201216

202217
// oxlint-disable-next-line sentry-cli/no-silent-catch -- grandfathered silent catch — see #1531; drain by adding log.debug()/log.warn() or re-throwing.
203218
try {

‎packages/cli/test/lib/error-reporting.test.ts‎

Lines changed: 39 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -366,6 +366,27 @@ describe("classifySilenced", () => {
366366
).toBe("user_input_error");
367367
});
368368

369+
test.each([
370+
[
371+
"repository",
372+
"Could not determine the repository: there is no 'origin' git remote and no CI repository variables.",
373+
],
374+
["repository", "No Sentry repository matching 'owner/repo' (from CI)."],
375+
[
376+
"commit.repository",
377+
"Sentry organization 'my-org' has no repository named 'owner/repo'.",
378+
],
379+
])(
380+
"silences set-commits ValidationError with field '%s' (CLI-17R, CLI-4G3)",
381+
(field, message) => {
382+
// The org's setup has to change (no repository in the build, or the
383+
// repository isn't added in Sentry); it is not a CLI bug.
384+
expect(classifySilenced(new ValidationError(message, field))).toBe(
385+
"user_validation",
386+
);
387+
},
388+
);
389+
369390
test("silences ResolutionError (user provided a value that wasn't found)", () => {
370391
expect(
371392
classifySilenced(
@@ -645,6 +666,24 @@ describe("reportCliError integration", () => {
645666
);
646667
});
647668

669+
test("silences set-commits repository ValidationError and records the field", () => {
670+
reportCliError(
671+
new ValidationError("No Sentry repository matching 'a/b'.", "repository"),
672+
);
673+
expect(captureSpy).not.toHaveBeenCalled();
674+
expect(metricSpy).toHaveBeenCalledWith(
675+
"cli.error.silenced",
676+
1,
677+
expect.objectContaining({
678+
attributes: expect.objectContaining({
679+
error_class: "ValidationError",
680+
reason: "user_validation",
681+
validation_field: "repository",
682+
}),
683+
}),
684+
);
685+
});
686+
648687
test("captures SeerError (marketing dashboard)", () => {
649688
reportCliError(new SeerError("not_enabled", "my-org"));
650689
expect(captureSpy).toHaveBeenCalled();

0 commit comments

Comments
 (0)