2007-03-13 01:33:44 +01:00
|
|
|
--
|
|
|
|
-- Tests to exercise the plan caching/invalidation mechanism
|
|
|
|
--
|
2007-03-16 17:11:49 +01:00
|
|
|
CREATE TEMP TABLE pcachetest AS SELECT * FROM int8_tbl;
|
2007-03-13 01:33:44 +01:00
|
|
|
-- create and use a cached plan
|
2007-03-16 17:11:49 +01:00
|
|
|
PREPARE prepstmt AS SELECT * FROM pcachetest;
|
2007-03-13 01:33:44 +01:00
|
|
|
EXECUTE prepstmt;
|
|
|
|
q1 | q2
|
|
|
|
------------------+-------------------
|
|
|
|
123 | 456
|
|
|
|
123 | 4567890123456789
|
|
|
|
4567890123456789 | 123
|
|
|
|
4567890123456789 | 4567890123456789
|
|
|
|
4567890123456789 | -4567890123456789
|
|
|
|
(5 rows)
|
|
|
|
|
|
|
|
-- and one with parameters
|
2007-03-16 17:11:49 +01:00
|
|
|
PREPARE prepstmt2(bigint) AS SELECT * FROM pcachetest WHERE q1 = $1;
|
2007-03-13 01:33:44 +01:00
|
|
|
EXECUTE prepstmt2(123);
|
|
|
|
q1 | q2
|
|
|
|
-----+------------------
|
|
|
|
123 | 456
|
|
|
|
123 | 4567890123456789
|
|
|
|
(2 rows)
|
|
|
|
|
|
|
|
-- invalidate the plans and see what happens
|
2007-03-16 17:11:49 +01:00
|
|
|
DROP TABLE pcachetest;
|
2007-03-13 01:33:44 +01:00
|
|
|
EXECUTE prepstmt;
|
2007-03-16 17:11:49 +01:00
|
|
|
ERROR: relation "pcachetest" does not exist
|
2007-03-13 01:33:44 +01:00
|
|
|
EXECUTE prepstmt2(123);
|
2007-03-16 17:11:49 +01:00
|
|
|
ERROR: relation "pcachetest" does not exist
|
2007-03-13 01:33:44 +01:00
|
|
|
-- recreate the temp table (this demonstrates that the raw plan is
|
|
|
|
-- purely textual and doesn't depend on OIDs, for instance)
|
2007-03-16 17:11:49 +01:00
|
|
|
CREATE TEMP TABLE pcachetest AS SELECT * FROM int8_tbl ORDER BY 2;
|
2007-03-13 01:33:44 +01:00
|
|
|
EXECUTE prepstmt;
|
|
|
|
q1 | q2
|
|
|
|
------------------+-------------------
|
|
|
|
4567890123456789 | -4567890123456789
|
|
|
|
4567890123456789 | 123
|
|
|
|
123 | 456
|
|
|
|
123 | 4567890123456789
|
|
|
|
4567890123456789 | 4567890123456789
|
|
|
|
(5 rows)
|
|
|
|
|
|
|
|
EXECUTE prepstmt2(123);
|
|
|
|
q1 | q2
|
|
|
|
-----+------------------
|
|
|
|
123 | 456
|
|
|
|
123 | 4567890123456789
|
|
|
|
(2 rows)
|
|
|
|
|
|
|
|
-- prepared statements should prevent change in output tupdesc,
|
|
|
|
-- since clients probably aren't expecting that to change on the fly
|
2007-03-16 17:11:49 +01:00
|
|
|
ALTER TABLE pcachetest ADD COLUMN q3 bigint;
|
2007-03-13 01:33:44 +01:00
|
|
|
EXECUTE prepstmt;
|
|
|
|
ERROR: cached plan must not change result type
|
|
|
|
EXECUTE prepstmt2(123);
|
|
|
|
ERROR: cached plan must not change result type
|
|
|
|
-- but we're nice guys and will let you undo your mistake
|
2007-03-16 17:11:49 +01:00
|
|
|
ALTER TABLE pcachetest DROP COLUMN q3;
|
2007-03-13 01:33:44 +01:00
|
|
|
EXECUTE prepstmt;
|
|
|
|
q1 | q2
|
|
|
|
------------------+-------------------
|
|
|
|
4567890123456789 | -4567890123456789
|
|
|
|
4567890123456789 | 123
|
|
|
|
123 | 456
|
|
|
|
123 | 4567890123456789
|
|
|
|
4567890123456789 | 4567890123456789
|
|
|
|
(5 rows)
|
|
|
|
|
|
|
|
EXECUTE prepstmt2(123);
|
|
|
|
q1 | q2
|
|
|
|
-----+------------------
|
|
|
|
123 | 456
|
|
|
|
123 | 4567890123456789
|
|
|
|
(2 rows)
|
|
|
|
|
|
|
|
-- Try it with a view, which isn't directly used in the resulting plan
|
|
|
|
-- but should trigger invalidation anyway
|
2007-03-16 17:11:49 +01:00
|
|
|
CREATE TEMP VIEW pcacheview AS
|
|
|
|
SELECT * FROM pcachetest;
|
|
|
|
PREPARE vprep AS SELECT * FROM pcacheview;
|
2007-03-13 01:33:44 +01:00
|
|
|
EXECUTE vprep;
|
|
|
|
q1 | q2
|
|
|
|
------------------+-------------------
|
|
|
|
4567890123456789 | -4567890123456789
|
|
|
|
4567890123456789 | 123
|
|
|
|
123 | 456
|
|
|
|
123 | 4567890123456789
|
|
|
|
4567890123456789 | 4567890123456789
|
|
|
|
(5 rows)
|
|
|
|
|
2007-03-16 17:11:49 +01:00
|
|
|
CREATE OR REPLACE TEMP VIEW pcacheview AS
|
|
|
|
SELECT q1, q2/2 AS q2 FROM pcachetest;
|
2007-03-13 01:33:44 +01:00
|
|
|
EXECUTE vprep;
|
|
|
|
q1 | q2
|
|
|
|
------------------+-------------------
|
|
|
|
4567890123456789 | -2283945061728394
|
|
|
|
4567890123456789 | 61
|
|
|
|
123 | 228
|
|
|
|
123 | 2283945061728394
|
|
|
|
4567890123456789 | 2283945061728394
|
|
|
|
(5 rows)
|
|
|
|
|
2007-03-16 00:12:07 +01:00
|
|
|
-- Check basic SPI plan invalidation
|
|
|
|
create function cache_test(int) returns int as $$
|
|
|
|
declare total int;
|
|
|
|
begin
|
|
|
|
create temp table t1(f1 int);
|
|
|
|
insert into t1 values($1);
|
|
|
|
insert into t1 values(11);
|
|
|
|
insert into t1 values(12);
|
|
|
|
insert into t1 values(13);
|
|
|
|
select sum(f1) into total from t1;
|
|
|
|
drop table t1;
|
|
|
|
return total;
|
|
|
|
end
|
|
|
|
$$ language plpgsql;
|
|
|
|
select cache_test(1);
|
|
|
|
cache_test
|
|
|
|
------------
|
|
|
|
37
|
|
|
|
(1 row)
|
|
|
|
|
|
|
|
select cache_test(2);
|
|
|
|
cache_test
|
|
|
|
------------
|
|
|
|
38
|
|
|
|
(1 row)
|
|
|
|
|
|
|
|
select cache_test(3);
|
|
|
|
cache_test
|
|
|
|
------------
|
|
|
|
39
|
|
|
|
(1 row)
|
|
|
|
|
|
|
|
-- Check invalidation of plpgsql "simple expression"
|
|
|
|
create temp view v1 as
|
|
|
|
select 2+2 as f1;
|
|
|
|
create function cache_test_2() returns int as $$
|
|
|
|
begin
|
|
|
|
return f1 from v1;
|
|
|
|
end$$ language plpgsql;
|
|
|
|
select cache_test_2();
|
|
|
|
cache_test_2
|
|
|
|
--------------
|
|
|
|
4
|
|
|
|
(1 row)
|
|
|
|
|
|
|
|
create or replace temp view v1 as
|
|
|
|
select 2+2+4 as f1;
|
|
|
|
select cache_test_2();
|
|
|
|
cache_test_2
|
|
|
|
--------------
|
|
|
|
8
|
|
|
|
(1 row)
|
|
|
|
|
|
|
|
create or replace temp view v1 as
|
|
|
|
select 2+2+4+(select max(unique1) from tenk1) as f1;
|
|
|
|
select cache_test_2();
|
|
|
|
cache_test_2
|
|
|
|
--------------
|
|
|
|
10007
|
|
|
|
(1 row)
|
|
|
|
|
2007-03-23 20:53:52 +01:00
|
|
|
--- Check that change of search_path is ignored by replans
|
|
|
|
create schema s1
|
|
|
|
create table abc (f1 int);
|
|
|
|
create schema s2
|
|
|
|
create table abc (f1 int);
|
|
|
|
insert into s1.abc values(123);
|
|
|
|
insert into s2.abc values(456);
|
|
|
|
set search_path = s1;
|
|
|
|
prepare p1 as select f1 from abc;
|
|
|
|
execute p1;
|
|
|
|
f1
|
|
|
|
-----
|
|
|
|
123
|
|
|
|
(1 row)
|
|
|
|
|
|
|
|
set search_path = s2;
|
|
|
|
select f1 from abc;
|
|
|
|
f1
|
|
|
|
-----
|
|
|
|
456
|
|
|
|
(1 row)
|
|
|
|
|
|
|
|
execute p1;
|
|
|
|
f1
|
|
|
|
-----
|
|
|
|
123
|
|
|
|
(1 row)
|
|
|
|
|
|
|
|
alter table s1.abc add column f2 float8; -- force replan
|
|
|
|
execute p1;
|
|
|
|
f1
|
|
|
|
-----
|
|
|
|
123
|
|
|
|
(1 row)
|
|
|
|
|
|
|
|
drop schema s1 cascade;
|
|
|
|
NOTICE: drop cascades to table s1.abc
|
|
|
|
drop schema s2 cascade;
|
|
|
|
NOTICE: drop cascades to table abc
|
2007-11-30 19:38:34 +01:00
|
|
|
reset search_path;
|
2007-10-11 20:05:27 +02:00
|
|
|
-- Check that invalidation deals with regclass constants
|
|
|
|
create temp sequence seq;
|
|
|
|
prepare p2 as select nextval('seq');
|
|
|
|
execute p2;
|
|
|
|
nextval
|
|
|
|
---------
|
|
|
|
1
|
|
|
|
(1 row)
|
|
|
|
|
|
|
|
drop sequence seq;
|
|
|
|
create temp sequence seq;
|
|
|
|
execute p2;
|
|
|
|
nextval
|
|
|
|
---------
|
|
|
|
1
|
|
|
|
(1 row)
|
|
|
|
|
2007-11-30 19:38:34 +01:00
|
|
|
-- Check DDL via SPI, immediately followed by SPI plan re-use
|
|
|
|
-- (bug in original coding)
|
|
|
|
create function cachebug() returns void as $$
|
|
|
|
declare r int;
|
|
|
|
begin
|
|
|
|
drop table if exists temptable cascade;
|
|
|
|
create temp table temptable as select * from generate_series(1,3) as f1;
|
|
|
|
create temp view vv as select * from temptable;
|
|
|
|
for r in select * from vv loop
|
|
|
|
raise notice '%', r;
|
|
|
|
end loop;
|
|
|
|
end$$ language plpgsql;
|
|
|
|
select cachebug();
|
|
|
|
NOTICE: table "temptable" does not exist, skipping
|
|
|
|
CONTEXT: SQL statement "drop table if exists temptable cascade"
|
|
|
|
PL/pgSQL function "cachebug" line 3 at SQL statement
|
|
|
|
NOTICE: 1
|
|
|
|
NOTICE: 2
|
|
|
|
NOTICE: 3
|
|
|
|
cachebug
|
|
|
|
----------
|
|
|
|
|
|
|
|
(1 row)
|
|
|
|
|
|
|
|
select cachebug();
|
|
|
|
NOTICE: drop cascades to view vv
|
|
|
|
CONTEXT: SQL statement "drop table if exists temptable cascade"
|
|
|
|
PL/pgSQL function "cachebug" line 3 at SQL statement
|
|
|
|
NOTICE: 1
|
|
|
|
NOTICE: 2
|
|
|
|
NOTICE: 3
|
|
|
|
cachebug
|
|
|
|
----------
|
|
|
|
|
|
|
|
(1 row)
|
|
|
|
|