fix(migration): quote camelCase identifiers in compression option strings#181
Conversation
…ings TimescaleDB's parser for compress_segmentby and compress_orderby folds unquoted identifiers to lowercase (same behaviour as PostgreSQL's regclass parser, which bit us in #179). Prisma's columns are camelCase ('pipelineId', 'nodeId'), so 'pipelineId' was being looked up as 'pipelineid' and the migration failed with: ERROR: column "pipelineid" does not exist HINT: The timescaledb.compress_segmentby option must reference a valid column. Wrap every column name in double quotes inside the option strings — the same pattern used for the table-name argument in #179.
Greptile SummaryThis PR fixes a case-sensitivity bug in TimescaleDB compression option strings by wrapping all column identifiers in double quotes inside the option string literals. The fix is applied consistently to all four affected tables ( Confidence Score: 5/5Safe to merge — targeted, mechanical fix with no logic changes and consistent application across all four tables. The fix is a straightforward text correction: adding escaped double-quotes inside four pairs of compression option strings. All four hypertables are updated identically. The add_compression_policy calls are unaffected. The IF EXISTS guard preserves the no-op behaviour on plain Postgres. No logic, schema, or data is altered. No files require special attention. Important Files Changed
Flowchart%%{init: {'theme': 'neutral'}}%%
flowchart TD
A[prisma migrate deploy] --> B{TimescaleDB installed?}
B -- No --> C[IF EXISTS guard -- no-op on plain Postgres]
B -- Yes --> D[ALTER TABLE SET compression options with quoted identifiers]
D --> D1[PipelineMetric -- segmentby pipelineId -- orderby timestamp DESC id]
D --> D2[NodeMetric -- segmentby nodeId -- orderby timestamp DESC id]
D --> D3[PipelineLog -- segmentby pipelineId -- orderby timestamp DESC id]
D --> D4[NodeStatusEvent -- segmentby nodeId -- orderby timestamp DESC id]
D1 & D2 & D3 & D4 --> E[add_compression_policy 7-day interval per hypertable]
E --> F[Migration complete]
Reviews (1): Last reviewed commit: "fix(migration): quote camelCase identifi..." | Re-trigger Greptile |
#182) Bare SELECT inside a PL/pgSQL DO block is invalid when the result is discarded — Postgres raises 42601 "query has no destination for result data". Switch the four add_compression_policy calls to PERFORM so the migration applies cleanly on TimescaleDB. Follows #179, #180, #181 — same file, same DO block.
Summary
Third in the TimescaleDB-demo bring-up bug series (after #179, #180). Once #180 fixed the missing-column constraint, the migration hit another error on the demo:
```
ERROR: column "pipelineid" does not exist
HINT: The timescaledb.compress_segmentby option must reference a valid column.
```
Note the lowercase `pipelineid` — same bug class as #179. TimescaleDB's parser for `compress_segmentby` and `compress_orderby` folds unquoted identifiers to lowercase. Prisma's columns are camelCase (`pipelineId`, `nodeId`), so `'pipelineId'` was being looked up as `pipelineid` and failing.
Fix
Wrap every column name in double quotes inside the option strings — the same idiom used for the table-name argument in #179.
```sql
ALTER TABLE "PipelineMetric" SET (
timescaledb.compress,
timescaledb.compress_segmentby = '"pipelineId"',
timescaledb.compress_orderby = '"timestamp" DESC, "id"'
);
```
`timestamp` and `id` were already lowercase so they were technically working unquoted, but quoting them too makes the policy here defensive and consistent — a future column rename to e.g. `createdAt` would now still parse correctly without another fix-up.
Why this didn't surface earlier
Same as #179 / #180: every prior deployment ran on plain Postgres, where the `IF EXISTS (... timescaledb)` guard makes this whole migration a no-op. The hosted demo on `timescale/timescaledb:2.16.0-pg16` is the first environment in the wild with the extension installed.
Recovery instructions
For anyone whose DB is currently in the failed state on this migration:
Option A — wipe and reapply (cleanest if no real data, e.g. demo):
```sh
docker compose down -v
docker volume ls | grep vf-demo-pg # verify gone, manual rm if needed
docker compose up
```
Option B — preserve data:
```sh
npx prisma migrate resolve --rolled-back 20260329000001_timescaledb_compression
npx prisma migrate deploy
```
Drift warning for plain-Postgres users
Same caveat as #179 / #180: the migration's checksum changes. On next `prisma migrate deploy` you may see a "migration was modified after applied" warning. Resolve with:
```sh
npx prisma migrate resolve --applied 20260329000001_timescaledb_compression
```
One-time fix; the no-op behaviour on plain Postgres is unchanged.
Test plan