dziś pierwszy odcinek o zmianach w postgresie 8.2. tematem odcinka są zapytania “… returning".
do zapytań modyfikujących dane – INSERT INTO, UPDATE, DELETE FROM zostało dodane rozszerzenie “RETURNING".
składnia wygląda następująco:
- INSERT INTO tabelka (pola) VALUES (costam) RETURNING wyrażenie;
- UPDATE tabelka SET pole = X WHERE cośtam RETURNING wyrażenie;
- DELETE FROM tabelka WHERE cośtam RETURNING wyrażenie;
przykłady użycia dla INSERT:
# CREATE TABLE x (id serial PRIMARY KEY, ble INT4); NOTICE: CREATE TABLE will CREATE implicit SEQUENCE "x_id_seq" FOR serial COLUMN "x.id" NOTICE: CREATE TABLE / PRIMARY KEY will CREATE implicit INDEX "x_pkey" FOR TABLE "x" CREATE TABLE # INSERT INTO x (ble) VALUES ('123') returning id; id ---- 1 (1 ROW) INSERT 0 1 # INSERT INTO x (ble) VALUES ('123') returning id, ble + 123; id | ?COLUMN? ----+---------- 2 | 246 (1 ROW) INSERT 0 1 # INSERT INTO x (ble) VALUES ('123') returning *; id | ble ----+----- 3 | 123 (1 ROW) INSERT 0 1 # INSERT INTO x (ble) VALUES ('123') returning *, now(), (SELECT COUNT(*) FROM pg_class); id | ble | now | ?COLUMN? ----+-----+-------------------------------+---------- 4 | 123 | 2006-12-07 22:52:24.573777+01 | 209 (1 ROW) INSERT 0 1 # SELECT * FROM x; id | ble ----+----- 1 | 123 2 | 123 3 | 123 4 | 123 (4 ROWS) # INSERT INTO x (ble) SELECT ble + 2 FROM x returning *; id | ble ----+----- 5 | 125 6 | 125 7 | 125 8 | 125 (4 ROWS) INSERT 0 4
miłe, czyż nie? głównym celem jest możliwość automatycznego pobierania wartości typu id – nadawanych z sekwencji. ale zadziała to także zwracając dane modyfikowane przez triggery.
to co jest po “RETURNING" musi być zgodne formatowo z tym co jest w standardowym select'cie między SELECT a FROM.
przykłady użycia dla UPDATE:
# UPDATE x SET ble = ble * 2 WHERE id % 2 = 0 returning *; id | ble ----+----- 2 | 246 4 | 246 6 | 250 8 | 250 (4 ROWS) UPDATE 4
zwracam uwagę na to, że returning zwraca nowe wartości! czyli tak po triggerowemu mówiąc: retyrning * oznacza return NEW; a nie return OLD;!
przykłady użycia dla DELETE:
# DELETE FROM x WHERE id % 2 = 1 returning *; id | ble ----+----- 1 | 123 3 | 123 5 | 125 7 | 125 (4 ROWS) DELETE 4
jak widać składnia wszędzie jest podobna, miła łatwa i prosta. a do tego niesie sporo ułatwień. mnie osobiście cieszy INSERT … returning id; bo załatwia mi w piękny sposób odpowiadanie ludziom pytającym o id, i reagującym nerwowo na sugestie: select currval() : “ale czy jak dwa połączenia wstawią rekordy …" 🙂