SQLite
 sql >> Baza danych >  >> RDS >> SQLite

Szybki post o SQLite UPSERT i nowej klauzuli RETURNING.

Klauzula RETURNING

Oficjalne dokumenty można przeczytać tutaj.

Wiele razy po wstawieniu rekordów do naszej bazy danych chcemy zwrócić niektóre dane (prawdopodobnie id). Od wersji 3.35.0 (2021-03-12), SQLite obsługuje RETURNING klauzula, która pozwala zwrócić wiersz wynikowy (lub określone kolumny) dla każdego zmodyfikowanego wiersza bazy danych przez DELETE , UPDATE lub INSERT oświadczenie.

INSERT INTO customers (fullName, birthdateTimestamp, address) 
VALUES ('Andrew Mitch', 643911868, '206 Grange Road, Gillingham') 
RETURNING *;

Powyższe zapytanie, po wykonaniu, zwróci nam każdą wartość wstawioną do bazy danych, wraz z id każdego rzędu. W ten sposób możemy uniknąć wykonywania kolejnego SELECT zapytanie do bazy danych. Całkiem fajnie, co?

Klauzula UPSERT

Oficjalne dokumenty można przeczytać tutaj.

Kolejną fajną małą funkcją jest UPSERT klauzula. Zostało to dodane w wersji 3.24.0 (2018-06-04) i powoduje to INSERT zachowywać się jak UPDATE lub no-op , w przypadku UNIQUE CONSTRAINT lub PRIMARY KEY CONSTRAINT naruszenie.

Aby rozwinąć, załóżmy, że masz action_records tabela, która zawiera wszystkie akcje uruchomione przez użytkowników w users tabela, dla konkretnej sesji . Po uruchomieniu nowej akcji chcesz wstawić nowy action_record bez błędu lub, jeśli istniejący ORAZ ma tę samą sygnaturę czasową sesji (jest to obsługiwane przez ON CONFLICT klauzuli), zaktualizuj starą. Możesz również opcjonalnie dodać WHERE oświadczenie, które spowoduje no-op , jeśli nie zostały spełnione. Poniższe zapytanie powinno wystarczyć:

-- 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

PODNOSZENIE I ZWROT połączone

Jedną z rzeczy, które bardzo mi się podobało, jest to, że można połączyć te klauzule, po prostu dodając RETURNING * na końcu zapytania. W ten sposób zostanie zwrócony dowolny wiersz (lub określone kolumny), wstawiony lub zaktualizowany.


  1. Database
  2.   
  3. Mysql
  4.   
  5. Oracle
  6.   
  7. Sqlserver
  8.   
  9. PostgreSQL
  10.   
  11. Access
  12.   
  13. SQLite
  14.   
  15. MariaDB
  1. group_concat i jak używać numeru wiersza w sqlite

  2. Wyszukiwanie z akcentem w sqlite (Android)

  3. android.database.sqlite.SQLiteException:blisko s:błąd składni (kod 1):,

  4. SQLite - Utwórz relację

  5. Maksymalny rozmiar bazy danych SQLite w aplikacji na Androida