SELECT FROM VALUES incorrectly throws an error about undefined values
Nobody has claimed this yet.
- Dominant language
- JavaScript
- Stars
- 8.7k
- Forks
- 374
- Avg merge
- 11d 16h
- Merged PRs (30d)
- 1
Description
Bug Repro
There seems to be a bug in the way the SQL is composed via template strings. Consider the following code:
async function repro() {
const design = 'd203e218-ea68-46c4-a7c5-a99986062931';
rows = [{ pos: 0, stone: 'fcc6fdb8-8b7d-47ee-9c7e-891e68718d43', color: 1 }];
await sql`
WITH ${makeCheckpointCte(design)}
INSERT INTO palette (design, checkpoint, pos, stone, color)
SELECT
${design},
(SELECT checkpoint FROM next_checkpoint),
input.pos,
input.stone,
input.color
FROM (VALUES ${sql(rows, 'pos', 'stone', 'color')})
AS input (pos, stone, color)`;
}
function makeCheckpointCte(design: string) {
return sql`
current_checkpoint AS (
SELECT COALESCE(MAX(checkpoint), -1) AS checkpoint
FROM design_checkpoints
WHERE design = (${design})
), next_checkpoint AS (
INSERT INTO design_checkpoints (design, checkpoint)
SELECT (${design}), 1 + current.checkpoint
FROM current_checkpoint current
RETURNING checkpoint
)`;
}
The line that does FROM (VALUES (...)) causes the following crash.
Error: UNDEFINED_VALUE: Undefined values are not allowed
at handleValue (/workspaces/ddt-project-manager/node_modules/.pnpm/postgres@3.4.7/node_modules/postgres/cjs/src/types.js:83:20)
at stringifyValue (/workspaces/ddt-project-manager/node_modules/.pnpm/postgres@3.4.7/node_modules/postgres/cjs/src/types.js:113:5)
at /workspaces/ddt-project-manager/node_modules/.pnpm/postgres@3.4.7/node_modules/postgres/cjs/src/types.js:125:7
at Array.map (<anonymous>)
at /workspaces/ddt-project-manager/node_modules/.pnpm/postgres@3.4.7/node_modules/postgres/cjs/src/types.js:124:19
at Array.map (<anonymous>)
at valuesBuilder (/workspaces/ddt-project-manager/node_modules/.pnpm/postgres@3.4.7/node_modules/postgres/cjs/src/types.js:123:16)
at Object.values [as fn] (/workspaces/ddt-project-manager/node_modules/.pnpm/postgres@3.4.7/node_modules/postgres/cjs/src/types.js:133:10)
at Builder.build (/workspaces/ddt-project-manager/node_modules/.pnpm/postgres@3.4.7/node_modules/postgres/cjs/src/types.js:71:17)
at stringifyValue (/workspaces/ddt-project-manager/node_modules/.pnpm/postgres@3.4.7/node_modules/postgres/cjs/src/types.js:109:38)
at cachedError (/workspaces/ddt-project-manager/node_modules/.pnpm/postgres@3.4.7/node_modules/postgres/cjs/src/query.js:170:23)
at new Query (/workspaces/ddt-project-manager/node_modules/.pnpm/postgres@3.4.7/node_modules/postgres/cjs/src/query.js:36:24)
at sql (/workspaces/ddt-project-manager/node_modules/.pnpm/postgres@3.4.7/node_modules/postgres/cjs/src/index.js:112:11)
at Object.updatePalette (/workspaces/ddt-project-manager/target/src/server/database.js:94:19) {
code: 'UNDEFINED_VALUE'
}
The SQL I used is close to what the SQL would be without this library. However, I had a suspicion that VALUES should perhaps be dropped. However, doing that only causes a different error.
With the line
FROM (${sql(rows, 'pos', 'stone', 'color')})
the error becomes
TypeError: str.replace is not a function
at escape (/workspaces/ddt-project-manager/node_modules/.pnpm/postgres@3.4.7/node_modules/postgres/cjs/src/types.js:217:20)
at /workspaces/ddt-project-manager/node_modules/.pnpm/postgres@3.4.7/node_modules/postgres/cjs/src/types.js:213:22
at Array.map (<anonymous>)
at escapeIdentifiers (/workspaces/ddt-project-manager/node_modules/.pnpm/postgres@3.4.7/node_modules/postgres/cjs/src/types.js:213:13)
at Object.select [as fn] (/workspaces/ddt-project-manager/node_modules/.pnpm/postgres@3.4.7/node_modules/postgres/cjs/src/types.js:139:12)
at Builder.build (/workspaces/ddt-project-manager/node_modules/.pnpm/postgres@3.4.7/node_modules/postgres/cjs/src/types.js:71:17)
at stringifyValue (/workspaces/ddt-project-manager/node_modules/.pnpm/postgres@3.4.7/node_modules/postgres/cjs/src/types.js:109:38)
at stringify (/workspaces/ddt-project-manager/node_modules/.pnpm/postgres@3.4.7/node_modules/postgres/cjs/src/types.js:100:16)
at build (/workspaces/ddt-project-manager/node_modules/.pnpm/postgres@3.4.7/node_modules/postgres/cjs/src/connection.js:223:20)
at Object.execute (/workspaces/ddt-project-manager/node_modules/.pnpm/postgres@3.4.7/node_modules/postgres/cjs/src/connection.js:167:7)
at cachedError (/workspaces/ddt-project-manager/node_modules/.pnpm/postgres@3.4.7/node_modules/postgres/cjs/src/query.js:170:23)
at new Query (/workspaces/ddt-project-manager/node_modules/.pnpm/postgres@3.4.7/node_modules/postgres/cjs/src/query.js:36:24)
at sql (/workspaces/ddt-project-manager/node_modules/.pnpm/postgres@3.4.7/node_modules/postgres/cjs/src/index.js:112:11)
at Object.updatePalette (/workspaces/ddt-project-manager/target/src/server/database.js:94:19)
so apparently this is not even caught as bad library usage.
Dropping the parenthesis around the interpolated values changes nothing.
Version Info
$ cat package.json | jq .dependencies.postgres
"3.4.7"
$ pnpm -v
10.11.0
$ node -v
v22.16.0
Related Issues
I have only found #1042 to be potentially related.
Contributor guide
No contributing guide indexed for this repository
First steps
- Read the whole issue, then the project's contributing guide.
- Comment on the issue to say you are picking it up — it saves two people doing the same work.
- Fork the repository and make your change on a branch.
- Open a pull request that references the issue number.
Research direction
Start with the reproducer at target/src/server/database.js:94 and the postgres 3.4.7 handling shown in node_modules/.../src/types.js, then run the supplied VALUES query with the reported Node and pnpm versions. Done means the interpolated rows work in the INSERT without UNDEFINED_VALUE or str.replace errors.
Written by the indexing model from the issue text.
Assessment
- Tech stack
- javascript, nodejs, postgres
- Domain
- backend, databases
- Issue type
- Bug
- Difficulty
- 3/5
- Estimated time
- 1-2 days
- Activity status
- Quiet
- Clarity
- Mostly clear
- Newbie friendliness
- 50/100