Skip to content

chore(release): merge release/4.6.1 to main#1981

Open
amandagonsalves wants to merge 3 commits into
mainfrom
chore/merge-release-4.6.1-to-main
Open

chore(release): merge release/4.6.1 to main#1981
amandagonsalves wants to merge 3 commits into
mainfrom
chore/merge-release-4.6.1-to-main

Conversation

@amandagonsalves

Copy link
Copy Markdown
Collaborator

Description

Merges release/4.6.1 into main for the 4.6.1 release.

Context

N/A

Testing

  • ./gradlew test

Documentation

N/A

Known limitations

N/A

Merges main into develop for the 4.6.0 release.
…r backfill to V31 (#1979)

### Description

`V29__sep31_customer_id_owner.sql` was edited in place after ANCHOR-1248
to add a backfill `INSERT`, on the assumption it had never shipped in a
tagged release. That held against the 4.5.0 tag, but not against every
deployed environment: at least one already had the original, bare V29
(table creation only) applied before 4.6.0 shipped, so its recorded
Flyway checksum no longer matched the file, and the app correctly
refused to start.

This reverts V29 to its original, already-released form (bare `CREATE
TABLE`), and moves the backfill `INSERT` (ANCHOR-1248) plus the
muxed-account decode repair (V30) into a new migration, V31. V31
delegates to V30's existing decode logic instead of duplicating it.

Reverting V29 only fixes environments that still have the original
(pre-4.6.0) checksum recorded. Any environment that already booted 4.6.0
successfully recorded the *with-backfill* checksum for V29, and would
now fail validation in the opposite direction once V29 is reverted.
Since neither history can be edited by hand (no DB access), this PR also
adds `FlywayChecksumCompatibilityCallback`, a Flyway `BEFORE_VALIDATE`
callback that normalizes the with-backfill checksum back to the original
one, in-app, before Flyway validates. It's a no-op for every other case
(fresh install, or a database that already has the original checksum),
so it's safe to leave in place regardless of which of the two known
histories a given environment has.

The callback is registered as a `@Bean` in `DataBeans`
(`component.share`), since that's the one config package every
Flyway-enabled server (`platform`, `sep`, `observer`, `event-processor`)
actually component-scans - each server's `@ComponentScan` is otherwise
scoped to its own controller/component packages and excludes
`platform.configurator`, so a plain `@Component` there would never reach
Spring Boot's `FlywayAutoConfiguration`.

The table-existence check that guards the normalization scopes its
metadata lookup to `connection.getSchema()` rather than searching every
schema. `data.schema` is configurable, and an unqualified lookup would
treat a fresh target schema as already-initialized if any other schema
in the same database happened to have a `flyway_schema_history` table -
the check would pass, but the subsequent unqualified `UPDATE` (which
resolves against the connection's actual current schema) would then fail
because that schema's table doesn't exist.

**Changes**
- `V29__sep31_customer_id_owner.sql`: reverted to its original content
(byte-identical to the pre-ANCHOR-1248 commit).
- `V31__backfill_sep31_customer_id_owner.java` (new): runs the same
backfill `INSERT` that used to live in V29, then delegates to
`V30__backfill_muxed_sep31_customer_id_owner`'s existing `migrate()` for
the muxed-account repair.
- `FlywayChecksumCompatibilityCallback.java` (new): Flyway callback that
rewrites V29's recorded checksum from the 4.6.0 with-backfill value back
to the original value, only when the with-backfill value is actually
present in the connection's current schema.
- `DataBeans.java`: registers the callback as a `@Bean` so every
Flyway-enabled server picks it up.

### Context

Production incident: the `event-processor` service failed to start after
the 4.6.0 release with `FlywayValidateException: Migration checksum
mismatch for migration version 29` - `Applied to database: 1190516276`
(the bare, pre-backfill V29) vs. `Resolved locally: 1803170936` (the
with-backfill V29 shipped in 4.6.0).

### Testing

- `./gradlew :core:test :platform:test` - BUILD SUCCESSFUL.
- Manual, against a live Postgres 16 instance:
1. Fresh install: ran the actual Flyway engine through the full V1-V31
chain on an empty database with seeded `sep31_transaction` history
(plain and muxed callers) - applies cleanly in order,
`sep31_customer_id_owner` ends up fully and correctly backfilled. The
new callback is a verified no-op here (`flyway_schema_history` doesn't
exist yet at `BEFORE_VALIDATE` time; the callback detects that and
returns early instead of erroring).
2. Already-broken environment (reported incident): simulated the exact
reported state (bare V29 applied, V30/V31 never run) and ran V31
directly - produces the identical, correct result.
3. The environment this fix is actually for - one that already booted
4.6.0 and recorded the with-backfill checksum for V29: seeded
`flyway_schema_history` with that exact checksum (1803170936) via a real
migrate run against the old with-backfill V29 file, then ran Flyway
again against the reverted V29 with the callback registered - validation
succeeds and the recorded checksum is rewritten to 1190516276. Confirmed
as a negative control that the same scenario without the callback throws
the checksum mismatch (in the reverse direction from the original
incident, as expected).
4. Cross-schema false-positive: with `public` already holding an
initialized `flyway_schema_history`, pointed a fresh, never-migrated
`fresh_target` schema (via `currentSchema=fresh_target`) at the same
database and confirmed it migrates cleanly - i.e. `public` having
history doesn't fool the check into skipping/misinterpreting
`fresh_target`'s own state.
  5. Re-ran in all scenarios to confirm idempotency.

### Documentation
N/A

### Known limitations

This normalizes exactly the two checksums known from this incident (the
original V29 and the 4.6.0 with-backfill V29). It does not attempt to
handle a third, unknown checksum for V29 - that would still fail
validation and require a manual `flyway repair`. Any environment
currently crash-looping on this checksum mismatch, in either direction,
can redeploy directly once this ships - no manual DB access needed.
## Description
This bumps the version to 4.6.1

## Context
Release

## Testing
./gradlew test

## Documentation
N/A

## Known limitations
N/A
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants