Skip to content

ref(seer): Genericize night shift result table#114790

Merged
trevor-e merged 9 commits intomasterfrom
telkins/night-shift-feedback-summary
May 5, 2026
Merged

ref(seer): Genericize night shift result table#114790
trevor-e merged 9 commits intomasterfrom
telkins/night-shift-feedback-summary

Conversation

@trevor-e
Copy link
Copy Markdown
Member

@trevor-e trevor-e commented May 4, 2026

Repurposes the existing night-shift result table so it can host more than just agentic triage. No behavior change.

  • Renames SeerNightShiftRunIssueSeerNightShiftRunResult (state-only via SeparateDatabaseAndState + RenameModel; underlying Postgres table keeps the historical seer_nightshiftrunissue name).
  • Adds a kind discriminator (with a NightShiftRunResultKind enum) and a per-row extras JSON.
  • Migrates action, error_message, and triage_strategy data into JSON (extras) and marks the legacy columns SafeRemoveField(MOVE_TO_PENDING). Physical drop ships in a follow-up.
  • Serializer keeps issues, triageStrategy, and errorMessage aliases for the existing frontend; new results key is the canonical shape going forward.

Renames SeerNightShiftRunIssue → SeerNightShiftRunResult (state-only;
db_table preserved) and adds a `kind` discriminator + per-row `extras`
JSON to support nightly per-org work beyond agentic triage. Triage's
existing `action` column is moved into extras["action"] via a
deploy-time backfill. Legacy columns (action, triage_strategy,
error_message) are marked SafeRemoveField MOVE_TO_PENDING; their
physical drop ships in a follow-up.
@github-actions github-actions Bot added the Scope: Backend Automatically applied to PRs that change backend components label May 4, 2026
@github-actions
Copy link
Copy Markdown
Contributor

github-actions Bot commented May 4, 2026

This PR has a migration; here is the generated SQL for src/sentry/seer/migrations/0009_genericize_night_shift_results.py

for 0009_genericize_night_shift_results in seer

--
-- Custom state/database change combination
--
-- (no-op)
--
-- Alter field run on seernightshiftrunresult
--
-- (no-op)
--
-- Add field kind to seernightshiftrunresult
--
ALTER TABLE "seer_nightshiftrunissue" ADD COLUMN "kind" varchar(256) DEFAULT 'agentic_triage' NOT NULL;
--
-- Add field extras to seernightshiftrunresult
--
ALTER TABLE "seer_nightshiftrunissue" ADD COLUMN "extras" jsonb DEFAULT '{}'::jsonb NOT NULL;
--
-- Alter field group on seernightshiftrunresult
--
ALTER TABLE "seer_nightshiftrunissue" ALTER COLUMN "group_id" DROP NOT NULL;
--
-- Alter field action on seernightshiftrunresult
--
ALTER TABLE "seer_nightshiftrunissue" ALTER COLUMN "action" DROP NOT NULL;
--
-- Alter field triage_strategy on seernightshiftrun
--
ALTER TABLE "seer_nightshiftrun" ALTER COLUMN "triage_strategy" DROP NOT NULL;
--
-- Create index seer_nights_run_id_d5406e_idx on field(s) run, kind of model seernightshiftrunresult
--
CREATE INDEX CONCURRENTLY "seer_nights_run_id_d5406e_idx" ON "seer_nightshiftrunissue" ("run_id", "kind");
--
-- Raw Python operation
--
-- THIS OPERATION CANNOT BE WRITTEN AS SQL
--
-- Moved seernightshiftrunresult.action field to pending deletion state
--
-- (no-op)
--
-- Moved seernightshiftrun.triage_strategy field to pending deletion state
--
-- (no-op)
--
-- Raw Python operation
--
-- THIS OPERATION CANNOT BE WRITTEN AS SQL
--
-- Moved seernightshiftrun.error_message field to pending deletion state
--
-- (no-op)

Comment thread src/sentry/seer/migrations/0009_genericize_night_shift_results.py
Without this, runs that had an error_message recorded against the
legacy column would return errorMessage: null from the API after the
column is removed from model state via SafeRemoveField(MOVE_TO_PENDING).
Adds a second RunPython op (run before the error_message
SafeRemoveField) and extends the migration test to cover both the
existing action backfill and the new error_message backfill.
Comment thread src/sentry/seer/migrations/0009_genericize_night_shift_results.py Outdated
trevor-e added 2 commits May 4, 2026 18:47
Mypy flagged the missing annotation on the migration test's
setup_before_migration override.
Dropping the db_default in the same migration that adds the NOT NULL
column breaks rolling deploys: old replicas still INSERTing without
kind would fail with a NOT NULL violation between when the migration
applies and when those replicas are replaced. Defer the db_default
drop to the follow-up PR2 (the same one that runs SafeRemoveField
DELETE for the legacy columns), which already requires PR1 to be
fully deployed.
Copy link
Copy Markdown
Contributor

@cursor cursor Bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Cursor Bugbot has reviewed your changes and found 1 potential issue.

Fix All in Cursor

❌ Bugbot Autofix is OFF. To automatically fix reported issues with cloud agents, enable autofix in the Cursor dashboard.

Reviewed by Cursor Bugbot for commit adea73a. Configure here.

Comment thread src/sentry/api/serializers/models/seer_night_shift_run.py Outdated
trevor-e added 4 commits May 4, 2026 19:23
Pre-migration the triage_strategy column was a required CharField,
always set to "agentic_triage" — including for runs that produced no
result rows (failed quota check, no eligible projects, dry runs). My
earlier serializer change derived the legacy alias from result-row
presence, silently flipping triageStrategy to null for those runs.
Hardcode it back to "agentic_triage" so the API surface matches the
old behavior. Multi-kind serializer logic ships with the feature PR.
The migration has 12 operations including a CONCURRENTLY index, so
TestMigrations.setUp's roll-back/forward cycle was hovering at or
over CI's 120s fail-slow budget per test. The migration itself is
already exercised by:

- Direct application against dev DB with real data (47 result rows
  backfilled correctly).
- The full night-shift test suite (49 tests) running against the
  post-migration schema with --create-db.
- The two RunPython callbacks are simple idempotent loops; the cost
  of an integration test has stopped paying for itself.
Drive-by edit from the original PR1 commit. No reason for it.
group=c.group,
action=c.action,
seer_run_id=str(seer_run_id),
extras={"action": str(c.action)},
Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Will have to update our dashboard.

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

ack, will do

@trevor-e trevor-e marked this pull request as ready for review May 5, 2026 01:50
@trevor-e trevor-e requested review from a team as code owners May 5, 2026 01:50
Copy link
Copy Markdown
Contributor

@chromy chromy left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

lgtm

@trevor-e trevor-e merged commit edb631e into master May 5, 2026
82 of 83 checks passed
@trevor-e trevor-e deleted the telkins/night-shift-feedback-summary branch May 5, 2026 14:12
cleptric pushed a commit that referenced this pull request May 5, 2026
Repurposes the existing night-shift result table so it can host more
than just agentic triage. No behavior change.

- Renames `SeerNightShiftRunIssue` → `SeerNightShiftRunResult`
(state-only via `SeparateDatabaseAndState` + `RenameModel`; underlying
Postgres table keeps the historical `seer_nightshiftrunissue` name).
- Adds a `kind` discriminator (with a `NightShiftRunResultKind` enum)
and a per-row `extras` JSON.
- Migrates `action`, `error_message`, and `triage_strategy` data into
JSON (`extras`) and marks the legacy columns
`SafeRemoveField(MOVE_TO_PENDING)`. Physical drop ships in a follow-up.
- Serializer keeps `issues`, `triageStrategy`, and `errorMessage`
aliases for the existing frontend; new `results` key is the canonical
shape going forward.
trevor-e added a commit that referenced this pull request May 5, 2026
**Stacked on #114790** — review and land that one first, then wait for
full deploy before merging this.

Drops the legacy night-shift columns now that #114790 has fully deployed
and all live code has stopped reading/writing them.

- `SafeRemoveField(DELETE)` for `seer_nightshiftrunissue.action`,
`seer_nightshiftrun.triage_strategy`, and
`seer_nightshiftrun.error_message` — physically drops the columns from
Postgres.
- Drops the `db_default` on `kind` (kept in #114790 to keep INSERTs from
old replicas valid mid-rolling-deploy). All live code now specifies
`kind` explicitly, so the safety net is no longer needed.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

Scope: Backend Automatically applied to PRs that change backend components

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants