sqlc-dev / sqlc

Generate type-safe code from SQL
https://sqlc.dev
MIT License
12.24k stars 778 forks source link

Same parameter used multiple times not respected when using PgVector with pgx (Postgres) #3496

Open rob2244 opened 1 month ago

rob2244 commented 1 month ago

Version

1.26.0

What happened?

When using the same numbered parameter multiple times in the same statement, or when using sqlc.arg or sqlc.narg with the same parameter name with a PgVector Vector type, the parameter is output in the generated struct multiple times.

The expectation is that the parameter is generated in the struct only once and used multiple times in the SQL. It seems to only be a problem with PgVector and is working correctly with other data types.

Relevant log output

No response

Database schema

CREATE TABLE IF NOT EXISTS client_portal.public.glossary (
    id SERIAL primary key,
    org_id uuid NOT NULL,
    user_id uuid NOT NULL,
    term varchar NOT NULL,
    definition varchar NOT NULL,
    tags varchar,
    term_embedding vector(1024),
    tags_query tsquery,
    created_date timestamp DEFAULT (now() at time zone 'utc'),
    updated_date timestamp DEFAULT (now() at time zone 'utc'),
    UNIQUE(org_id, user_id, term)
);

SQL queries

-- name: SearchGlossaryByEmbedding :many
SELECT
    id,
    term,
    definition,
    tags
FROM glossary
WHERE 1 - (term_embedding <=> $1) >= $2
    AND org_id = $3
ORDER BY 1 - (term_embedding <=> $1) DESC
LIMIT $4;

Configuration

version: "2"
sql:
  - engine: "postgresql"
    queries: "/pkg/dal/queries/"
    schema: "migrations/"
    gen:
      go:
        package: "dal"
        out: "pkg/dal/sqlc"
        sql_package: "pgx/v5"

Playground URL

https://play.sqlc.dev/p/ef4803670b12447e6b7b3bb4330920573dd2e1f32fbf0262657355baec04dd84

What operating system are you using?

Linux

What database engines are you using?

PostgreSQL

What type of code are you generating?

Go

felipesdias commented 1 month ago

The issue is that your query has a named parameter "term_embedding" and a sequence parameter "$1" inferred as "term_embedding". To resolve this, you just need to change the name of the parameter "term_embedding".

example:

-- name: foo :many
SELECT
    id,
    term,
    definition,
    tags
FROM glossary
WHERE 1 - (term_embedding <=> sqlc.arg(term_embedding_p)) >= $1
    AND org_id = $2
ORDER BY 1 - (term_embedding <=> sqlc.arg(term_embedding_p)) DESC
LIMIT $3;
rob2244 commented 1 month ago

@felipesdias Same issue, I get TermEmbedding and Embedding in generated struct

https://play.sqlc.dev/p/c62075bad2d8348587ff871fda37f694911eab79225a8592050d31459e2aaca0

rob2244 commented 1 month ago

@felipesdias Same issue, I get TermEmbedding and Embedding in generated struct

https://play.sqlc.dev/p/c62075bad2d8348587ff871fda37f694911eab79225a8592050d31459e2aaca0

Ah nvm I see the problem I have to cast $1 as a float, it's thinking it's another vector, ty!

rob2244 commented 1 month ago

I think I'm gonna make a docs pr in case this naming thing trips anybosy else up