Skip to content

docs: the upgrade path is reachable for the installations it targets - #873

Merged
blaipr merged 1 commit into
mainfrom
docs/the-upgrade-path-is-reachable-for-the-installs-it-targets
Aug 23, 2026
Merged

docs: the upgrade path is reachable for the installations it targets#873
blaipr merged 1 commit into
mainfrom
docs/the-upgrade-path-is-reachable-for-the-installs-it-targets

Conversation

@blaipr

@blaipr blaipr commented Aug 23, 2026

Copy link
Copy Markdown
Member

#867 recorded the two shipped migrations as declaring versions the application can never
reach, and left resolving that as a deployment decision. The first half is true and the
second was the wrong conclusion, so this corrects the record before somebody acts on it.

AppInfoInterface::APP_BUILD has not moved since the rewrite was imported, so the code
reports 400.21031301 while the migrations declare 400.24210101 and 400.24240101.
But checkUpgradeNeeded() compares the stored version against that, and
getTargetUpgradeHandlers() then selects every handler above the stored one. An
installation arriving from 3.2 stores something like 320.19012701, which is behind
both — so it triggers the upgrade and runs both migrations. Measured against the real
Version class rather than reasoned about.

What cannot reach them is an installation this rewrite performed, which is stamped with
the version the code reports. Neither migration applies to one: dbstructure.sql already
ships CustomFieldData with the composite primary key and no id column, and text written
after the escaping change is stored as typed.

Bumping APP_BUILD would make it worse. 40024210101.sql would run against schemas that
already have it applied, dropping a column that is not there; and 40024240101.sql
decodes stored text, saying in its own header that it is not idempotent and that no decode
of stored text could be — so on an installation whose text is already correct it turns a
name typed as Q&A into something else. The population that would benefit is the narrow
one installed by this rewrite before the escaping change; the population that would be
damaged is every installation since.

The two stay on the list, and the list keeps doing the job it was added for: a third
migration cannot join them unnoticed. No behaviour changes here — only the reasoning
recorded on the constant, which is what the next person will read before touching
APP_BUILD.

#867 recorded the two shipped migrations as declaring versions the application can never
reach, and left resolving that as a deployment decision. The first half is true and the
second was the wrong conclusion, so this corrects the record before somebody acts on it.

`AppInfoInterface::APP_BUILD` has not moved since the rewrite was imported, so the code
reports `400.21031301` while the migrations declare `400.24210101` and `400.24240101`.
But `checkUpgradeNeeded()` compares the *stored* version against that, and
`getTargetUpgradeHandlers()` then selects every handler above the stored one. An
installation arriving from 3.2 stores something like `320.19012701`, which is behind
both — so it triggers the upgrade and runs both migrations. Measured against the real
Version class rather than reasoned about.

What cannot reach them is an installation this rewrite performed, which is stamped with
the version the code reports. Neither migration applies to one: `dbstructure.sql` already
ships CustomFieldData with the composite primary key and no `id` column, and text written
after the escaping change is stored as typed.

Bumping APP_BUILD would make it worse. `40024210101.sql` would run against schemas that
already have it applied, dropping a column that is not there; and `40024240101.sql`
decodes stored text, saying in its own header that it is not idempotent and that no decode
of stored text could be — so on an installation whose text is already correct it turns a
name typed as `Q&A` into something else. The population that would benefit is the narrow
one installed by this rewrite before the escaping change; the population that would be
damaged is every installation since.

The two stay on the list, and the list keeps doing the job it was added for: a third
migration cannot join them unnoticed. No behaviour changes here — only the reasoning
recorded on the constant, which is what the next person will read before touching
APP_BUILD.
@blaipr
blaipr merged commit a5d18c4 into main Aug 23, 2026
8 checks passed
@blaipr
blaipr deleted the docs/the-upgrade-path-is-reachable-for-the-installs-it-targets branch August 23, 2026 23:58
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.

1 participant