You can subscribe to this list here.
2010 |
Jan
|
Feb
|
Mar
|
Apr
(4) |
May
(28) |
Jun
(12) |
Jul
(11) |
Aug
(12) |
Sep
(5) |
Oct
(19) |
Nov
(14) |
Dec
(12) |
---|---|---|---|---|---|---|---|---|---|---|---|---|
2011 |
Jan
(18) |
Feb
(30) |
Mar
(115) |
Apr
(89) |
May
(50) |
Jun
(44) |
Jul
(22) |
Aug
(13) |
Sep
(11) |
Oct
(30) |
Nov
(28) |
Dec
(39) |
2012 |
Jan
(38) |
Feb
(18) |
Mar
(43) |
Apr
(91) |
May
(108) |
Jun
(46) |
Jul
(37) |
Aug
(44) |
Sep
(33) |
Oct
(29) |
Nov
(36) |
Dec
(15) |
2013 |
Jan
(35) |
Feb
(611) |
Mar
(5) |
Apr
(55) |
May
(30) |
Jun
(28) |
Jul
(458) |
Aug
(34) |
Sep
(9) |
Oct
(39) |
Nov
(22) |
Dec
(32) |
2014 |
Jan
(16) |
Feb
(16) |
Mar
(42) |
Apr
(179) |
May
(7) |
Jun
(6) |
Jul
(9) |
Aug
|
Sep
(4) |
Oct
|
Nov
(3) |
Dec
|
2015 |
Jan
|
Feb
|
Mar
|
Apr
(2) |
May
(4) |
Jun
|
Jul
|
Aug
|
Sep
|
Oct
|
Nov
|
Dec
|
S | M | T | W | T | F | S |
---|---|---|---|---|---|---|
|
|
1
(3) |
2
(5) |
3
|
4
(4) |
5
|
6
|
7
(7) |
8
(10) |
9
(6) |
10
(5) |
11
(1) |
12
|
13
|
14
|
15
|
16
|
17
(4) |
18
(1) |
19
|
20
|
21
(5) |
22
(15) |
23
(18) |
24
(7) |
25
(4) |
26
|
27
|
28
(3) |
29
(2) |
30
(11) |
31
(4) |
|
|
From: Michael P. <mic...@us...> - 2011-03-25 17:11:16
|
Project "Postgres-XC". The branch, merge_postgres_9_0_3 has been updated via 4f1d506fd83393fbbe98797fa49e862b5b17f19e (commit) from 796bf6e4b113d356b7d725daa71d62835faf9c68 (commit) - Log ----------------------------------------------------------------- commit 4f1d506fd83393fbbe98797fa49e862b5b17f19e Author: Michael P <mic...@us...> Date: Sat Mar 26 02:09:57 2011 +0900 Fix for regression test privileges Postgres-XC does not support yet TEMP tables and non-immutable functions, so this output is correct. diff --git a/src/test/regress/expected/privileges_1.out b/src/test/regress/expected/privileges_1.out new file mode 100644 index 0000000..90043e4 --- /dev/null +++ b/src/test/regress/expected/privileges_1.out @@ -0,0 +1,1310 @@ +-- +-- Test access privileges +-- +-- Clean up in case a prior regression run failed +-- Suppress NOTICE messages when users/groups don't exist +SET client_min_messages TO 'warning'; +DROP ROLE IF EXISTS regressgroup1; +DROP ROLE IF EXISTS regressgroup2; +DROP ROLE IF EXISTS regressuser1; +DROP ROLE IF EXISTS regressuser2; +DROP ROLE IF EXISTS regressuser3; +DROP ROLE IF EXISTS regressuser4; +DROP ROLE IF EXISTS regressuser5; +DROP ROLE IF EXISTS regressuser6; +SELECT lo_unlink(oid) FROM pg_largeobject_metadata; + lo_unlink +----------- +(0 rows) + +RESET client_min_messages; +-- test proper begins here +CREATE USER regressuser1; +CREATE USER regressuser2; +CREATE USER regressuser3; +CREATE USER regressuser4; +CREATE USER regressuser5; +CREATE USER regressuser5; -- duplicate +ERROR: role "regressuser5" already exists +CREATE GROUP regressgroup1; +CREATE GROUP regressgroup2 WITH USER regressuser1, regressuser2; +ALTER GROUP regressgroup1 ADD USER regressuser4; +ALTER GROUP regressgroup2 ADD USER regressuser2; -- duplicate +NOTICE: role "regressuser2" is already a member of role "regressgroup2" +ALTER GROUP regressgroup2 DROP USER regressuser2; +ALTER GROUP regressgroup2 ADD USER regressuser4; +-- test owner privileges +SET SESSION AUTHORIZATION regressuser1; +SELECT session_user, current_user; + session_user | current_user +--------------+-------------- + regressuser1 | regressuser1 +(1 row) + +CREATE TABLE atest1 ( a int, b text ); +SELECT * FROM atest1; + a | b +---+--- +(0 rows) + +INSERT INTO atest1 VALUES (1, 'one'); +DELETE FROM atest1; +UPDATE atest1 SET a = 1 WHERE b = 'blech'; +ERROR: Partition column can't be updated in current version +TRUNCATE atest1; +BEGIN; +LOCK atest1 IN ACCESS EXCLUSIVE MODE; +COMMIT; +REVOKE ALL ON atest1 FROM PUBLIC; +SELECT * FROM atest1; + a | b +---+--- +(0 rows) + +GRANT ALL ON atest1 TO regressuser2; +GRANT SELECT ON atest1 TO regressuser3, regressuser4; +SELECT * FROM atest1; + a | b +---+--- +(0 rows) + +CREATE TABLE atest2 (col1 varchar(10), col2 boolean); +GRANT SELECT ON atest2 TO regressuser2; +GRANT UPDATE ON atest2 TO regressuser3; +GRANT INSERT ON atest2 TO regressuser4; +GRANT TRUNCATE ON atest2 TO regressuser5; +SET SESSION AUTHORIZATION regressuser2; +SELECT session_user, current_user; + session_user | current_user +--------------+-------------- + regressuser2 | regressuser2 +(1 row) + +-- try various combinations of queries on atest1 and atest2 +SELECT * FROM atest1; -- ok + a | b +---+--- +(0 rows) + +SELECT * FROM atest2; -- ok + col1 | col2 +------+------ +(0 rows) + +INSERT INTO atest1 VALUES (2, 'two'); -- ok +INSERT INTO atest2 VALUES ('foo', true); -- fail +ERROR: permission denied for relation atest2 +INSERT INTO atest1 SELECT 1, b FROM atest1; -- ok +UPDATE atest1 SET a = 1 WHERE a = 2; -- ok +ERROR: Partition column can't be updated in current version +UPDATE atest2 SET col2 = NOT col2; -- fail +ERROR: permission denied for relation atest2 +SELECT * FROM atest1 FOR UPDATE; -- ok + a | b +---+----- + 2 | two +(1 row) + +SELECT * FROM atest2 FOR UPDATE; -- fail +ERROR: permission denied for relation atest2 +DELETE FROM atest2; -- fail +ERROR: permission denied for relation atest2 +TRUNCATE atest2; -- fail +ERROR: permission denied for relation atest2 +BEGIN; +LOCK atest2 IN ACCESS EXCLUSIVE MODE; -- fail +ERROR: permission denied for relation atest2 +COMMIT; +COPY atest2 FROM stdin; -- fail +ERROR: permission denied for relation atest2 +GRANT ALL ON atest1 TO PUBLIC; -- fail +WARNING: no privileges were granted for "atest1" +-- checks in subquery, both ok +SELECT * FROM atest1 WHERE ( b IN ( SELECT col1 FROM atest2 ) ); + a | b +---+--- +(0 rows) + +SELECT * FROM atest2 WHERE ( col1 IN ( SELECT b FROM atest1 ) ); + col1 | col2 +------+------ +(0 rows) + +SET SESSION AUTHORIZATION regressuser3; +SELECT session_user, current_user; + session_user | current_user +--------------+-------------- + regressuser3 | regressuser3 +(1 row) + +SELECT * FROM atest1; -- ok + a | b +---+----- + 2 | two +(1 row) + +SELECT * FROM atest2; -- fail +ERROR: permission denied for relation atest2 +INSERT INTO atest1 VALUES (2, 'two'); -- fail +ERROR: permission denied for relation atest1 +INSERT INTO atest2 VALUES ('foo', true); -- fail +ERROR: permission denied for relation atest2 +INSERT INTO atest1 SELECT 1, b FROM atest1; -- fail +ERROR: permission denied for relation atest1 +UPDATE atest1 SET a = 1 WHERE a = 2; -- fail +ERROR: Partition column can't be updated in current version +UPDATE atest2 SET col2 = NULL; -- ok +UPDATE atest2 SET col2 = NOT col2; -- fails; requires SELECT on atest2 +ERROR: permission denied for relation atest2 +UPDATE atest2 SET col2 = true FROM atest1 WHERE atest1.a = 5; -- ok +SELECT * FROM atest1 FOR UPDATE; -- fail +ERROR: permission denied for relation atest1 +SELECT * FROM atest2 FOR UPDATE; -- fail +ERROR: permission denied for relation atest2 +DELETE FROM atest2; -- fail +ERROR: permission denied for relation atest2 +TRUNCATE atest2; -- fail +ERROR: permission denied for relation atest2 +BEGIN; +LOCK atest2 IN ACCESS EXCLUSIVE MODE; -- ok +COMMIT; +COPY atest2 FROM stdin; -- fail +ERROR: permission denied for relation atest2 +-- checks in subquery, both fail +SELECT * FROM atest1 WHERE ( b IN ( SELECT col1 FROM atest2 ) ); +ERROR: permission denied for relation atest2 +SELECT * FROM atest2 WHERE ( col1 IN ( SELECT b FROM atest1 ) ); +ERROR: permission denied for relation atest2 +SET SESSION AUTHORIZATION regressuser4; +COPY atest2 FROM stdin; -- ok +SELECT * FROM atest1; -- ok + a | b +---+----- + 2 | two +(1 row) + +-- groups +SET SESSION AUTHORIZATION regressuser3; +CREATE TABLE atest3 (one int, two int, three int); +GRANT DELETE ON atest3 TO GROUP regressgroup2; +SET SESSION AUTHORIZATION regressuser1; +SELECT * FROM atest3; -- fail +ERROR: permission denied for relation atest3 +DELETE FROM atest3; -- ok +-- views +SET SESSION AUTHORIZATION regressuser3; +CREATE VIEW atestv1 AS SELECT * FROM atest1; -- ok +/* The next *should* fail, but it's not implemented that way yet. */ +CREATE VIEW atestv2 AS SELECT * FROM atest2; +CREATE VIEW atestv3 AS SELECT * FROM atest3; -- ok +SELECT * FROM atestv1; -- ok + a | b +---+----- + 2 | two +(1 row) + +SELECT * FROM atestv2; -- fail +ERROR: permission denied for relation atest2 +GRANT SELECT ON atestv1, atestv3 TO regressuser4; +GRANT SELECT ON atestv2 TO regressuser2; +SET SESSION AUTHORIZATION regressuser4; +SELECT * FROM atestv1; -- ok + a | b +---+----- + 2 | two +(1 row) + +SELECT * FROM atestv2; -- fail +ERROR: permission denied for relation atestv2 +SELECT * FROM atestv3; -- ok + one | two | three +-----+-----+------- +(0 rows) + +CREATE VIEW atestv4 AS SELECT * FROM atestv3; -- nested view +SELECT * FROM atestv4; -- ok + one | two | three +-----+-----+------- +(0 rows) + +GRANT SELECT ON atestv4 TO regressuser2; +SET SESSION AUTHORIZATION regressuser2; +-- Two complex cases: +SELECT * FROM atestv3; -- fail +ERROR: permission denied for relation atestv3 +SELECT * FROM atestv4; -- ok (even though regressuser2 cannot access underlying atestv3) + one | two | three +-----+-----+------- +(0 rows) + +SELECT * FROM atest2; -- ok + col1 | col2 +------+------ + bar | t +(1 row) + +SELECT * FROM atestv2; -- fail (even though regressuser2 can access underlying atest2) +ERROR: permission denied for relation atest2 +-- Test column level permissions +SET SESSION AUTHORIZATION regressuser1; +CREATE TABLE atest5 (one int, two int, three int); +CREATE TABLE atest6 (one int, two int, blue int); +GRANT SELECT (one), INSERT (two), UPDATE (three) ON atest5 TO regressuser4; +GRANT ALL (one) ON atest5 TO regressuser3; +INSERT INTO atest5 VALUES (1,2,3); +SET SESSION AUTHORIZATION regressuser4; +SELECT * FROM atest5; -- fail +ERROR: permission denied for relation atest5 +SELECT one FROM atest5; -- ok + one +----- + 1 +(1 row) + +COPY atest5 (one) TO stdout; -- ok +1 +SELECT two FROM atest5; -- fail +ERROR: permission denied for relation atest5 +COPY atest5 (two) TO stdout; -- fail +ERROR: permission denied for relation atest5 +SELECT atest5 FROM atest5; -- fail +ERROR: permission denied for relation atest5 +COPY atest5 (one,two) TO stdout; -- fail +ERROR: permission denied for relation atest5 +SELECT 1 FROM atest5; -- ok + ?column? +---------- + 1 +(1 row) + +SELECT 1 FROM atest5 a JOIN atest5 b USING (one); -- ok + ?column? +---------- + 1 +(1 row) + +SELECT 1 FROM atest5 a JOIN atest5 b USING (two); -- fail +ERROR: permission denied for relation atest5 +SELECT 1 FROM atest5 a NATURAL JOIN atest5 b; -- fail +ERROR: permission denied for relation atest5 +SELECT (j.*) IS NULL FROM (atest5 a JOIN atest5 b USING (one)) j; -- fail +ERROR: permission denied for relation atest5 +SELECT 1 FROM atest5 WHERE two = 2; -- fail +ERROR: permission denied for relation atest5 +SELECT * FROM atest1, atest5; -- fail +ERROR: permission denied for relation atest5 +SELECT atest1.* FROM atest1, atest5; -- ok + a | b +---+----- + 2 | two +(1 row) + +SELECT atest1.*,atest5.one FROM atest1, atest5; -- ok + a | b | one +---+-----+----- + 2 | two | 1 +(1 row) + +SELECT atest1.*,atest5.one FROM atest1 JOIN atest5 ON (atest1.a = atest5.two); -- fail +ERROR: permission denied for relation atest5 +SELECT atest1.*,atest5.one FROM atest1 JOIN atest5 ON (atest1.a = atest5.one); -- ok + a | b | one +---+---+----- +(0 rows) + +SELECT one, two FROM atest5; -- fail +ERROR: permission denied for relation atest5 +SET SESSION AUTHORIZATION regressuser1; +GRANT SELECT (one,two) ON atest6 TO regressuser4; +SET SESSION AUTHORIZATION regressuser4; +SELECT one, two FROM atest5 NATURAL JOIN atest6; -- fail still +ERROR: permission denied for relation atest5 +SET SESSION AUTHORIZATION regressuser1; +GRANT SELECT (two) ON atest5 TO regressuser4; +SET SESSION AUTHORIZATION regressuser4; +SELECT one, two FROM atest5 NATURAL JOIN atest6; -- ok now + one | two +-----+----- +(0 rows) + +-- test column-level privileges for INSERT and UPDATE +INSERT INTO atest5 (two) VALUES (3); -- ok +COPY atest5 FROM stdin; -- fail +ERROR: permission denied for relation atest5 +COPY atest5 (two) FROM stdin; -- ok +INSERT INTO atest5 (three) VALUES (4); -- fail +ERROR: permission denied for relation atest5 +INSERT INTO atest5 VALUES (5,5,5); -- fail +ERROR: permission denied for relation atest5 +UPDATE atest5 SET three = 10; -- ok +UPDATE atest5 SET one = 8; -- fail +ERROR: Partition column can't be updated in current version +UPDATE atest5 SET three = 5, one = 2; -- fail +ERROR: Partition column can't be updated in current version +SET SESSION AUTHORIZATION regressuser1; +REVOKE ALL (one) ON atest5 FROM regressuser4; +GRANT SELECT (one,two,blue) ON atest6 TO regressuser4; +SET SESSION AUTHORIZATION regressuser4; +SELECT one FROM atest5; -- fail +ERROR: permission denied for relation atest5 +UPDATE atest5 SET one = 1; -- fail +ERROR: Partition column can't be updated in current version +SELECT atest6 FROM atest6; -- ok + atest6 +-------- +(0 rows) + +COPY atest6 TO stdout; -- ok +-- test column-level privileges when involved with DELETE +SET SESSION AUTHORIZATION regressuser1; +ALTER TABLE atest6 ADD COLUMN three integer; +GRANT DELETE ON atest5 TO regressuser3; +GRANT SELECT (two) ON atest5 TO regressuser3; +REVOKE ALL (one) ON atest5 FROM regressuser3; +GRANT SELECT (one) ON atest5 TO regressuser4; +SET SESSION AUTHORIZATION regressuser4; +SELECT atest6 FROM atest6; -- fail +ERROR: permission denied for relation atest6 +SELECT one FROM atest5 NATURAL JOIN atest6; -- fail +ERROR: permission denied for relation atest5 +SET SESSION AUTHORIZATION regressuser1; +ALTER TABLE atest6 DROP COLUMN three; +SET SESSION AUTHORIZATION regressuser4; +SELECT atest6 FROM atest6; -- ok + atest6 +-------- +(0 rows) + +SELECT one FROM atest5 NATURAL JOIN atest6; -- ok + one +----- +(0 rows) + +SET SESSION AUTHORIZATION regressuser1; +ALTER TABLE atest6 DROP COLUMN two; +REVOKE SELECT (one,blue) ON atest6 FROM regressuser4; +SET SESSION AUTHORIZATION regressuser4; +SELECT * FROM atest6; -- fail +ERROR: permission denied for relation atest6 +SELECT 1 FROM atest6; -- fail +ERROR: permission denied for relation atest6 +SET SESSION AUTHORIZATION regressuser3; +DELETE FROM atest5 WHERE one = 1; -- fail +ERROR: permission denied for relation atest5 +DELETE FROM atest5 WHERE two = 2; -- ok +-- check inheritance cases +SET SESSION AUTHORIZATION regressuser1; +CREATE TABLE atestp1 (f1 int, f2 int) WITH OIDS; +CREATE TABLE atestp2 (fx int, fy int) WITH OIDS; +CREATE TABLE atestc (fz int) INHERITS (atestp1, atestp2); +ERROR: Cannot currently distribute a table with more than one parent. +GRANT SELECT(fx,fy,oid) ON atestp2 TO regressuser2; +GRANT SELECT(fx) ON atestc TO regressuser2; +ERROR: relation "atestc" does not exist +SET SESSION AUTHORIZATION regressuser2; +SELECT fx FROM atestp2; -- ok + fx +---- +(0 rows) + +SELECT fy FROM atestp2; -- ok + fy +---- +(0 rows) + +SELECT atestp2 FROM atestp2; -- ok + atestp2 +--------- +(0 rows) + +SELECT oid FROM atestp2; -- ok + oid +----- +(0 rows) + +SELECT fy FROM atestc; -- fail +ERROR: relation "atestc" does not exist +LINE 1: SELECT fy FROM atestc; + ^ +SET SESSION AUTHORIZATION regressuser1; +GRANT SELECT(fy,oid) ON atestc TO regressuser2; +ERROR: relation "atestc" does not exist +SET SESSION AUTHORIZATION regressuser2; +SELECT fx FROM atestp2; -- still ok + fx +---- +(0 rows) + +SELECT fy FROM atestp2; -- ok + fy +---- +(0 rows) + +SELECT atestp2 FROM atestp2; -- ok + atestp2 +--------- +(0 rows) + +SELECT oid FROM atestp2; -- ok + oid +----- +(0 rows) + +-- privileges on functions, languages +-- switch to superuser +\c - +REVOKE ALL PRIVILEGES ON LANGUAGE sql FROM PUBLIC; +GRANT USAGE ON LANGUAGE sql TO regressuser1; -- ok +GRANT USAGE ON LANGUAGE c TO PUBLIC; -- fail +ERROR: language "c" is not trusted +HINT: Only superusers can use untrusted languages. +SET SESSION AUTHORIZATION regressuser1; +GRANT USAGE ON LANGUAGE sql TO regressuser2; -- fail +WARNING: no privileges were granted for "sql" +CREATE FUNCTION testfunc1(int) RETURNS int AS 'select 2 * $1;' LANGUAGE sql; +ERROR: stable and volatile not yet supported, function volatility has to be immutable +CREATE FUNCTION testfunc2(int) RETURNS int AS 'select 3 * $1;' LANGUAGE sql; +ERROR: stable and volatile not yet supported, function volatility has to be immutable +REVOKE ALL ON FUNCTION testfunc1(int), testfunc2(int) FROM PUBLIC; +ERROR: function testfunc1(integer) does not exist +GRANT EXECUTE ON FUNCTION testfunc1(int), testfunc2(int) TO regressuser2; +ERROR: function testfunc1(integer) does not exist +GRANT USAGE ON FUNCTION testfunc1(int) TO regressuser3; -- semantic error +ERROR: function testfunc1(integer) does not exist +GRANT ALL PRIVILEGES ON FUNCTION testfunc1(int) TO regressuser4; +ERROR: function testfunc1(integer) does not exist +GRANT ALL PRIVILEGES ON FUNCTION testfunc_nosuch(int) TO regressuser4; +ERROR: function testfunc_nosuch(integer) does not exist +CREATE FUNCTION testfunc4(boolean) RETURNS text + AS 'select col1 from atest2 where col2 = $1;' + LANGUAGE sql SECURITY DEFINER; +ERROR: stable and volatile not yet supported, function volatility has to be immutable +GRANT EXECUTE ON FUNCTION testfunc4(boolean) TO regressuser3; +ERROR: function testfunc4(boolean) does not exist +SET SESSION AUTHORIZATION regressuser2; +SELECT testfunc1(5), testfunc2(5); -- ok +ERROR: function testfunc1(integer) does not exist +LINE 1: SELECT testfunc1(5), testfunc2(5); + ^ +HINT: No function matches the given name and argument types. You might need to add explicit type casts. +CREATE FUNCTION testfunc3(int) RETURNS int AS 'select 2 * $1;' LANGUAGE sql; -- fail +ERROR: permission denied for language sql +SET SESSION AUTHORIZATION regressuser3; +SELECT testfunc1(5); -- fail +ERROR: function testfunc1(integer) does not exist +LINE 1: SELECT testfunc1(5); + ^ +HINT: No function matches the given name and argument types. You might need to add explicit type casts. +SELECT col1 FROM atest2 WHERE col2 = true; -- fail +ERROR: permission denied for relation atest2 +SELECT testfunc4(true); -- ok +ERROR: function testfunc4(boolean) does not exist +LINE 1: SELECT testfunc4(true); + ^ +HINT: No function matches the given name and argument types. You might need to add explicit type casts. +SET SESSION AUTHORIZATION regressuser4; +SELECT testfunc1(5); -- ok +ERROR: function testfunc1(integer) does not exist +LINE 1: SELECT testfunc1(5); + ^ +HINT: No function matches the given name and argument types. You might need to add explicit type casts. +DROP FUNCTION testfunc1(int); -- fail +ERROR: function testfunc1(integer) does not exist +\c - +DROP FUNCTION testfunc1(int); -- ok +ERROR: function testfunc1(integer) does not exist +-- restore to sanity +GRANT ALL PRIVILEGES ON LANGUAGE sql TO PUBLIC; +-- truncate +SET SESSION AUTHORIZATION regressuser5; +TRUNCATE atest2; -- ok +TRUNCATE atest3; -- fail +ERROR: permission denied for relation atest3 +-- has_table_privilege function +-- bad-input checks +select has_table_privilege(NULL,'pg_authid','select'); + has_table_privilege +--------------------- + +(1 row) + +select has_table_privilege('pg_shad','select'); +ERROR: relation "pg_shad" does not exist +select has_table_privilege('nosuchuser','pg_authid','select'); +ERROR: role "nosuchuser" does not exist +select has_table_privilege('pg_authid','sel'); +ERROR: unrecognized privilege type: "sel" +select has_table_privilege(-999999,'pg_authid','update'); +ERROR: role with OID 4293967297 does not exist +select has_table_privilege(1,'select'); + has_table_privilege +--------------------- + +(1 row) + +-- superuser +\c - +select has_table_privilege(current_user,'pg_authid','select'); + has_table_privilege +--------------------- + t +(1 row) + +select has_table_privilege(current_user,'pg_authid','insert'); + has_table_privilege +--------------------- + t +(1 row) + +select has_table_privilege(t2.oid,'pg_authid','update') +from (select oid from pg_roles where rolname = current_user) as t2; + has_table_privilege +--------------------- + t +(1 row) + +select has_table_privilege(t2.oid,'pg_authid','delete') +from (select oid from pg_roles where rolname = current_user) as t2; + has_table_privilege +--------------------- + t +(1 row) + +-- 'rule' privilege no longer exists, but for backwards compatibility +-- has_table_privilege still recognizes the keyword and says FALSE +select has_table_privilege(current_user,t1.oid,'rule') +from (select oid from pg_class where relname = 'pg_authid') as t1; + has_table_privilege +--------------------- + f +(1 row) + +select has_table_privilege(current_user,t1.oid,'references') +from (select oid from pg_class where relname = 'pg_authid') as t1; + has_table_privilege +--------------------- + t +(1 row) + +select has_table_privilege(t2.oid,t1.oid,'select') +from (select oid from pg_class where relname = 'pg_authid') as t1, + (select oid from pg_roles where rolname = current_user) as t2; + has_table_privilege +--------------------- + t +(1 row) + +select has_table_privilege(t2.oid,t1.oid,'insert') +from (select oid from pg_class where relname = 'pg_authid') as t1, + (select oid from pg_roles where rolname = current_user) as t2; + has_table_privilege +--------------------- + t +(1 row) + +select has_table_privilege('pg_authid','update'); + has_table_privilege +--------------------- + t +(1 row) + +select has_table_privilege('pg_authid','delete'); + has_table_privilege +--------------------- + t +(1 row) + +select has_table_privilege('pg_authid','truncate'); + has_table_privilege +--------------------- + t +(1 row) + +select has_table_privilege(t1.oid,'select') +from (select oid from pg_class where relname = 'pg_authid') as t1; + has_table_privilege +--------------------- + t +(1 row) + +select has_table_privilege(t1.oid,'trigger') +from (select oid from pg_class where relname = 'pg_authid') as t1; + has_table_privilege +--------------------- + t +(1 row) + +-- non-superuser +SET SESSION AUTHORIZATION regressuser3; +select has_table_privilege(current_user,'pg_class','select'); + has_table_privilege +--------------------- + t +(1 row) + +select has_table_privilege(current_user,'pg_class','insert'); + has_table_privilege +--------------------- + f +(1 row) + +select has_table_privilege(t2.oid,'pg_class','update') +from (select oid from pg_roles where rolname = current_user) as t2; + has_table_privilege +--------------------- + f +(1 row) + +select has_table_privilege(t2.oid,'pg_class','delete') +from (select oid from pg_roles where rolname = current_user) as t2; + has_table_privilege +--------------------- + f +(1 row) + +select has_table_privilege(current_user,t1.oid,'references') +from (select oid from pg_class where relname = 'pg_class') as t1; + has_table_privilege +--------------------- + f +(1 row) + +select has_table_privilege(t2.oid,t1.oid,'select') +from (select oid from pg_class where relname = 'pg_class') as t1, + (select oid from pg_roles where rolname = current_user) as t2; + has_table_privilege +--------------------- + t +(1 row) + +select has_table_privilege(t2.oid,t1.oid,'insert') +from (select oid from pg_class where relname = 'pg_class') as t1, + (select oid from pg_roles where rolname = current_user) as t2; + has_table_privilege +--------------------- + f +(1 row) + +select has_table_privilege('pg_class','update'); + has_table_privilege +--------------------- + f +(1 row) + +select has_table_privilege('pg_class','delete'); + has_table_privilege +--------------------- + f +(1 row) + +select has_table_privilege('pg_class','truncate'); + has_table_privilege +--------------------- + f +(1 row) + +select has_table_privilege(t1.oid,'select') +from (select oid from pg_class where relname = 'pg_class') as t1; + has_table_privilege +--------------------- + t +(1 row) + +select has_table_privilege(t1.oid,'trigger') +from (select oid from pg_class where relname = 'pg_class') as t1; + has_table_privilege +--------------------- + f +(1 row) + +select has_table_privilege(current_user,'atest1','select'); + has_table_privilege +--------------------- + t +(1 row) + +select has_table_privilege(current_user,'atest1','insert'); + has_table_privilege +--------------------- + f +(1 row) + +select has_table_privilege(t2.oid,'atest1','update') +from (select oid from pg_roles where rolname = current_user) as t2; + has_table_privilege +--------------------- + f +(1 row) + +select has_table_privilege(t2.oid,'atest1','delete') +from (select oid from pg_roles where rolname = current_user) as t2; + has_table_privilege +--------------------- + f +(1 row) + +select has_table_privilege(current_user,t1.oid,'references') +from (select oid from pg_class where relname = 'atest1') as t1; + has_table_privilege +--------------------- + f +(1 row) + +select has_table_privilege(t2.oid,t1.oid,'select') +from (select oid from pg_class where relname = 'atest1') as t1, + (select oid from pg_roles where rolname = current_user) as t2; + has_table_privilege +--------------------- + t +(1 row) + +select has_table_privilege(t2.oid,t1.oid,'insert') +from (select oid from pg_class where relname = 'atest1') as t1, + (select oid from pg_roles where rolname = current_user) as t2; + has_table_privilege +--------------------- + f +(1 row) + +select has_table_privilege('atest1','update'); + has_table_privilege +--------------------- + f +(1 row) + +select has_table_privilege('atest1','delete'); + has_table_privilege +--------------------- + f +(1 row) + +select has_table_privilege('atest1','truncate'); + has_table_privilege +--------------------- + f +(1 row) + +select has_table_privilege(t1.oid,'select') +from (select oid from pg_class where relname = 'atest1') as t1; + has_table_privilege +--------------------- + t +(1 row) + +select has_table_privilege(t1.oid,'trigger') +from (select oid from pg_class where relname = 'atest1') as t1; + has_table_privilege +--------------------- + f +(1 row) + +-- Grant options +SET SESSION AUTHORIZATION regressuser1; +CREATE TABLE atest4 (a int); +GRANT SELECT ON atest4 TO regressuser2 WITH GRANT OPTION; +GRANT UPDATE ON atest4 TO regressuser2; +GRANT SELECT ON atest4 TO GROUP regressgroup1 WITH GRANT OPTION; +SET SESSION AUTHORIZATION regressuser2; +GRANT SELECT ON atest4 TO regressuser3; +GRANT UPDATE ON atest4 TO regressuser3; -- fail +WARNING: no privileges were granted for "atest4" +SET SESSION AUTHORIZATION regressuser1; +REVOKE SELECT ON atest4 FROM regressuser3; -- does nothing +SELECT has_table_privilege('regressuser3', 'atest4', 'SELECT'); -- true + has_table_privilege +--------------------- + t +(1 row) + +REVOKE SELECT ON atest4 FROM regressuser2; -- fail +ERROR: dependent privileges exist +HINT: Use CASCADE to revoke them too. +REVOKE GRANT OPTION FOR SELECT ON atest4 FROM regressuser2 CASCADE; -- ok +SELECT has_table_privilege('regressuser2', 'atest4', 'SELECT'); -- true + has_table_privilege +--------------------- + t +(1 row) + +SELECT has_table_privilege('regressuser3', 'atest4', 'SELECT'); -- false + has_table_privilege +--------------------- + f +(1 row) + +SELECT has_table_privilege('regressuser1', 'atest4', 'SELECT WITH GRANT OPTION'); -- true + has_table_privilege +--------------------- + t +(1 row) + +-- has_sequence_privilege tests +\c - +CREATE SEQUENCE x_seq; +GRANT USAGE on x_seq to regressuser2; +SELECT has_sequence_privilege('regressuser1', 'atest1', 'SELECT'); +ERROR: "atest1" is not a sequence +SELECT has_sequence_privilege('regressuser1', 'x_seq', 'INSERT'); +ERROR: unrecognized privilege type: "INSERT" +SELECT has_sequence_privilege('regressuser1', 'x_seq', 'SELECT'); + has_sequence_privilege +------------------------ + f +(1 row) + +SET SESSION AUTHORIZATION regressuser2; +SELECT has_sequence_privilege('x_seq', 'USAGE'); + has_sequence_privilege +------------------------ + t +(1 row) + +-- largeobject privilege tests +\c - +SET SESSION AUTHORIZATION regressuser1; +SELECT lo_create(1001); + lo_create +----------- + 1001 +(1 row) + +SELECT lo_create(1002); + lo_create +----------- + 1002 +(1 row) + +SELECT lo_create(1003); + lo_create +----------- + 1003 +(1 row) + +SELECT lo_create(1004); + lo_create +----------- + 1004 +(1 row) + +SELECT lo_create(1005); + lo_create +----------- + 1005 +(1 row) + +GRANT ALL ON LARGE OBJECT 1001 TO PUBLIC; +GRANT SELECT ON LARGE OBJECT 1003 TO regressuser2; +GRANT SELECT,UPDATE ON LARGE OBJECT 1004 TO regressuser2; +GRANT ALL ON LARGE OBJECT 1005 TO regressuser2; +GRANT SELECT ON LARGE OBJECT 1005 TO regressuser2 WITH GRANT OPTION; +GRANT SELECT, INSERT ON LARGE OBJECT 1001 TO PUBLIC; -- to be failed +ERROR: invalid privilege type INSERT for large object +GRANT SELECT, UPDATE ON LARGE OBJECT 1001 TO nosuchuser; -- to be failed +ERROR: role "nosuchuser" does not exist +GRANT SELECT, UPDATE ON LARGE OBJECT 999 TO PUBLIC; -- to be failed +ERROR: large object 999 does not exist +\c - +SET SESSION AUTHORIZATION regressuser2; +SELECT lo_create(2001); + lo_create +----------- + 2001 +(1 row) + +SELECT lo_create(2002); + lo_create +----------- + 2002 +(1 row) + +SELECT loread(lo_open(1001, x'40000'::int), 32); + loread +-------- + \x +(1 row) + +SELECT loread(lo_open(1002, x'40000'::int), 32); -- to be denied +ERROR: permission denied for large object 1002 +SELECT loread(lo_open(1003, x'40000'::int), 32); + loread +-------- + \x +(1 row) + +SELECT loread(lo_open(1004, x'40000'::int), 32); + loread +-------- + \x +(1 row) + +SELECT lowrite(lo_open(1001, x'20000'::int), 'abcd'); + lowrite +--------- + 4 +(1 row) + +SELECT lowrite(lo_open(1002, x'20000'::int), 'abcd'); -- to be denied +ERROR: permission denied for large object 1002 +SELECT lowrite(lo_open(1003, x'20000'::int), 'abcd'); -- to be denied +ERROR: permission denied for large object 1003 +SELECT lowrite(lo_open(1004, x'20000'::int), 'abcd'); + lowrite +--------- + 4 +(1 row) + +GRANT SELECT ON LARGE OBJECT 1005 TO regressuser3; +GRANT UPDATE ON LARGE OBJECT 1006 TO regressuser3; -- to be denied +ERROR: large object 1006 does not exist +REVOKE ALL ON LARGE OBJECT 2001, 2002 FROM PUBLIC; +GRANT ALL ON LARGE OBJECT 2001 TO regressuser3; +SELECT lo_unlink(1001); -- to be denied +ERROR: must be owner of large object 1001 +SELECT lo_unlink(2002); + lo_unlink +----------- + 1 +(1 row) + +\c - +-- confirm ACL setting +SELECT oid, pg_get_userbyid(lomowner) ownername, lomacl FROM pg_largeobject_metadata; + oid | ownername | lomacl +------+--------------+------------------------------------------------------------------------------------------ + 1002 | regressuser1 | + 1001 | regressuser1 | {regressuser1=rw/regressuser1,=rw/regressuser1} + 1003 | regressuser1 | {regressuser1=rw/regressuser1,regressuser2=r/regressuser1} + 1004 | regressuser1 | {regressuser1=rw/regressuser1,regressuser2=rw/regressuser1} + 1005 | regressuser1 | {regressuser1=rw/regressuser1,regressuser2=r*w/regressuser1,regressuser3=r/regressuser2} + 2001 | regressuser2 | {regressuser2=rw/regressuser2,regressuser3=rw/regressuser2} +(6 rows) + +SET SESSION AUTHORIZATION regressuser3; +SELECT loread(lo_open(1001, x'40000'::int), 32); + loread +------------ + \x61626364 +(1 row) + +SELECT loread(lo_open(1003, x'40000'::int), 32); -- to be denied +ERROR: permission denied for large object 1003 +SELECT loread(lo_open(1005, x'40000'::int), 32); + loread +-------- + \x +(1 row) + +SELECT lo_truncate(lo_open(1005, x'20000'::int), 10); -- to be denied +ERROR: permission denied for large object 1005 +SELECT lo_truncate(lo_open(2001, x'20000'::int), 10); + lo_truncate +------------- + 0 +(1 row) + +-- compatibility mode in largeobject permission +\c - +SET lo_compat_privileges = false; -- default setting +SET SESSION AUTHORIZATION regressuser4; +SELECT loread(lo_open(1002, x'40000'::int), 32); -- to be denied +ERROR: permission denied for large object 1002 +SELECT lowrite(lo_open(1002, x'20000'::int), 'abcd'); -- to be denied +ERROR: permission denied for large object 1002 +SELECT lo_truncate(lo_open(1002, x'20000'::int), 10); -- to be denied +ERROR: permission denied for large object 1002 +SELECT lo_unlink(1002); -- to be denied +ERROR: must be owner of large object 1002 +SELECT lo_export(1001, '/dev/null'); -- to be denied +ERROR: must be superuser to use server-side lo_export() +HINT: Anyone can use the client-side lo_export() provided by libpq. +\c - +SET lo_compat_privileges = true; -- compatibility mode +SET SESSION AUTHORIZATION regressuser4; +SELECT loread(lo_open(1002, x'40000'::int), 32); + loread +-------- + \x +(1 row) + +SELECT lowrite(lo_open(1002, x'20000'::int), 'abcd'); + lowrite +--------- + 4 +(1 row) + +SELECT lo_truncate(lo_open(1002, x'20000'::int), 10); + lo_truncate +------------- + 0 +(1 row) + +SELECT lo_unlink(1002); + lo_unlink +----------- + 1 +(1 row) + +SELECT lo_export(1001, '/dev/null'); -- to be denied +ERROR: must be superuser to use server-side lo_export() +HINT: Anyone can use the client-side lo_export() provided by libpq. +-- don't allow unpriv users to access pg_largeobject contents +\c - +SELECT * FROM pg_largeobject LIMIT 0; + loid | pageno | data +------+--------+------ +(0 rows) + +SET SESSION AUTHORIZATION regressuser1; +SELECT * FROM pg_largeobject LIMIT 0; -- to be denied +ERROR: permission denied for relation pg_largeobject +-- test default ACLs +\c - +CREATE SCHEMA testns; +GRANT ALL ON SCHEMA testns TO regressuser1; +CREATE TABLE testns.acltest1 (x int); +SELECT has_table_privilege('regressuser1', 'testns.acltest1', 'SELECT'); -- no + has_table_privilege +--------------------- + f +(1 row) + +SELECT has_table_privilege('regressuser1', 'testns.acltest1', 'INSERT'); -- no + has_table_privilege +--------------------- + f +(1 row) + +ALTER DEFAULT PRIVILEGES IN SCHEMA testns GRANT SELECT ON TABLES TO public; +SELECT has_table_privilege('regressuser1', 'testns.acltest1', 'SELECT'); -- no + has_table_privilege +--------------------- + f +(1 row) + +SELECT has_table_privilege('regressuser1', 'testns.acltest1', 'INSERT'); -- no + has_table_privilege +--------------------- + f +(1 row) + +DROP TABLE testns.acltest1; +CREATE TABLE testns.acltest1 (x int); +SELECT has_table_privilege('regressuser1', 'testns.acltest1', 'SELECT'); -- yes + has_table_privilege +--------------------- + t +(1 row) + +SELECT has_table_privilege('regressuser1', 'testns.acltest1', 'INSERT'); -- no + has_table_privilege +--------------------- + f +(1 row) + +ALTER DEFAULT PRIVILEGES IN SCHEMA testns GRANT INSERT ON TABLES TO regressuser1; +DROP TABLE testns.acltest1; +CREATE TABLE testns.acltest1 (x int); +SELECT has_table_privilege('regressuser1', 'testns.acltest1', 'SELECT'); -- yes + has_table_privilege +--------------------- + t +(1 row) + +SELECT has_table_privilege('regressuser1', 'testns.acltest1', 'INSERT'); -- yes + has_table_privilege +--------------------- + t +(1 row) + +ALTER DEFAULT PRIVILEGES IN SCHEMA testns REVOKE INSERT ON TABLES FROM regressuser1; +DROP TABLE testns.acltest1; +CREATE TABLE testns.acltest1 (x int); +SELECT has_table_privilege('regressuser1', 'testns.acltest1', 'SELECT'); -- yes + has_table_privilege +--------------------- + t +(1 row) + +SELECT has_table_privilege('regressuser1', 'testns.acltest1', 'INSERT'); -- no + has_table_privilege +--------------------- + f +(1 row) + +ALTER DEFAULT PRIVILEGES FOR ROLE regressuser1 REVOKE EXECUTE ON FUNCTIONS FROM public; +SET ROLE regressuser1; +CREATE FUNCTION testns.foo() RETURNS int AS 'select 1' LANGUAGE sql; +ERROR: stable and volatile not yet supported, function volatility has to be immutable +SELECT has_function_privilege('regressuser2', 'testns.foo()', 'EXECUTE'); -- no +ERROR: function "testns.foo()" does not exist +ALTER DEFAULT PRIVILEGES IN SCHEMA testns GRANT EXECUTE ON FUNCTIONS to public; +DROP FUNCTION testns.foo(); +ERROR: function testns.foo() does not exist +CREATE FUNCTION testns.foo() RETURNS int AS 'select 1' LANGUAGE sql; +ERROR: stable and volatile not yet supported, function volatility has to be immutable +SELECT has_function_privilege('regressuser2', 'testns.foo()', 'EXECUTE'); -- yes +ERROR: function "testns.foo()" does not exist +DROP FUNCTION testns.foo(); +ERROR: function testns.foo() does not exist +RESET ROLE; +SELECT count(*) + FROM pg_default_acl d LEFT JOIN pg_namespace n ON defaclnamespace = n.oid + WHERE nspname = 'testns'; + count +------- + 2 +(1 row) + +DROP SCHEMA testns CASCADE; +NOTICE: drop cascades to table testns.acltest1 +SELECT d.* -- check that entries went away + FROM pg_default_acl d LEFT JOIN pg_namespace n ON defaclnamespace = n.oid + WHERE nspname IS NULL AND defaclnamespace != 0; + defaclrole | defaclnamespace | defaclobjtype | defaclacl +------------+-----------------+---------------+----------- +(0 rows) + +-- Grant on all objects of given type in a schema +\c - +CREATE SCHEMA testns; +CREATE TABLE testns.t1 (f1 int); +CREATE TABLE testns.t2 (f1 int); +SELECT has_table_privilege('regressuser1', 'testns.t1', 'SELECT'); -- false + has_table_privilege +--------------------- + f +(1 row) + +GRANT ALL ON ALL TABLES IN SCHEMA testns TO regressuser1; +SELECT has_table_privilege('regressuser1', 'testns.t1', 'SELECT'); -- true + has_table_privilege +--------------------- + t +(1 row) + +SELECT has_table_privilege('regressuser1', 'testns.t2', 'SELECT'); -- true + has_table_privilege +--------------------- + t +(1 row) + +REVOKE ALL ON ALL TABLES IN SCHEMA testns FROM regressuser1; +SELECT has_table_privilege('regressuser1', 'testns.t1', 'SELECT'); -- false + has_table_privilege +--------------------- + f +(1 row) + +SELECT has_table_privilege('regressuser1', 'testns.t2', 'SELECT'); -- false + has_table_privilege +--------------------- + f +(1 row) + +CREATE FUNCTION testns.testfunc(int) RETURNS int AS 'select 3 * $1;' LANGUAGE sql; +SELECT has_function_privilege('regressuser1', 'testns.testfunc(int)', 'EXECUTE'); -- true by default + has_function_privilege +------------------------ + t +(1 row) + +REVOKE ALL ON ALL FUNCTIONS IN SCHEMA testns FROM PUBLIC; +SELECT has_function_privilege('regressuser1', 'testns.testfunc(int)', 'EXECUTE'); -- false + has_function_privilege +------------------------ + f +(1 row) + +SET client_min_messages TO 'warning'; +DROP SCHEMA testns CASCADE; +RESET client_min_messages; +-- clean up +\c +drop sequence x_seq; +DROP FUNCTION testfunc2(int); +ERROR: function testfunc2(integer) does not exist +DROP FUNCTION testfunc4(boolean); +ERROR: function testfunc4(boolean) does not exist +DROP VIEW atestv1; +ERROR: view "atestv1" does not exist +DROP VIEW atestv2; +ERROR: view "atestv2" does not exist +-- this should cascade to drop atestv4 +DROP VIEW atestv3 CASCADE; +NOTICE: drop cascades to view atestv4 +ERROR: view "atestv3" does not exist +-- this should complain "does not exist" +DROP VIEW atestv4; +ERROR: view "atestv4" does not exist +DROP TABLE atest1; +ERROR: cannot drop table atest1 because other objects depend on it +DETAIL: view atestv1 depends on table atest1 +HINT: Use DROP ... CASCADE to drop the dependent objects too. +DROP TABLE atest2; +ERROR: cannot drop table atest2 because other objects depend on it +DETAIL: view atestv2 depends on table atest2 +HINT: Use DROP ... CASCADE to drop the dependent objects too. +DROP TABLE atest3; +ERROR: cannot drop table atest3 because other objects depend on it +DETAIL: view atestv3 depends on table atest3 +view atestv4 depends on view atestv3 +HINT: Use DROP ... CASCADE to drop the dependent objects too. +DROP TABLE atest4; +DROP TABLE atest5; +DROP TABLE atest6; +DROP TABLE atestc; +ERROR: table "atestc" does not exist +DROP TABLE atestp1; +DROP TABLE atestp2; +SELECT lo_unlink(oid) FROM pg_largeobject_metadata; + lo_unlink +----------- + 1 + 1 + 1 + 1 + 1 +(5 rows) + +DROP GROUP regressgroup1; +DROP GROUP regressgroup2; +ERROR: role "regressgroup2" cannot be dropped because some objects depend on it +DETAIL: privileges for table atest3 +-- these are needed to clean up permissions +REVOKE USAGE ON LANGUAGE sql FROM regressuser1; +DROP OWNED BY regressuser1; +ERROR: cannot drop desired object(s) because other objects depend on them +DETAIL: view atestv1 depends on table atest1 +view atestv2 depends on table atest2 +HINT: Use DROP ... CASCADE to drop the dependent objects too. +DROP USER regressuser1; +ERROR: role "regressuser1" cannot be dropped because some objects depend on it +DETAIL: owner of default privileges on new functions belonging to role regressuser1 +owner of table atest2 +owner of table atest1 +DROP USER regressuser2; +ERROR: role "regressuser2" cannot be dropped because some objects depend on it +DETAIL: privileges for view atestv4 +privileges for view atestv2 +privileges for table atest2 +privileges for table atest1 +DROP USER regressuser3; +ERROR: role "regressuser3" cannot be dropped because some objects depend on it +DETAIL: owner of view atestv3 +owner of view atestv2 +owner of view atestv1 +owner of table atest3 +privileges for table atest2 +privileges for table atest1 +DROP USER regressuser4; +ERROR: role "regressuser4" cannot be dropped because some objects depend on it +DETAIL: owner of view atestv4 +privileges for view atestv3 +privileges for view atestv1 +privileges for table atest2 +privileges for table atest1 +DROP USER regressuser5; +ERROR: role "regressuser5" cannot be dropped because some objects depend on it +DETAIL: privileges for table atest2 +DROP USER regressuser6; +ERROR: role "regressuser6" does not exist ----------------------------------------------------------------------- Summary of changes: .../expected/{privileges.out => privileges_1.out} | 166 +++++++++++++------- 1 files changed, 107 insertions(+), 59 deletions(-) copy src/test/regress/expected/{privileges.out => privileges_1.out} (87%) hooks/post-receive -- Postgres-XC |
From: Michael P. <mic...@us...> - 2011-03-25 17:03:49
|
Project "Postgres-XC". The branch, merge_postgres_9_0_3 has been updated via 796bf6e4b113d356b7d725daa71d62835faf9c68 (commit) from ca673e251cd252aa997c9ac51b8f90d2788e8bac (commit) - Log ----------------------------------------------------------------- commit 796bf6e4b113d356b7d725daa71d62835faf9c68 Author: Michael P <mic...@us...> Date: Sat Mar 26 02:02:14 2011 +0900 Fix for regression test create type Postgres-XC does not support TEMP tables, so this output is correct. diff --git a/src/test/regress/expected/create_type_1.out b/src/test/regress/expected/create_type_1.out new file mode 100644 index 0000000..9317dd9 --- /dev/null +++ b/src/test/regress/expected/create_type_1.out @@ -0,0 +1,118 @@ +-- +-- CREATE_TYPE +-- +-- +-- Note: widget_in/out were created in create_function_1, without any +-- prior shell-type creation. These commands therefore complete a test +-- of the "old style" approach of making the functions first. +-- +CREATE TYPE widget ( + internallength = 24, + input = widget_in, + output = widget_out, + typmod_in = numerictypmodin, + typmod_out = numerictypmodout, + alignment = double +); +CREATE TYPE city_budget ( + internallength = 16, + input = int44in, + output = int44out, + element = int4, + category = 'x', -- just to verify the system will take it + preferred = true -- ditto +); +-- Test creation and destruction of shell types +CREATE TYPE shell; +CREATE TYPE shell; -- fail, type already present +ERROR: type "shell" already exists +DROP TYPE shell; +DROP TYPE shell; -- fail, type not exist +ERROR: type "shell" does not exist +-- +-- Test type-related default values (broken in releases before PG 7.2) +-- +-- This part of the test also exercises the "new style" approach of making +-- a shell type and then filling it in. +-- +CREATE TYPE int42; +CREATE TYPE text_w_default; +-- Make dummy I/O routines using the existing internal support for int4, text +CREATE FUNCTION int42_in(cstring) + RETURNS int42 + AS 'int4in' + LANGUAGE internal STRICT; +NOTICE: return type int42 is only a shell +CREATE FUNCTION int42_out(int42) + RETURNS cstring + AS 'int4out' + LANGUAGE internal STRICT; +NOTICE: argument type int42 is only a shell +CREATE FUNCTION text_w_default_in(cstring) + RETURNS text_w_default + AS 'textin' + LANGUAGE internal STRICT; +NOTICE: return type text_w_default is only a shell +CREATE FUNCTION text_w_default_out(text_w_default) + RETURNS cstring + AS 'textout' + LANGUAGE internal STRICT; +NOTICE: argument type text_w_default is only a shell +CREATE TYPE int42 ( + internallength = 4, + input = int42_in, + output = int42_out, + alignment = int4, + default = 42, + passedbyvalue +); +CREATE TYPE text_w_default ( + internallength = variable, + input = text_w_default_in, + output = text_w_default_out, + alignment = int4, + default = 'zippo' +); +CREATE TABLE default_test (f1 text_w_default, f2 int42); +INSERT INTO default_test DEFAULT VALUES; +SELECT * FROM default_test; + f1 | f2 +-------+---- + zippo | 42 +(1 row) + +-- Test stand-alone composite type +CREATE TYPE default_test_row AS (f1 text_w_default, f2 int42); +CREATE FUNCTION get_default_test() RETURNS SETOF default_test_row AS ' + SELECT * FROM default_test; +' LANGUAGE SQL; +SELECT * FROM get_default_test(); + f1 | f2 +-------+---- + zippo | 42 +(1 row) + +-- Test comments +COMMENT ON TYPE bad IS 'bad comment'; +ERROR: type "bad" does not exist +COMMENT ON TYPE default_test_row IS 'good comment'; +COMMENT ON TYPE default_test_row IS NULL; +-- Check shell type create for existing types +CREATE TYPE text_w_default; -- should fail +ERROR: type "text_w_default" already exists +DROP TYPE default_test_row CASCADE; +NOTICE: drop cascades to function get_default_test() +DROP TABLE default_test; +-- Check usage of typmod with a user-defined type +-- (we have borrowed numeric's typmod functions) +CREATE TEMP TABLE mytab (foo widget(42,13,7)); -- should fail +ERROR: invalid NUMERIC type modifier +LINE 1: CREATE TEMP TABLE mytab (foo widget(42,13,7)); + ^ +CREATE TEMP TABLE mytab (foo widget(42,13)); +ERROR: PG-XC does not yet support temporary tables +SELECT format_type(atttypid,atttypmod) FROM pg_attribute +WHERE attrelid = 'mytab'::regclass AND attnum > 0; +ERROR: relation "mytab" does not exist +LINE 2: WHERE attrelid = 'mytab'::regclass AND attnum > 0; + ^ ----------------------------------------------------------------------- Summary of changes: .../{create_type.out => create_type_1.out} | 9 ++++----- 1 files changed, 4 insertions(+), 5 deletions(-) copy src/test/regress/expected/{create_type.out => create_type_1.out} (95%) hooks/post-receive -- Postgres-XC |
From: Michael P. <mic...@us...> - 2011-03-25 15:09:26
|
Project "Postgres-XC". The branch, merge_postgres_9_0_3 has been updated via ca673e251cd252aa997c9ac51b8f90d2788e8bac (commit) via 76f1d9cde238be026007d00a6af192b7f7ac4ce5 (commit) from 8f2f50bd72fd570de84518eaf39abbf464de7019 (commit) - Log ----------------------------------------------------------------- commit ca673e251cd252aa997c9ac51b8f90d2788e8bac Author: Michael P <mic...@us...> Date: Sat Mar 26 00:07:26 2011 +0900 Addition of a check when fetching tuples A strange crash was happening in xmlmap. diff --git a/src/backend/utils/sort/tuplesort.c b/src/backend/utils/sort/tuplesort.c index 0f3551c..a200628 100644 --- a/src/backend/utils/sort/tuplesort.c +++ b/src/backend/utils/sort/tuplesort.c @@ -2881,11 +2881,19 @@ getlen_datanode(Tuplesortstate *state, int tapenum, bool eofOK) * the node number is stored in combiner->tapenodes[tapenum]. * If connection is inactive and no buffered data we have EOF condition */ - int nodenum = conn ? conn->nodenum : combiner->tapenodes[tapenum]; + int nodenum; unsigned int len = 0; ListCell *lc; ListCell *prev = NULL; + /* May it ever happen ?! */ + if (!conn && !combiner->tapenodes) + ereport(ERROR, + (errcode(ERRCODE_INTERNAL_ERROR), + errmsg("Failed to fetch from data node cursor"))); + + nodenum = conn ? conn->nodenum : combiner->tapenodes[tapenum]; + /* * If there are buffered rows iterate over them and get first from * the requested tape commit 76f1d9cde238be026007d00a6af192b7f7ac4ce5 Author: Michael P <mic...@us...> Date: Fri Mar 25 21:12:42 2011 +0900 Fix for cache lookup bug for type With this fix, backend Datanode send back to remote Coordinator the type name and note the OID type to avoid type inconsistencies between nodes as Postgres-XC is a shared-nothing architecture. Patch idea is from Mason, base patch is from Benny, I just gathered all the ideas and improved the patch. diff --git a/src/backend/access/common/printtup.c b/src/backend/access/common/printtup.c index a5e811f..ad8c568 100644 --- a/src/backend/access/common/printtup.c +++ b/src/backend/access/common/printtup.c @@ -20,7 +20,10 @@ #include "libpq/pqformat.h" #include "tcop/pquery.h" #include "utils/lsyscache.h" - +#ifdef PGXC +#include "pgxc/pgxc.h" +#include "parser/parse_type.h" +#endif static void printtup_startup(DestReceiver *self, int operation, TupleDesc typeinfo); @@ -189,6 +192,20 @@ SendRowDescriptionMessage(TupleDesc typeinfo, List *targetlist, int16 *formats) int32 atttypmod = attrs[i]->atttypmod; pq_sendstring(&buf, NameStr(attrs[i]->attname)); + +#ifdef PGXC + /* + * Send the type name from a Postgres-XC Datanode backend. + * This preserves from OID inconsistencies as architecture is shared nothing. + */ + if (IS_PGXC_DATANODE && IsConnFromCoord()) + { + char *typename; + typename = typeTypeName(typeidType(atttypid)); + pq_sendstring(&buf, typename); + } +#endif + /* column ID info appears in protocol 3.0 and up */ if (proto >= 3) { diff --git a/src/backend/pgxc/pool/execRemote.c b/src/backend/pgxc/pool/execRemote.c index d517899..95f23f3 100644 --- a/src/backend/pgxc/pool/execRemote.c +++ b/src/backend/pgxc/pool/execRemote.c @@ -35,6 +35,7 @@ #include "utils/snapmgr.h" #include "pgxc/locator.h" #include "pgxc/pgxc.h" +#include "parser/parse_type.h" #define END_QUERY_TIMEOUT 20 #define DATA_NODE_FETCH_SIZE 1 @@ -405,10 +406,10 @@ create_tuple_desc(char *msg_body, size_t len) for (i = 1; i <= nattr; i++) { AttrNumber attnum; - char *attname; + char *attname; + char *typname; Oid oidtypeid; int32 typmod; - uint32 n32; attnum = (AttrNumber) i; @@ -417,28 +418,31 @@ create_tuple_desc(char *msg_body, size_t len) attname = msg_body; msg_body += strlen(attname) + 1; + /* type name */ + typname = msg_body; + msg_body += strlen(typname) + 1; + /* table OID, ignored */ msg_body += 4; /* column no, ignored */ msg_body += 2; - /* data type */ - memcpy(&n32, msg_body, 4); - oidtypeid = ntohl(n32); + /* data type OID, ignored */ msg_body += 4; /* type len, ignored */ msg_body += 2; - /* type mod */ - memcpy(&n32, msg_body, 4); - typmod = ntohl(n32); + /* type mod, ignored */ msg_body += 4; /* PGXCTODO text/binary flag? */ msg_body += 2; + /* Get the OID type and mode type from typename */ + parseTypeString(typname, &oidtypeid, &typmod); + TupleDescInitEntry(result, attnum, attname, oidtypeid, typmod, 0); } return result; ----------------------------------------------------------------------- Summary of changes: src/backend/access/common/printtup.c | 19 ++++++++++++++++++- src/backend/pgxc/pool/execRemote.c | 20 ++++++++++++-------- src/backend/utils/sort/tuplesort.c | 10 +++++++++- 3 files changed, 39 insertions(+), 10 deletions(-) hooks/post-receive -- Postgres-XC |
From: Abbas B. <ga...@us...> - 2011-03-25 10:44:55
|
Project "Postgres-XC". The branch, merge_postgres_9_0_3 has been updated via 8f2f50bd72fd570de84518eaf39abbf464de7019 (commit) from c696488cee189743e90303c52954f9e4d791e18c (commit) - Log ----------------------------------------------------------------- commit 8f2f50bd72fd570de84518eaf39abbf464de7019 Author: Abbas <abb...@en...> Date: Fri Mar 25 15:44:08 2011 +0500 Since the creation of unique indices is supposed to fail in XC hence this output is correct diff --git a/src/test/regress/expected/uuid_1.out b/src/test/regress/expected/uuid_1.out new file mode 100644 index 0000000..6a593be --- /dev/null +++ b/src/test/regress/expected/uuid_1.out @@ -0,0 +1,148 @@ +-- regression test for the uuid datatype +-- creating test tables +CREATE TABLE guid1 +( + guid_field UUID, + text_field TEXT DEFAULT(now()) +); +CREATE TABLE guid2 +( + guid_field UUID, + text_field TEXT DEFAULT(now()) +); +-- inserting invalid data tests +-- too long +INSERT INTO guid1(guid_field) VALUES('11111111-1111-1111-1111-111111111111F'); +ERROR: invalid input syntax for uuid: "11111111-1111-1111-1111-111111111111F" +LINE 1: INSERT INTO guid1(guid_field) VALUES('11111111-1111-1111-111... + ^ +-- too short +INSERT INTO guid1(guid_field) VALUES('{11111111-1111-1111-1111-11111111111}'); +ERROR: invalid input syntax for uuid: "{11111111-1111-1111-1111-11111111111}" +LINE 1: INSERT INTO guid1(guid_field) VALUES('{11111111-1111-1111-11... + ^ +-- valid data but invalid format +INSERT INTO guid1(guid_field) VALUES('111-11111-1111-1111-1111-111111111111'); +ERROR: invalid input syntax for uuid: "111-11111-1111-1111-1111-111111111111" +LINE 1: INSERT INTO guid1(guid_field) VALUES('111-11111-1111-1111-11... + ^ +INSERT INTO guid1(guid_field) VALUES('{22222222-2222-2222-2222-222222222222 '); +ERROR: invalid input syntax for uuid: "{22222222-2222-2222-2222-222222222222 " +LINE 1: INSERT INTO guid1(guid_field) VALUES('{22222222-2222-2222-22... + ^ +-- invalid data +INSERT INTO guid1(guid_field) VALUES('11111111-1111-1111-G111-111111111111'); +ERROR: invalid input syntax for uuid: "11111111-1111-1111-G111-111111111111" +LINE 1: INSERT INTO guid1(guid_field) VALUES('11111111-1111-1111-G11... + ^ +INSERT INTO guid1(guid_field) VALUES('11+11111-1111-1111-1111-111111111111'); +ERROR: invalid input syntax for uuid: "11+11111-1111-1111-1111-111111111111" +LINE 1: INSERT INTO guid1(guid_field) VALUES('11+11111-1111-1111-111... + ^ +--inserting three input formats +INSERT INTO guid1(guid_field) VALUES('11111111-1111-1111-1111-111111111111'); +INSERT INTO guid1(guid_field) VALUES('{22222222-2222-2222-2222-222222222222}'); +INSERT INTO guid1(guid_field) VALUES('3f3e3c3b3a3039383736353433a2313e'); +-- retrieving the inserted data +SELECT guid_field FROM guid1 ORDER BY guid_field; + guid_field +-------------------------------------- + 11111111-1111-1111-1111-111111111111 + 22222222-2222-2222-2222-222222222222 + 3f3e3c3b-3a30-3938-3736-353433a2313e +(3 rows) + +-- ordering test +SELECT guid_field FROM guid1 ORDER BY guid_field ASC; + guid_field +-------------------------------------- + 11111111-1111-1111-1111-111111111111 + 22222222-2222-2222-2222-222222222222 + 3f3e3c3b-3a30-3938-3736-353433a2313e +(3 rows) + +SELECT guid_field FROM guid1 ORDER BY guid_field DESC; + guid_field +-------------------------------------- + 3f3e3c3b-3a30-3938-3736-353433a2313e + 22222222-2222-2222-2222-222222222222 + 11111111-1111-1111-1111-111111111111 +(3 rows) + +-- = operator test +SELECT COUNT(*) FROM guid1 WHERE guid_field = '3f3e3c3b-3a30-3938-3736-353433a2313e'; + count +------- + 1 +(1 row) + +-- <> operator test +SELECT COUNT(*) FROM guid1 WHERE guid_field <> '11111111111111111111111111111111'; + count +------- + 2 +(1 row) + +-- < operator test +SELECT COUNT(*) FROM guid1 WHERE guid_field < '22222222-2222-2222-2222-222222222222'; + count +------- + 1 +(1 row) + +-- <= operator test +SELECT COUNT(*) FROM guid1 WHERE guid_field <= '22222222-2222-2222-2222-222222222222'; + count +------- + 2 +(1 row) + +-- > operator test +SELECT COUNT(*) FROM guid1 WHERE guid_field > '22222222-2222-2222-2222-222222222222'; + count +------- + 1 +(1 row) + +-- >= operator test +SELECT COUNT(*) FROM guid1 WHERE guid_field >= '22222222-2222-2222-2222-222222222222'; + count +------- + 2 +(1 row) + +-- btree and hash index creation test +CREATE INDEX guid1_btree ON guid1 USING BTREE (guid_field); +CREATE INDEX guid1_hash ON guid1 USING HASH (guid_field); +-- unique index test +CREATE UNIQUE INDEX guid1_unique_BTREE ON guid1 USING BTREE (guid_field); +ERROR: Cannot locally enforce a unique index on round robin distributed table. +-- should fail +INSERT INTO guid1(guid_field) VALUES('11111111-1111-1111-1111-111111111111'); +-- check to see whether the new indexes are actually there +SELECT count(*) FROM pg_class WHERE relkind='i' AND relname LIKE 'guid%'; + count +------- + 2 +(1 row) + +-- populating the test tables with additional records +INSERT INTO guid1(guid_field) VALUES('44444444-4444-4444-4444-444444444444'); +INSERT INTO guid2(guid_field) VALUES('11111111-1111-1111-1111-111111111111'); +INSERT INTO guid2(guid_field) VALUES('{22222222-2222-2222-2222-222222222222}'); +INSERT INTO guid2(guid_field) VALUES('3f3e3c3b3a3039383736353433a2313e'); +-- join test +SELECT COUNT(*) FROM guid1 g1 INNER JOIN guid2 g2 ON g1.guid_field = g2.guid_field; + count +------- + 4 +(1 row) + +SELECT COUNT(*) FROM guid1 g1 LEFT JOIN guid2 g2 ON g1.guid_field = g2.guid_field WHERE g2.guid_field IS NULL; + count +------- + 1 +(1 row) + +-- clean up +DROP TABLE guid1, guid2 CASCADE; ----------------------------------------------------------------------- Summary of changes: src/test/regress/expected/{uuid.out => uuid_1.out} | 7 +++---- 1 files changed, 3 insertions(+), 4 deletions(-) copy src/test/regress/expected/{uuid.out => uuid_1.out} (96%) hooks/post-receive -- Postgres-XC |