🐛 Make migration 0156 compatible with PostgreSQL 15

`SET STORAGE DEFAULT` needs PostgreSQL 16, but the official docker
images pin `postgres:15`, so migration 0156 failed on those
deployments. The migration now uses `SET STORAGE EXTENDED`, the
storage mode of the type of every column it touches (text, text[],
jsonb and bytea), which leaves the catalog in the same state on any
supported version.

The documented PostgreSQL floor goes back to >=15, the reason for
raising it was that syntax.

Verified on the test database: the 62 columns reset and no table
column keeps the legacy EXTERNAL storage.

The backend memory now records that migrations must stay within
PostgreSQL 15 syntax.

AI-assisted-by: minimax-m3.1-flash-free
This commit is contained in:
Andrey Antukh 2026-10-20 20:36:24 +00:00
parent 3bab9fa0aa
commit 021492a577
3 changed files with 72 additions and 68 deletions

View File

@ -41,6 +41,8 @@ Backend RPC command areas without focused memories include access tokens, binfil
Database migrations live in `backend/src/app/migrations/`; pure SQL migrations are under `backend/src/app/migrations/sql/`. SQL filenames conventionally start with a sequence and verb/table description, e.g. `0026-mod-profile-table-add-is-active-field`. Applied migrations are tracked in the `migrations` table.
Migrations must stay within PostgreSQL 15 syntax: the official docker images (`docker/images/docker-compose.yaml`) pin `postgres:15`, so anything newer breaks those deployments (`SET STORAGE DEFAULT` is PostgreSQL 16, for instance). The documented floor is >=15.
For interactive PostgreSQL access with correct dev defaults, use `scripts/psql`; to dump
the current DDL schema, use `scripts/db-schema` (see `mem:scripts/psql`).

View File

@ -12,118 +12,120 @@
-- already stored TOAST values keep their strategy until the row is
-- rewritten, new writes use the default.
--
-- NOTE: DEFAULT restores the storage mode of the column's data type
-- (EXTENDED for every column below: text, text[], jsonb and bytea). It
-- requires PostgreSQL 16 or newer, which is the minimum version the
-- project supports (see the database section of the technical guide).
-- RESET STORAGE is not valid syntax for a column.
-- NOTE: `SET STORAGE DEFAULT` would express the same thing (it restores
-- the storage mode of the column's data type), but it only exists since
-- PostgreSQL 16 and the project also runs on PostgreSQL 15. Here every
-- column below has a type whose default storage mode is EXTENDED
-- (text, text[], jsonb and bytea), so `SET STORAGE EXTENDED` reaches the
-- same catalog state on any supported version. RESET STORAGE is not
-- valid syntax for a column.
ALTER TABLE access_token
ALTER COLUMN name SET STORAGE DEFAULT,
ALTER COLUMN perms SET STORAGE DEFAULT,
ALTER COLUMN token SET STORAGE DEFAULT;
ALTER COLUMN name SET STORAGE EXTENDED,
ALTER COLUMN perms SET STORAGE EXTENDED,
ALTER COLUMN token SET STORAGE EXTENDED;
ALTER TABLE audit_log
ALTER COLUMN context SET STORAGE DEFAULT,
ALTER COLUMN name SET STORAGE DEFAULT,
ALTER COLUMN props SET STORAGE DEFAULT,
ALTER COLUMN source SET STORAGE DEFAULT,
ALTER COLUMN type SET STORAGE DEFAULT;
ALTER COLUMN context SET STORAGE EXTENDED,
ALTER COLUMN name SET STORAGE EXTENDED,
ALTER COLUMN props SET STORAGE EXTENDED,
ALTER COLUMN source SET STORAGE EXTENDED,
ALTER COLUMN type SET STORAGE EXTENDED;
ALTER TABLE comment
ALTER COLUMN content SET STORAGE DEFAULT;
ALTER COLUMN content SET STORAGE EXTENDED;
ALTER TABLE comment_thread
ALTER COLUMN page_name SET STORAGE DEFAULT,
ALTER COLUMN participants SET STORAGE DEFAULT;
ALTER COLUMN page_name SET STORAGE EXTENDED,
ALTER COLUMN participants SET STORAGE EXTENDED;
ALTER TABLE file
ALTER COLUMN data SET STORAGE DEFAULT,
ALTER COLUMN data_backend SET STORAGE DEFAULT,
ALTER COLUMN features SET STORAGE DEFAULT,
ALTER COLUMN name SET STORAGE DEFAULT;
ALTER COLUMN data SET STORAGE EXTENDED,
ALTER COLUMN data_backend SET STORAGE EXTENDED,
ALTER COLUMN features SET STORAGE EXTENDED,
ALTER COLUMN name SET STORAGE EXTENDED;
ALTER TABLE file_change
ALTER COLUMN changes SET STORAGE DEFAULT,
ALTER COLUMN data SET STORAGE DEFAULT,
ALTER COLUMN features SET STORAGE DEFAULT,
ALTER COLUMN label SET STORAGE DEFAULT;
ALTER COLUMN changes SET STORAGE EXTENDED,
ALTER COLUMN data SET STORAGE EXTENDED,
ALTER COLUMN features SET STORAGE EXTENDED,
ALTER COLUMN label SET STORAGE EXTENDED;
ALTER TABLE file_data_fragment
ALTER COLUMN metadata SET STORAGE DEFAULT;
ALTER COLUMN metadata SET STORAGE EXTENDED;
ALTER TABLE file_media_object
ALTER COLUMN mtype SET STORAGE DEFAULT,
ALTER COLUMN name SET STORAGE DEFAULT;
ALTER COLUMN mtype SET STORAGE EXTENDED,
ALTER COLUMN name SET STORAGE EXTENDED;
ALTER TABLE file_thumbnail
ALTER COLUMN data SET STORAGE DEFAULT,
ALTER COLUMN props SET STORAGE DEFAULT;
ALTER COLUMN data SET STORAGE EXTENDED,
ALTER COLUMN props SET STORAGE EXTENDED;
ALTER TABLE global_complaint_report
ALTER COLUMN content SET STORAGE DEFAULT,
ALTER COLUMN type SET STORAGE DEFAULT;
ALTER COLUMN content SET STORAGE EXTENDED,
ALTER COLUMN type SET STORAGE EXTENDED;
ALTER TABLE profile
ALTER COLUMN auth_backend SET STORAGE DEFAULT,
ALTER COLUMN email SET STORAGE DEFAULT,
ALTER COLUMN fullname SET STORAGE DEFAULT,
ALTER COLUMN lang SET STORAGE DEFAULT,
ALTER COLUMN password SET STORAGE DEFAULT,
ALTER COLUMN props SET STORAGE DEFAULT,
ALTER COLUMN theme SET STORAGE DEFAULT;
ALTER COLUMN auth_backend SET STORAGE EXTENDED,
ALTER COLUMN email SET STORAGE EXTENDED,
ALTER COLUMN fullname SET STORAGE EXTENDED,
ALTER COLUMN lang SET STORAGE EXTENDED,
ALTER COLUMN password SET STORAGE EXTENDED,
ALTER COLUMN props SET STORAGE EXTENDED,
ALTER COLUMN theme SET STORAGE EXTENDED;
ALTER TABLE profile_complaint_report
ALTER COLUMN content SET STORAGE DEFAULT,
ALTER COLUMN type SET STORAGE DEFAULT;
ALTER COLUMN content SET STORAGE EXTENDED,
ALTER COLUMN type SET STORAGE EXTENDED;
ALTER TABLE project
ALTER COLUMN name SET STORAGE DEFAULT;
ALTER COLUMN name SET STORAGE EXTENDED;
ALTER TABLE scheduled_task
ALTER COLUMN cron_expr SET STORAGE DEFAULT,
ALTER COLUMN id SET STORAGE DEFAULT;
ALTER COLUMN cron_expr SET STORAGE EXTENDED,
ALTER COLUMN id SET STORAGE EXTENDED;
ALTER TABLE server_error_report
ALTER COLUMN content SET STORAGE DEFAULT;
ALTER COLUMN content SET STORAGE EXTENDED;
ALTER TABLE server_prop
ALTER COLUMN content SET STORAGE DEFAULT,
ALTER COLUMN id SET STORAGE DEFAULT;
ALTER COLUMN content SET STORAGE EXTENDED,
ALTER COLUMN id SET STORAGE EXTENDED;
ALTER TABLE storage_object
ALTER COLUMN backend SET STORAGE DEFAULT,
ALTER COLUMN metadata SET STORAGE DEFAULT;
ALTER COLUMN backend SET STORAGE EXTENDED,
ALTER COLUMN metadata SET STORAGE EXTENDED;
ALTER TABLE task
ALTER COLUMN error SET STORAGE DEFAULT,
ALTER COLUMN label SET STORAGE DEFAULT,
ALTER COLUMN name SET STORAGE DEFAULT,
ALTER COLUMN props SET STORAGE DEFAULT,
ALTER COLUMN queue SET STORAGE DEFAULT,
ALTER COLUMN status SET STORAGE DEFAULT;
ALTER COLUMN error SET STORAGE EXTENDED,
ALTER COLUMN label SET STORAGE EXTENDED,
ALTER COLUMN name SET STORAGE EXTENDED,
ALTER COLUMN props SET STORAGE EXTENDED,
ALTER COLUMN queue SET STORAGE EXTENDED,
ALTER COLUMN status SET STORAGE EXTENDED;
ALTER TABLE team
ALTER COLUMN name SET STORAGE DEFAULT;
ALTER COLUMN name SET STORAGE EXTENDED;
ALTER TABLE team_font_variant
ALTER COLUMN font_family SET STORAGE DEFAULT,
ALTER COLUMN font_style SET STORAGE DEFAULT;
ALTER COLUMN font_family SET STORAGE EXTENDED,
ALTER COLUMN font_style SET STORAGE EXTENDED;
ALTER TABLE team_invitation
ALTER COLUMN email_to SET STORAGE DEFAULT,
ALTER COLUMN role SET STORAGE DEFAULT;
ALTER COLUMN email_to SET STORAGE EXTENDED,
ALTER COLUMN role SET STORAGE EXTENDED;
ALTER TABLE usage_quote
ALTER COLUMN target SET STORAGE DEFAULT;
ALTER COLUMN target SET STORAGE EXTENDED;
ALTER TABLE webhook
ALTER COLUMN error_code SET STORAGE DEFAULT,
ALTER COLUMN mtype SET STORAGE DEFAULT,
ALTER COLUMN secret_key SET STORAGE DEFAULT,
ALTER COLUMN uri SET STORAGE DEFAULT;
ALTER COLUMN error_code SET STORAGE EXTENDED,
ALTER COLUMN mtype SET STORAGE EXTENDED,
ALTER COLUMN secret_key SET STORAGE EXTENDED,
ALTER COLUMN uri SET STORAGE EXTENDED;
ALTER TABLE webhook_delivery
ALTER COLUMN error_code SET STORAGE DEFAULT,
ALTER COLUMN req_data SET STORAGE DEFAULT,
ALTER COLUMN rsp_data SET STORAGE DEFAULT;
ALTER COLUMN error_code SET STORAGE EXTENDED,
ALTER COLUMN req_data SET STORAGE EXTENDED,
ALTER COLUMN rsp_data SET STORAGE EXTENDED;

View File

@ -484,7 +484,7 @@ PENPOT_SECRET_KEY: my-super-secure-key
### Database
Penpot only supports PostgreSQL and we highly recommend >=16 version. If you are using official
Penpot only supports PostgreSQL and we highly recommend >=15 version. If you are using official
docker images this is already solved for you.
Essential database configuration: