Location via proxy:   [ UP ]  
[Report a bug]   [Manage cookies]                
Skip to content

PGPRO-8166: Fix build with vanilla at db93e739ac. #270

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 1 commit into from
Jun 22, 2023
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
203 changes: 203 additions & 0 deletions expected/pathman_column_type_2.out
Original file line number Diff line number Diff line change
@@ -0,0 +1,203 @@
/*
* In 9ce77d75c5a (>= 13) struct Var was changed, which caused the output
* of get_partition_cooked_key to change.
*/
\set VERBOSITY terse
SET search_path = 'public';
CREATE EXTENSION pg_pathman;
CREATE SCHEMA test_column_type;
/*
* RANGE partitioning.
*/
/* create new table (val int) */
CREATE TABLE test_column_type.test(val INT4 NOT NULL);
SELECT create_range_partitions('test_column_type.test', 'val', 1, 10, 10);
create_range_partitions
-------------------------
10
(1 row)

/* make sure that bounds and dispatch info has been cached */
SELECT * FROM test_column_type.test;
val
-----
(0 rows)

SELECT context, entries FROM pathman_cache_stats
WHERE context != 'partition status cache' ORDER BY context;
context | entries
-------------------------+---------
maintenance | 0
partition bounds cache | 10
partition parents cache | 10
(3 rows)

/*
* Get parsed and analyzed expression.
*/
CREATE FUNCTION get_cached_partition_cooked_key(REGCLASS)
RETURNS TEXT AS 'pg_pathman', 'get_cached_partition_cooked_key_pl'
LANGUAGE C STRICT;
SELECT get_partition_cooked_key('test_column_type.test'::REGCLASS);
get_partition_cooked_key
---------------------------------------------------------------------------------------------------------------------------------------------
{VAR :varno 1 :varattno 1 :vartype 23 :vartypmod -1 :varcollid 0 :varnullingrels (b) :varlevelsup 0 :varnosyn 1 :varattnosyn 1 :location 8}
(1 row)

SELECT get_cached_partition_cooked_key('test_column_type.test'::REGCLASS);
get_cached_partition_cooked_key
---------------------------------------------------------------------------------------------------------------------------------------------
{VAR :varno 1 :varattno 1 :vartype 23 :vartypmod -1 :varcollid 0 :varnullingrels (b) :varlevelsup 0 :varnosyn 1 :varattnosyn 1 :location 8}
(1 row)

SELECT get_partition_key_type('test_column_type.test'::REGCLASS);
get_partition_key_type
------------------------
integer
(1 row)

/* change column's type (should also flush caches) */
ALTER TABLE test_column_type.test ALTER val TYPE NUMERIC;
/* check that correct expression has been built */
SELECT get_partition_key_type('test_column_type.test'::REGCLASS);
get_partition_key_type
------------------------
numeric
(1 row)

SELECT get_partition_cooked_key('test_column_type.test'::REGCLASS);
get_partition_cooked_key
-----------------------------------------------------------------------------------------------------------------------------------------------
{VAR :varno 1 :varattno 1 :vartype 1700 :vartypmod -1 :varcollid 0 :varnullingrels (b) :varlevelsup 0 :varnosyn 1 :varattnosyn 1 :location 8}
(1 row)

SELECT get_cached_partition_cooked_key('test_column_type.test'::REGCLASS);
get_cached_partition_cooked_key
-----------------------------------------------------------------------------------------------------------------------------------------------
{VAR :varno 1 :varattno 1 :vartype 1700 :vartypmod -1 :varcollid 0 :varnullingrels (b) :varlevelsup 0 :varnosyn 1 :varattnosyn 1 :location 8}
(1 row)

DROP FUNCTION get_cached_partition_cooked_key(REGCLASS);
/* make sure that everything works properly */
SELECT * FROM test_column_type.test;
val
-----
(0 rows)

SELECT context, entries FROM pathman_cache_stats
WHERE context != 'partition status cache' ORDER BY context;
context | entries
-------------------------+---------
maintenance | 0
partition bounds cache | 10
partition parents cache | 10
(3 rows)

/* check insert dispatching */
INSERT INTO test_column_type.test VALUES (1);
SELECT tableoid::regclass, * FROM test_column_type.test;
tableoid | val
-------------------------+-----
test_column_type.test_1 | 1
(1 row)

SELECT drop_partitions('test_column_type.test');
NOTICE: 1 rows copied from test_column_type.test_1
NOTICE: 0 rows copied from test_column_type.test_2
NOTICE: 0 rows copied from test_column_type.test_3
NOTICE: 0 rows copied from test_column_type.test_4
NOTICE: 0 rows copied from test_column_type.test_5
NOTICE: 0 rows copied from test_column_type.test_6
NOTICE: 0 rows copied from test_column_type.test_7
NOTICE: 0 rows copied from test_column_type.test_8
NOTICE: 0 rows copied from test_column_type.test_9
NOTICE: 0 rows copied from test_column_type.test_10
drop_partitions
-----------------
10
(1 row)

DROP TABLE test_column_type.test CASCADE;
/*
* HASH partitioning.
*/
/* create new table (id int, val int) */
CREATE TABLE test_column_type.test(id INT4 NOT NULL, val INT4);
SELECT create_hash_partitions('test_column_type.test', 'id', 5);
create_hash_partitions
------------------------
5
(1 row)

/* make sure that bounds and dispatch info has been cached */
SELECT * FROM test_column_type.test;
id | val
----+-----
(0 rows)

SELECT context, entries FROM pathman_cache_stats
WHERE context != 'partition status cache' ORDER BY context;
context | entries
-------------------------+---------
maintenance | 0
partition bounds cache | 5
partition parents cache | 5
(3 rows)

/* change column's type (should NOT work) */
ALTER TABLE test_column_type.test ALTER id TYPE NUMERIC;
ERROR: cannot change type of column "id" of table "test" partitioned by HASH
/* make sure that everything works properly */
SELECT * FROM test_column_type.test;
id | val
----+-----
(0 rows)

SELECT context, entries FROM pathman_cache_stats
WHERE context != 'partition status cache' ORDER BY context;
context | entries
-------------------------+---------
maintenance | 0
partition bounds cache | 5
partition parents cache | 5
(3 rows)

/* change column's type (should flush caches) */
ALTER TABLE test_column_type.test ALTER val TYPE NUMERIC;
/* make sure that everything works properly */
SELECT * FROM test_column_type.test;
id | val
----+-----
(0 rows)

SELECT context, entries FROM pathman_cache_stats
WHERE context != 'partition status cache' ORDER BY context;
context | entries
-------------------------+---------
maintenance | 0
partition bounds cache | 5
partition parents cache | 5
(3 rows)

/* check insert dispatching */
INSERT INTO test_column_type.test VALUES (1);
SELECT tableoid::regclass, * FROM test_column_type.test;
tableoid | id | val
-------------------------+----+-----
test_column_type.test_0 | 1 |
(1 row)

SELECT drop_partitions('test_column_type.test');
NOTICE: 1 rows copied from test_column_type.test_0
NOTICE: 0 rows copied from test_column_type.test_1
NOTICE: 0 rows copied from test_column_type.test_2
NOTICE: 0 rows copied from test_column_type.test_3
NOTICE: 0 rows copied from test_column_type.test_4
drop_partitions
-----------------
5
(1 row)

DROP TABLE test_column_type.test CASCADE;
DROP SCHEMA test_column_type;
DROP EXTENSION pg_pathman;
160 changes: 160 additions & 0 deletions expected/pathman_join_clause_5.out
Original file line number Diff line number Diff line change
@@ -0,0 +1,160 @@
/*
* Since 8edd0e794 (>= 12) Append nodes with single subplan are eliminated,
* causing different output; pathman_gaps_1.out is the updated version.
*/
\set VERBOSITY terse
SET search_path = 'public';
CREATE SCHEMA pathman;
CREATE EXTENSION pg_pathman SCHEMA pathman;
CREATE SCHEMA test;
/*
* Test push down a join clause into child nodes of append
*/
/* create test tables */
CREATE TABLE test.fk (
id1 INT NOT NULL,
id2 INT NOT NULL,
start_key INT,
end_key INT,
PRIMARY KEY (id1, id2));
CREATE TABLE test.mytbl (
id1 INT NOT NULL,
id2 INT NOT NULL,
key INT NOT NULL,
CONSTRAINT fk_fk FOREIGN KEY (id1, id2) REFERENCES test.fk(id1, id2),
PRIMARY KEY (id1, key));
SELECT pathman.create_hash_partitions('test.mytbl', 'id1', 8);
create_hash_partitions
------------------------
8
(1 row)

/* ...fill out with test data */
INSERT INTO test.fk VALUES (1, 1);
INSERT INTO test.mytbl VALUES (1, 1, 5), (1, 1, 6);
/* gather statistics on test tables to have deterministic plans */
ANALYZE;
/* run test queries */
EXPLAIN (COSTS OFF) /* test plan */
SELECT m.tableoid::regclass, id1, id2, key, start_key, end_key
FROM test.mytbl m JOIN test.fk USING(id1, id2)
WHERE NOT key <@ int4range(6, end_key);
QUERY PLAN
-------------------------------------------------------------------------------------------------------
Nested Loop
-> Seq Scan on fk
-> Custom Scan (RuntimeAppend)
Prune by: (m.id1 = fk.id1)
-> Seq Scan on mytbl_0 m
Filter: ((id1 = fk.id1) AND (fk.id2 = id2) AND (NOT (key <@ int4range(6, fk.end_key))))
-> Seq Scan on mytbl_1 m
Filter: ((id1 = fk.id1) AND (fk.id2 = id2) AND (NOT (key <@ int4range(6, fk.end_key))))
-> Seq Scan on mytbl_2 m
Filter: ((id1 = fk.id1) AND (fk.id2 = id2) AND (NOT (key <@ int4range(6, fk.end_key))))
-> Seq Scan on mytbl_3 m
Filter: ((id1 = fk.id1) AND (fk.id2 = id2) AND (NOT (key <@ int4range(6, fk.end_key))))
-> Seq Scan on mytbl_4 m
Filter: ((id1 = fk.id1) AND (fk.id2 = id2) AND (NOT (key <@ int4range(6, fk.end_key))))
-> Seq Scan on mytbl_5 m
Filter: ((id1 = fk.id1) AND (fk.id2 = id2) AND (NOT (key <@ int4range(6, fk.end_key))))
-> Seq Scan on mytbl_6 m
Filter: ((id1 = fk.id1) AND (fk.id2 = id2) AND (NOT (key <@ int4range(6, fk.end_key))))
-> Seq Scan on mytbl_7 m
Filter: ((id1 = fk.id1) AND (fk.id2 = id2) AND (NOT (key <@ int4range(6, fk.end_key))))
(20 rows)

/* test joint data */
SELECT m.tableoid::regclass, id1, id2, key, start_key, end_key
FROM test.mytbl m JOIN test.fk USING(id1, id2)
WHERE NOT key <@ int4range(6, end_key);
tableoid | id1 | id2 | key | start_key | end_key
--------------+-----+-----+-----+-----------+---------
test.mytbl_6 | 1 | 1 | 5 | |
(1 row)

/*
* Test case by @dimarick
*/
CREATE TABLE test.parent (
id SERIAL NOT NULL,
owner_id INTEGER NOT NULL
);
CREATE TABLE test.child (
parent_id INTEGER NOT NULL,
owner_id INTEGER NOT NULL
);
CREATE TABLE test.child_nopart (
parent_id INTEGER NOT NULL,
owner_id INTEGER NOT NULL
);
INSERT INTO test.parent (owner_id) VALUES (1), (2), (3), (3);
INSERT INTO test.child (parent_id, owner_id) VALUES (1, 1), (2, 2), (3, 3), (5, 3);
INSERT INTO test.child_nopart (parent_id, owner_id) VALUES (1, 1), (2, 2), (3, 3), (5, 3);
SELECT pathman.create_hash_partitions('test.child', 'owner_id', 2);
create_hash_partitions
------------------------
2
(1 row)

/* gather statistics on test tables to have deterministic plans */
ANALYZE;
/* Query #1 */
EXPLAIN (COSTS OFF) SELECT * FROM test.parent
LEFT JOIN test.child ON test.child.parent_id = test.parent.id AND
test.child.owner_id = test.parent.owner_id
WHERE test.parent.owner_id = 3 and test.parent.id IN (3, 4);
QUERY PLAN
----------------------------------------------------------------------
Nested Loop Left Join
Join Filter: (child.parent_id = parent.id)
-> Seq Scan on parent
Filter: ((id = ANY ('{3,4}'::integer[])) AND (owner_id = 3))
-> Seq Scan on child_1 child
Filter: (owner_id = 3)
(6 rows)

SELECT * FROM test.parent
LEFT JOIN test.child ON test.child.parent_id = test.parent.id AND
test.child.owner_id = test.parent.owner_id
WHERE test.parent.owner_id = 3 and test.parent.id IN (3, 4);
id | owner_id | parent_id | owner_id
----+----------+-----------+----------
3 | 3 | 3 | 3
4 | 3 | |
(2 rows)

/* Query #2 */
EXPLAIN (COSTS OFF) SELECT * FROM test.parent
LEFT JOIN test.child ON test.child.parent_id = test.parent.id AND
test.child.owner_id = 3
WHERE test.parent.owner_id = 3 and test.parent.id IN (3, 4);
QUERY PLAN
----------------------------------------------------------------------
Nested Loop Left Join
Join Filter: (child.parent_id = parent.id)
-> Seq Scan on parent
Filter: ((id = ANY ('{3,4}'::integer[])) AND (owner_id = 3))
-> Seq Scan on child_1 child
Filter: (owner_id = 3)
(6 rows)

SELECT * FROM test.parent
LEFT JOIN test.child ON test.child.parent_id = test.parent.id AND
test.child.owner_id = 3
WHERE test.parent.owner_id = 3 and test.parent.id IN (3, 4);
id | owner_id | parent_id | owner_id
----+----------+-----------+----------
3 | 3 | 3 | 3
4 | 3 | |
(2 rows)

DROP TABLE test.child CASCADE;
NOTICE: drop cascades to 2 other objects
DROP TABLE test.child_nopart CASCADE;
DROP TABLE test.mytbl CASCADE;
NOTICE: drop cascades to 8 other objects
DROP TABLE test.fk CASCADE;
DROP TABLE test.parent CASCADE;
DROP SCHEMA test;
DROP EXTENSION pg_pathman CASCADE;
DROP SCHEMA pathman;
8 changes: 4 additions & 4 deletions src/hooks.c
Original file line number Diff line number Diff line change
Expand Up @@ -449,12 +449,12 @@ pathman_rel_pathlist_hook(PlannerInfo *root,
tce = lookup_type_cache(prel->ev_type, TYPECACHE_LT_OPR | TYPECACHE_GT_OPR);

/* Make pathkeys */
pathkeys = build_expression_pathkey(root, (Expr *) part_expr, NULL,
tce->lt_opr, NULL, false);
pathkeys = build_expression_pathkey_compat(root, (Expr *) part_expr, NULL,
tce->lt_opr, NULL, false);
if (pathkeys)
pathkeyAsc = (PathKey *) linitial(pathkeys);
pathkeys = build_expression_pathkey(root, (Expr *) part_expr, NULL,
tce->gt_opr, NULL, false);
pathkeys = build_expression_pathkey_compat(root, (Expr *) part_expr, NULL,
tce->gt_opr, NULL, false);
if (pathkeys)
pathkeyDesc = (PathKey *) linitial(pathkeys);
}
Expand Down
Loading