Jak być może wiesz we wszystkich wersjach aż do PostgreSQL 10, nie było możliwe utworzenie procedury w PostgreSQL. W PostgreSQL 11, PROCEDURE został dodany jako nowy obiekt schematu, który jest podobnym obiektem do FUNCTION, ale bez wartości zwracanej.
Przez lata wiele osób chciało mieć tę funkcjonalność i ostatecznie została ona dodana w PostgreSQL 11. Tradycyjnie PostgreSQL zapewniał wszystkie środki do pisania funkcji (które nazywano procedurami składowanymi), jednak w funkcji nie można uruchamiać transakcji. Wszystko, czego naprawdę możesz użyć, to wyjątki, które są w zasadzie punktami zapisu. Wewnątrz ciała funkcji nie można po prostu zatwierdzić transakcji lub otworzyć nowej. Nowa PROCEDURA CREATE zmieni to wszystko i zapewni funkcjonalność do uruchamiania transakcji wewnątrz kodu proceduralnego.
Zalety korzystania z procedur zapisanych
- Kontrola transakcji pozwalająca nam na ZATWIERDZANIE i WYCOFANIE wewnątrz procedur.
- Bardzo pomocne przy migracji Oracle do PostgreSQL, nowa funkcjonalność procedury może znacznie zaoszczędzić czas.
- Jak widać, istnieje kilka podobieństw między CREATE FUNCTION i CREATE PROCEDURE, więc dla większości użytkowników końcowych wszystko powinno być naprawdę łatwe.
Jak korzystać z procedury składowanej w PostgreSQL
Użyj CREATE PROCEDURE, aby utworzyć nową procedurę w PostgreSQL 11, pozwoli ci to napisać procedurę tak jak inne bazy danych. PROCEDURA jest prawie taka sama jak FUNKCJA bez zwracanej wartości. PROCEDURE jest tworzony za pomocą instrukcji CREATE PROCEDURE w PostgreSQL 11. W przeciwieństwie do instrukcji CREATE FUNCTION, nie ma klauzul RETURNS, klauzul ROWS itp.
Składnia
postgres=# \h CREATE PROCEDURE
Command: CREATE PROCEDURE
Description: define a new procedure
Syntax:
CREATE [ OR REPLACE ] PROCEDURE
name ( [ [ argmode ] [ argname ] argtype [ { DEFAULT | = } default_expr ] [, ...] ] )
{ LANGUAGE lang_name
| TRANSFORM { FOR TYPE type_name } [, ... ]
| [ EXTERNAL ] SECURITY INVOKER | [ EXTERNAL ] SECURITY DEFINER
| SET configuration_parameter { TO value | = value | FROM CURRENT }
| AS 'definition'
| AS 'obj_file', 'link_symbol'
} ...
Przykład
CREATE PROCEDURE procedure1(INOUT p1 TEXT)
AS $$
BEGIN
RAISE NOTICE 'Procedure Parameter: %', p1 ;
END ;
$$
LANGUAGE plpgsql ;
Wykonaj PROCEDURĘ w PostgreSQL
Aby wykonać PROCEDURE w PostgreSQL, użyj instrukcji CALL zamiast instrukcji SELECT. Jest to jedna z różnic między PROCEDUJĄ a FUNKCJĄ.
postgres=# CALL procedure1 (' CREATE PROCEDURE functionality supported in PostgreSQL 11! ');
NOTICE: Procedure Parameter: CREATE PROCEDURE functionality supported in PostgreSQL 11!
p1
--------------------------------------------------------------
CREATE PROCEDURE functionality supported in PostgreSQL 11!
(1 row)
Możesz również określić nazwę parametru w instrukcji CALL. To kolejny sposób na wykonanie PROCEDURY.
postgres=# CALL procedure1 (p1=>'CREATE PROCEDURE functionality supported in PostgreSQL 11!');
NOTICE: Procedure Parameter: CREATE PROCEDURE functionality supported in PostgreSQL 11!
p1
------------------------------------------------------------
CREATE PROCEDURE functionality supported in PostgreSQL 11!
(1 row)
Wyświetl listę utworzonej PROCEDURY
Możesz sprawdzić definicję utworzonej PROCEDURY z polecenia psql, czyli '\df'. Polecenie psql '\df' służy również do wyświetlania definicji utworzonej FUNKCJI.
PROCEDURA pokazuje kolumnę Type jako „proc”, a jeśli jest to FUNCTION, kolumna Type zmienia się na „func”.
Na poniższej liście funkcji utworzyliśmy jedną PROCEDURĘ, więc kolumna Typ zmieniła się na „proc”.
postgres=# \df
List of functions
Schema | Name | Result data type | Argument data types | Type
--------+------------+------------------+---------------------+------
public | procedure1 | | INOUT p1 text | proc
(1 row)
Tutaj możemy utworzyć jedną FUNKCJĘ, aby sprawdzić kolumnę Typ.
CREATE FUNCTION function1(INOUT p1 TEXT)
AS $$
BEGIN
RAISE NOTICE 'Function Parameter: %', p1 ;
END ;
$$
LANGUAGE plpgsql ;
Uruchom FUNKCJĘ za pomocą polecenia WYBIERZ.
postgres=# SELECT function1('CREATE PROCEDURE functionality supported in PostgreSQL 11!');
NOTICE: Function Parameter: CREATE PROCEDURE functionality supported in PostgreSQL 11!
function1
------------------------------------------------------------
CREATE PROCEDURE functionality supported in PostgreSQL 11!
(1 row)
Teraz możesz sprawdzić kolumnę Typ i zobaczyć różnicę. Dla funkcji FUNCTION1 kolumna Type została zmieniona na „func”. Tutaj widać jeszcze jedną różnicę, PROCEDURA jest prawie taka sama jak FUNKCJA bez wartości zwracanej.
postgres=# \df
List of functions
Schema | Name | Result data type | Argument data types | Type
--------+------------+------------------+---------------------+------
public | function1 | text | INOUT p1 text | func
public | procedure1 | | INOUT p1 text | proc
(2 rows)
Wyświetl definicję PROCEDURY w PostgreSQL
Użyj „\sf”, aby wyświetlić definicję utworzonej PROCEDURY.
postgres=# \sf procedure1
CREATE OR REPLACE PROCEDURE public.procedure1(INOUT p1 text)
LANGUAGE plpgsql
AS $procedure$
BEGIN
RAISE NOTICE 'Procedure Parameter: %', p1 ;
END ;
$procedure$
Pobierz oficjalny dokument już dziś Zarządzanie i automatyzacja PostgreSQL za pomocą ClusterControlDowiedz się, co musisz wiedzieć, aby wdrażać, monitorować, zarządzać i skalować PostgreSQLPobierz oficjalny dokument Kontrola transakcji w PROCEDURZE
Kontrola transakcji pozwalająca na COMMIT i ROLLBACK wewnątrz procedur. CREATE FUNCTION nie obsługuje transakcji wewnątrz funkcji. To jest główna różnica między FUNKCJĄ a PROCEDURĄ w PostgreSQL.
Stwórzmy prostą procedurę składowaną, która obsługuje transakcje.
CREATE OR REPLACE PROCEDURE transaction_test()
LANGUAGE plpgsql
AS $$
DECLARE
BEGIN
CREATE TABLE committed_table (id int);
INSERT INTO committed_table VALUES (1);
COMMIT;
CREATE TABLE rollback_table (id int);
INSERT INTO rollback_table VALUES (1);
ROLLBACK;
END $$;
Wykonaj PROCEDURĘ za pomocą instrukcji CALL.
postgres=# CALL transaction_test();
CALL
Sprawdź wynik wykonania.
postgres=# \d
List of relations
Schema | Name | Type | Owner
--------+-----------------+-------+----------
public | committed_table | table | postgres
(1 row)
postgres=# SELECT * FROM committed_table;
id
----
1
(1 row)
W tym blogu widzieliśmy kontrolę transakcji dla CREATE PROCEDURE przy użyciu języka PL/pgSQL, ale kontrola transakcji jest również dostępna w innych językach, takich jak PL/Python, PL/Tcl, PL/Perl.
Składnia kontroli transakcji w innych językach jest następująca:
- PL/Python
- plpy.commit()
- plpy.rollback()
- PL/Tcl
- Potwierdź
- cofanie
- PL/Perl
- spi_commit()
- spi_rollback()
Wniosek
PROCEDURA CREATE jest zdecydowanie jedną z ważnych i pożądanych funkcji PostgreSQL 11. Ta funkcja jest bardzo przydatna przy migracji Oracle do PostgreSQL i wielu różnych przypadkach użycia, a wiele osób z pewnością ją z zadowoleniem.