stephencelis / SQLite.swift

A type-safe, Swift-language layer over SQLite3.
MIT License
9.57k stars 1.54k forks source link

It is not possible to use UPSERT with a composite/multicolumn unique index #1219

Open DominikPalo opened 11 months ago

DominikPalo commented 11 months ago

Build Information

Issue

I'm trying to execute UPSERT on a table, where the unique index is a composite index - composed of multiple columns (node_id and name in my case). Unfortunately, it seems that the upsert method doesn't allow passing multiple expressions/columns as an onConflictOf argument.

A possible solution would be to allow passing an array instead of just a single expression, e.g.:

// ...
let expNodeId = Expression<Int64>("node_id")
let expName = Expression<String>("name")
let expValue = Expression<String>("value")

myTable.upsert(expValue <- "foo", onConflictOf: [expNodeId, expName])

which would produce a valid UPSERT expression:

INSERT INTO "myTable" ("value") VALUES ('foo') ON CONFLICT ("node_id" , "name") DO UPDATE SET "node_id" = "excluded"."node_id", "name" = "excluded"."name", "value" = "excluded"."value"

UPDATE: As a workaround, I ended up with this:

myTable.upsert(expValue <- "foo",  Expression<Void>(literal: "\"node_id\", \"name\""))