diff options
| author | Tom Lane | 2006-08-14 21:14:42 +0000 |
|---|---|---|
| committer | Tom Lane | 2006-08-14 21:14:42 +0000 |
| commit | 3d1e01caa46b87b734e4758ad9885e1e12bc77c8 (patch) | |
| tree | 5bb57f3ebf3e752145f32b0a9ce8fca093ce321d /src/test | |
| parent | 29fa051316115fd0b7e8f965c77d5e04a155dcd6 (diff) | |
Support INSERT/UPDATE/DELETE RETURNING in plpgsql, with rowcount checking
as per yesterday's proposal. Also make things a tad more orthogonal by
adding the recent STRICT addition to EXECUTE INTO.
Jonah Harris and Tom Lane
Diffstat (limited to 'src/test')
| -rw-r--r-- | src/test/regress/expected/plpgsql.out | 140 | ||||
| -rw-r--r-- | src/test/regress/sql/plpgsql.sql | 116 |
2 files changed, 256 insertions, 0 deletions
diff --git a/src/test/regress/expected/plpgsql.out b/src/test/regress/expected/plpgsql.out index e776c8f33cd..c0c76c0a987 100644 --- a/src/test/regress/expected/plpgsql.out +++ b/src/test/regress/expected/plpgsql.out @@ -2048,6 +2048,7 @@ select * from foo; 20 (2 rows) +drop table foo; -- Test for pass-by-ref values being stored in proper context create function test_variable_storage() returns text as $$ declare x text; @@ -2794,3 +2795,142 @@ select multi_datum_use(42); t (1 row) +-- +-- Test STRICT limiter in both planned and EXECUTE invocations. +-- Note that a data-modifying query is quasi strict (disallow multi rows) +-- by default in the planned case, but not in EXECUTE. +-- +create temp table foo (f1 int, f2 int); +insert into foo values (1,2), (3,4); +create or replace function footest() returns void as $$ +declare x record; +begin + -- should work + insert into foo values(5,6) returning * into x; + raise notice 'x.f1 = %, x.f2 = %', x.f1, x.f2; +end$$ language plpgsql; +select footest(); +NOTICE: x.f1 = 5, x.f2 = 6 + footest +--------- + +(1 row) + +create or replace function footest() returns void as $$ +declare x record; +begin + -- should fail due to implicit strict + insert into foo values(7,8),(9,10) returning * into x; + raise notice 'x.f1 = %, x.f2 = %', x.f1, x.f2; +end$$ language plpgsql; +select footest(); +ERROR: query returned more than one row +CONTEXT: PL/pgSQL function "footest" line 4 at SQL statement +create or replace function footest() returns void as $$ +declare x record; +begin + -- should work + execute 'insert into foo values(5,6) returning *' into x; + raise notice 'x.f1 = %, x.f2 = %', x.f1, x.f2; +end$$ language plpgsql; +select footest(); +NOTICE: x.f1 = 5, x.f2 = 6 + footest +--------- + +(1 row) + +create or replace function footest() returns void as $$ +declare x record; +begin + -- this should work since EXECUTE isn't as picky + execute 'insert into foo values(7,8),(9,10) returning *' into x; + raise notice 'x.f1 = %, x.f2 = %', x.f1, x.f2; +end$$ language plpgsql; +select footest(); +NOTICE: x.f1 = 7, x.f2 = 8 + footest +--------- + +(1 row) + +select * from foo; + f1 | f2 +----+---- + 1 | 2 + 3 | 4 + 5 | 6 + 5 | 6 + 7 | 8 + 9 | 10 +(6 rows) + +create or replace function footest() returns void as $$ +declare x record; +begin + -- should work + select * from foo where f1 = 3 into strict x; + raise notice 'x.f1 = %, x.f2 = %', x.f1, x.f2; +end$$ language plpgsql; +select footest(); +NOTICE: x.f1 = 3, x.f2 = 4 + footest +--------- + +(1 row) + +create or replace function footest() returns void as $$ +declare x record; +begin + -- should fail, no rows + select * from foo where f1 = 0 into strict x; + raise notice 'x.f1 = %, x.f2 = %', x.f1, x.f2; +end$$ language plpgsql; +select footest(); +ERROR: query returned no rows +CONTEXT: PL/pgSQL function "footest" line 4 at SQL statement +create or replace function footest() returns void as $$ +declare x record; +begin + -- should fail, too many rows + select * from foo where f1 > 3 into strict x; + raise notice 'x.f1 = %, x.f2 = %', x.f1, x.f2; +end$$ language plpgsql; +select footest(); +ERROR: query returned more than one row +CONTEXT: PL/pgSQL function "footest" line 4 at SQL statement +create or replace function footest() returns void as $$ +declare x record; +begin + -- should work + execute 'select * from foo where f1 = 3' into strict x; + raise notice 'x.f1 = %, x.f2 = %', x.f1, x.f2; +end$$ language plpgsql; +select footest(); +NOTICE: x.f1 = 3, x.f2 = 4 + footest +--------- + +(1 row) + +create or replace function footest() returns void as $$ +declare x record; +begin + -- should fail, no rows + execute 'select * from foo where f1 = 0' into strict x; + raise notice 'x.f1 = %, x.f2 = %', x.f1, x.f2; +end$$ language plpgsql; +select footest(); +ERROR: query returned no rows +CONTEXT: PL/pgSQL function "footest" line 4 at execute statement +create or replace function footest() returns void as $$ +declare x record; +begin + -- should fail, too many rows + execute 'select * from foo where f1 > 3' into strict x; + raise notice 'x.f1 = %, x.f2 = %', x.f1, x.f2; +end$$ language plpgsql; +select footest(); +ERROR: query returned more than one row +CONTEXT: PL/pgSQL function "footest" line 4 at execute statement +drop function footest(); diff --git a/src/test/regress/sql/plpgsql.sql b/src/test/regress/sql/plpgsql.sql index 86aa2ec0574..6e8f6de2e07 100644 --- a/src/test/regress/sql/plpgsql.sql +++ b/src/test/regress/sql/plpgsql.sql @@ -1777,6 +1777,8 @@ reset statement_timeout; select * from foo; +drop table foo; + -- Test for pass-by-ref values being stored in proper context create function test_variable_storage() returns text as $$ declare x text; @@ -2324,3 +2326,117 @@ begin end$$ language plpgsql; select multi_datum_use(42); + +-- +-- Test STRICT limiter in both planned and EXECUTE invocations. +-- Note that a data-modifying query is quasi strict (disallow multi rows) +-- by default in the planned case, but not in EXECUTE. +-- + +create temp table foo (f1 int, f2 int); + +insert into foo values (1,2), (3,4); + +create or replace function footest() returns void as $$ +declare x record; +begin + -- should work + insert into foo values(5,6) returning * into x; + raise notice 'x.f1 = %, x.f2 = %', x.f1, x.f2; +end$$ language plpgsql; + +select footest(); + +create or replace function footest() returns void as $$ +declare x record; +begin + -- should fail due to implicit strict + insert into foo values(7,8),(9,10) returning * into x; + raise notice 'x.f1 = %, x.f2 = %', x.f1, x.f2; +end$$ language plpgsql; + +select footest(); + +create or replace function footest() returns void as $$ +declare x record; +begin + -- should work + execute 'insert into foo values(5,6) returning *' into x; + raise notice 'x.f1 = %, x.f2 = %', x.f1, x.f2; +end$$ language plpgsql; + +select footest(); + +create or replace function footest() returns void as $$ +declare x record; +begin + -- this should work since EXECUTE isn't as picky + execute 'insert into foo values(7,8),(9,10) returning *' into x; + raise notice 'x.f1 = %, x.f2 = %', x.f1, x.f2; +end$$ language plpgsql; + +select footest(); + +select * from foo; + +create or replace function footest() returns void as $$ +declare x record; +begin + -- should work + select * from foo where f1 = 3 into strict x; + raise notice 'x.f1 = %, x.f2 = %', x.f1, x.f2; +end$$ language plpgsql; + +select footest(); + +create or replace function footest() returns void as $$ +declare x record; +begin + -- should fail, no rows + select * from foo where f1 = 0 into strict x; + raise notice 'x.f1 = %, x.f2 = %', x.f1, x.f2; +end$$ language plpgsql; + +select footest(); + +create or replace function footest() returns void as $$ +declare x record; +begin + -- should fail, too many rows + select * from foo where f1 > 3 into strict x; + raise notice 'x.f1 = %, x.f2 = %', x.f1, x.f2; +end$$ language plpgsql; + +select footest(); + +create or replace function footest() returns void as $$ +declare x record; +begin + -- should work + execute 'select * from foo where f1 = 3' into strict x; + raise notice 'x.f1 = %, x.f2 = %', x.f1, x.f2; +end$$ language plpgsql; + +select footest(); + +create or replace function footest() returns void as $$ +declare x record; +begin + -- should fail, no rows + execute 'select * from foo where f1 = 0' into strict x; + raise notice 'x.f1 = %, x.f2 = %', x.f1, x.f2; +end$$ language plpgsql; + +select footest(); + +create or replace function footest() returns void as $$ +declare x record; +begin + -- should fail, too many rows + execute 'select * from foo where f1 > 3' into strict x; + raise notice 'x.f1 = %, x.f2 = %', x.f1, x.f2; +end$$ language plpgsql; + +select footest(); + +drop function footest(); |
