Indexer: add down migration for timecurve_unredeemed_launched_token (151-1) #152

Closed
opened 2026-05-05 05:45:36 +00:00 by PlasticDigits · 7 comments
PlasticDigits commented 2026-05-05 05:45:36 +00:00 (Migrated from gitlab.com)

Problem

The migration 20260504180000_timecurve_unredeemed_launched_token ships *.up.sql only — there is no paired *.down.sql. Every other migration in indexer/migrations/ follows the paired pattern.

Impact: Operators cannot roll back this schema step via the SQLx migration runner. A forced post-deploy revert requires manual DROP TABLE plus manual reconciliation of _sqlx_migrations, which blocks clean re-application of the same version and breaks automated rollback playbooks ahead of mainnet/TGE-style deploys.

Split from GitLab #151 (Finding 1 — Medium). Feature background: unredeemed launched-token sweep observability (GitLab #128).

Area Location
Migration (up) indexer/migrations/20260504180000_timecurve_unredeemed_launched_token.up.sql
Down (missing) Add indexer/migrations/20260504180000_timecurve_unredeemed_launched_token.down.sql (new; pair with .up.sql)
Indexer decoder (context) indexer/src/decoder.rs — unredeemed launched-token events
Indexer invariant docs/testing/invariants-and-business-logic.md — anchor INV-INDEXER-128 / unredeemed sweep
Guardrails skill .cursor/skills/yieldomega-guardrails/SKILL.md
Contracts No Solidity change; tables mirror onchain events for UnredeemedLaunchedTokenRecipientSet / sweep (see decoder + #128)

Contracts / frontend: No code change required for closing this ticket — only the indexer migration pair.

Acceptance criteria

  1. 20260504180000_timecurve_unredeemed_launched_token.down.sql exists and reverses the .up migration: drop indexes (if not dropped with CASCADE) then DROP TABLE IF EXISTS for both idx_timecurve_unredeemed_launched_token_recipient_set and idx_timecurve_unredeemed_launched_token_swept, in an order safe for FK-free standalone tables (match project style for other .down.sql files).
  2. Down is idempotent enough for dev: DROP TABLE IF EXISTS / DROP INDEX IF EXISTS as used elsewhere in this repo’s migrations.
  3. Documented or verified: sqlx migrate revert (or project-standard migrate command) can apply down then up on a throwaway Postgres without error.
  4. If any doc mentions “this migration has no down”, update that note.

Verification checklist

  • ls indexer/migrations/ | grep 20260504180000 shows both .up.sql and .down.sql.
  • Compare .down.sql objects to .up.sql: every CREATE TABLE / CREATE INDEX has a corresponding drop (naming matches).
  • On a clean test DB: sqlx database create (if needed) → sqlx migrate run → confirm tables exist → sqlx migrate revert (one step) → tables gone → sqlx migrate run → tables restored.
  • _sqlx_migrations row for 20260504180000 disappears after revert and returns after re-run (no manual version hacks).
  • CI / cargo test for indexer still passes if integration tests touch migrations (indexer/tests/).
  • Cross-read INV-INDEXER-128 in invariants-and-business-logic.md: no doc claim that migrations are intentionally one-way for this version; update if needed.
## Problem The migration `20260504180000_timecurve_unredeemed_launched_token` ships **`*.up.sql` only** — there is no paired **`*.down.sql`**. Every other migration in `indexer/migrations/` follows the paired pattern. **Impact:** Operators cannot roll back this schema step via the SQLx migration runner. A forced post-deploy revert requires manual `DROP TABLE` plus manual reconciliation of `_sqlx_migrations`, which blocks clean re-application of the same version and breaks automated rollback playbooks ahead of mainnet/TGE-style deploys. Split from [GitLab #151](https://gitlab.com/PlasticDigits/yieldomega/-/issues/151) (Finding 1 — Medium). Feature background: unredeemed launched-token sweep observability ([GitLab #128](https://gitlab.com/PlasticDigits/yieldomega/-/issues/128)). ## Related code & docs | Area | Location | |------|----------| | **Migration (up)** | [`indexer/migrations/20260504180000_timecurve_unredeemed_launched_token.up.sql`](https://gitlab.com/PlasticDigits/yieldomega/-/blob/main/indexer/migrations/20260504180000_timecurve_unredeemed_launched_token.up.sql) | | **Down (missing)** | Add `indexer/migrations/20260504180000_timecurve_unredeemed_launched_token.down.sql` (new; pair with [`.up.sql`](https://gitlab.com/PlasticDigits/yieldomega/-/blob/main/indexer/migrations/20260504180000_timecurve_unredeemed_launched_token.up.sql)) | | **Indexer decoder (context)** | [`indexer/src/decoder.rs`](https://gitlab.com/PlasticDigits/yieldomega/-/blob/main/indexer/src/decoder.rs) — unredeemed launched-token events | | **Indexer invariant** | [`docs/testing/invariants-and-business-logic.md`](https://gitlab.com/PlasticDigits/yieldomega/-/blob/main/docs/testing/invariants-and-business-logic.md) — anchor `INV-INDEXER-128` / unredeemed sweep | | **Guardrails skill** | [`.cursor/skills/yieldomega-guardrails/SKILL.md`](https://gitlab.com/PlasticDigits/yieldomega/-/blob/main/.cursor/skills/yieldomega-guardrails/SKILL.md) | | **Contracts** | No Solidity change; tables mirror onchain events for `UnredeemedLaunchedTokenRecipientSet` / sweep (see decoder + #128) | **Contracts / frontend:** No code change required for closing this ticket — only the indexer migration pair. ## Acceptance criteria 1. **`20260504180000_timecurve_unredeemed_launched_token.down.sql` exists** and reverses the `.up` migration: drop indexes (if not dropped with `CASCADE`) then `DROP TABLE IF EXISTS` for both `idx_timecurve_unredeemed_launched_token_recipient_set` and `idx_timecurve_unredeemed_launched_token_swept`, in an order safe for FK-free standalone tables (match project style for other `.down.sql` files). 2. **Down is idempotent enough for dev:** `DROP TABLE IF EXISTS` / `DROP INDEX IF EXISTS` as used elsewhere in this repo’s migrations. 3. **Documented or verified:** `sqlx migrate revert` (or project-standard migrate command) can apply **down** then **up** on a throwaway Postgres without error. 4. If any doc mentions “this migration has no down”, update that note. ## Verification checklist - [ ] `ls indexer/migrations/ | grep 20260504180000` shows **both** `.up.sql` and `.down.sql`. - [ ] Compare `.down.sql` objects to `.up.sql`: every `CREATE TABLE` / `CREATE INDEX` has a corresponding drop (naming matches). - [ ] On a clean test DB: `sqlx database create` (if needed) → `sqlx migrate run` → confirm tables exist → `sqlx migrate revert` (one step) → tables **gone** → `sqlx migrate run` → tables **restored**. - [ ] `_sqlx_migrations` row for `20260504180000` disappears after revert and returns after re-run (no manual version hacks). - [ ] CI / `cargo test` for indexer still passes if integration tests touch migrations ([`indexer/tests/`](https://gitlab.com/PlasticDigits/yieldomega/-/tree/main/indexer/tests)). - [ ] Cross-read **INV-INDEXER-128** in [`invariants-and-business-logic.md`](https://gitlab.com/PlasticDigits/yieldomega/-/blob/main/docs/testing/invariants-and-business-logic.md): no doc claim that migrations are intentionally one-way for this version; update if needed.
PlasticDigits commented 2026-05-05 05:45:39 +00:00 (Migrated from gitlab.com)

marked this issue as related to #151

marked this issue as related to #151
PlasticDigits commented 2026-05-05 05:46:12 +00:00 (Migrated from gitlab.com)

mentioned in issue #151

mentioned in issue #151
PlasticDigits commented 2026-05-05 05:47:55 +00:00 (Migrated from gitlab.com)

marked this issue as related to #128

marked this issue as related to #128
PlasticDigits commented 2026-05-05 06:36:54 +00:00 (Migrated from gitlab.com)

mentioned in commit 435a446d72

mentioned in commit 435a446d72af8ebcdb7abc4a279d2d6b0837c8ad
PlasticDigits commented 2026-05-05 06:38:06 +00:00 (Migrated from gitlab.com)

Implemented in main (commit on main after push).

What changed

  • Added indexer/migrations/20260504180000_timecurve_unredeemed_launched_token.down.sql: DROP INDEX IF EXISTS on both _block indexes, then DROP TABLE IF EXISTS for idx_timecurve_unredeemed_launched_token_swept and idx_timecurve_unredeemed_launched_token_recipient_set (reverse order of .up.sql dependencies).
  • Documented INV-INDEXER-128 SQLx paired migration / sqlx migrate revert path (GitLab #152); indexer README § SQLx migrations; cross-links in guardrails, skills/README.md, play-timecurve-doubloon.

Verification performed

  • cargo test + cargo clippy --all-targets -- -D warnings in indexer/ (green).
  • Disposable Postgres: full sqlx migrate run → revert stack through 20260504180000 → both idx_timecurve_unredeemed_* tables absent, _sqlx_migrations row removed → sqlx migrate run → tables and version row restored.

Checklist for @brouie

  • ls indexer/migrations/ | grep 20260504180000 shows .up.sql and .down.sql.
  • On a throwaway DB: sqlx migrate run (full chain) → \dt idx_timecurve_unredeemed* shows 2 tables → revert until 20260504180000 is undone → 0 such tables → sqlx migrate run → tables back.
  • SELECT * FROM _sqlx_migrations WHERE version = 20260504180000 absent after that revert, present after re-run.
  • CI / local cd indexer && cargo test still green.

Leaving issue open for your sign-off.

Implemented in **main** (commit on `main` after push). ### What changed - Added **`indexer/migrations/20260504180000_timecurve_unredeemed_launched_token.down.sql`**: `DROP INDEX IF EXISTS` on both `_block` indexes, then `DROP TABLE IF EXISTS` for **`idx_timecurve_unredeemed_launched_token_swept`** and **`idx_timecurve_unredeemed_launched_token_recipient_set`** (reverse order of `.up.sql` dependencies). - Documented **`INV-INDEXER-128`** SQLx paired migration / **`sqlx migrate revert`** path ([GitLab #152](https://gitlab.com/PlasticDigits/yieldomega/-/issues/152)); **indexer README** § SQLx migrations; cross-links in **guardrails**, **`skills/README.md`**, **`play-timecurve-doubloon`**. ### Verification performed - `cargo test` + `cargo clippy --all-targets -- -D warnings` in **`indexer/`** (green). - Disposable Postgres: full **`sqlx migrate run`** → revert stack through **`20260504180000`** → both **`idx_timecurve_unredeemed_*`** tables absent, **`_sqlx_migrations`** row removed → **`sqlx migrate run`** → tables and version row restored. ### Checklist for @brouie - [ ] `ls indexer/migrations/ | grep 20260504180000` shows **`.up.sql`** and **`.down.sql`**. - [ ] On a throwaway DB: **`sqlx migrate run`** (full chain) → `\dt idx_timecurve_unredeemed*` shows **2** tables → revert until **`20260504180000`** is undone → **0** such tables → **`sqlx migrate run`** → tables back. - [ ] **`SELECT * FROM _sqlx_migrations WHERE version = 20260504180000`** absent after that revert, present after re-run. - [ ] CI / local **`cd indexer && cargo test`** still green. Leaving issue **open** for your sign-off.
Brouie commented 2026-05-05 07:02:10 +00:00 (Migrated from gitlab.com)

@PlasticDigits — verification PASS at HEAD 435a446. walked your checklist:

  • ls indexer/migrations/ | grep 20260504180000: both .up.sql and .down.sql present.
  • _sqlx_migrations row for version 20260504180000 ("timecurve unredeemed launched token") shows success = t — clean apply on the running stack from the #150 fresh DB rebuild earlier today, no PK collision noise.
  • INV-INDEXER-128 anchor + indexer README §SQLx migrations cross-link reads cleanly.

skipped the disposable-DB sqlx migrate run → revert → re-run cycle (your dev-side verification covered that path against a throwaway DB). source pair is symmetric with the rest of the migration set, sqlx applies cleanly on the live stack here.

ready for close on your end.

@PlasticDigits — verification PASS at HEAD `435a446`. walked your checklist: - `ls indexer/migrations/ | grep 20260504180000`: both `.up.sql` and `.down.sql` present. - `_sqlx_migrations` row for version `20260504180000` ("timecurve unredeemed launched token") shows `success = t` — clean apply on the running stack from the #150 fresh DB rebuild earlier today, no PK collision noise. - INV-INDEXER-128 anchor + indexer README §SQLx migrations cross-link reads cleanly. skipped the disposable-DB `sqlx migrate run → revert → re-run` cycle (your dev-side verification covered that path against a throwaway DB). source pair is symmetric with the rest of the migration set, sqlx applies cleanly on the live stack here. ready for close on your end.
PlasticDigits (Migrated from gitlab.com) closed this issue 2026-05-05 07:18:14 +00:00
PlasticDigits commented 2026-05-13 15:13:33 +00:00 (Migrated from gitlab.com)

mentioned in commit 740b22e53c

mentioned in commit 740b22e53cd4282f22e2a987c51f82577e6a4282
Sign in to join this conversation.
No milestone
No project
No assignees
1 participant
Notifications
Due date
The due date is invalid or out of range. Please use the format "yyyy-mm-dd".

No due date set.

Dependencies

No dependencies set

Reference
code/yieldomega#152
No description provided.