RETURNING-sætningen
Du kan læse de officielle dokumenter her.
Mange gange finder vi os selv i at ville returnere nogle data (sandsynligvis id'et) efter at have indsat poster i vores database. Siden version 3.35.0
(2021-03-12), SQLite understøtter RETURNING
klausul, som giver dig mulighed for at returnere en resultatrække (eller specifikke kolonner) for hver ændret databaserække med en DELETE
, UPDATE
eller INSERT
erklæring.
INSERT INTO customers (fullName, birthdateTimestamp, address)
VALUES ('Andrew Mitch', 643911868, '206 Grange Road, Gillingham')
RETURNING *;
Ovenstående forespørgsel vil efter udførelse returnere alle værdier indsat i databasen sammen med id
af hver række. På denne måde kan vi undgå at lave endnu en SELECT
forespørgsel til databasen. Ret pænt, ikke?
UPSERT-klausulen
Du kan læse de officielle dokumenter her.
En anden fin lille funktion er UPSERT
klausul. Dette blev tilføjet i version 3.24.0
(2018-06-04), og det forårsager INSERT
at opføre sig enten som en UPDATE
eller en no-op
, i tilfælde af en UNIQUE CONSTRAINT
eller en PRIMARY KEY CONSTRAINT
krænkelse.
For at uddybe, lad os antage, at du har en action_records
tabel, som indeholder alle handlinger udført af brugere i users
tabel, for en bestemt session . Når en ny handling udløses, vil du enten indsætte en ny action_record
uden fejl, eller hvis eksisterende OG har samme sessionstidsstempel (dette håndteres af ON CONFLICT
klausul), opdatere den gamle. Du kan også valgfrit tilføje en WHERE
sætning, som vil resultere i en no-op
, hvis ikke opfyldt. Forespørgslen nedenfor burde gøre det:
-- Create users table and assign userID and sessionStartTimestamp as a UNIQUE CONSTRAINT.
DROP TABLE IF EXISTS "action_records";
CREATE TABLE IF NOT EXISTS "action_records" (
"id" INTEGER NOT NULL,
"userID" INTEGER NOT NULL,
"sessionStartTimestamp" INTEGER NOT NULL,
"errorMsg" TEXT,
PRIMARY KEY("id" AUTOINCREMENT),
FOREIGN KEY("userID") REFERENCES "users"("id") ON DELETE CASCADE,
UNIQUE(userID, sessionStartTimestamp)
);
-- Insert new record or update the old one based on UNIQUE_CONSTRAINT OF userID & session_start_timestamp
INSERT INTO action_records (userID, errorMsg, sessionStartTimestamp)
VALUES (258, null, 643911868)
ON CONFLICT(userID, sessionStartTimestamp) -- Conflict when a record for the same user and session exists
DO UPDATE SET errorMsg = 'An error occured'
WHERE errorMsg IS NOT NULL -- This will be a no-op in case there is already an error and you don't want to update it
RETURNING *; -- Optionally adding RETURNING to retrieve any number of columns we want
UPSERT OG RETURNERING kombineret
En ting, jeg virkelig kunne lide, er det faktum, at du kan kombinere disse klausuler ved blot at tilføje RETURNING *
i slutningen af forespørgslen. På denne måde vil enhver række (eller specificerede kolonner), enten indsat eller opdateret, blive returneret.