1CREATE FUNCTION alter_op_test_fn(boolean, boolean)
2RETURNS boolean AS $$ SELECT NULL::BOOLEAN; $$ LANGUAGE sql IMMUTABLE;
3CREATE FUNCTION customcontsel(internal, oid, internal, integer)
4RETURNS float8 AS 'contsel' LANGUAGE internal STABLE STRICT;
5CREATE OPERATOR === (
6    LEFTARG = boolean,
7    RIGHTARG = boolean,
8    PROCEDURE = alter_op_test_fn,
9    COMMUTATOR = ===,
10    NEGATOR = !==,
11    RESTRICT = customcontsel,
12    JOIN = contjoinsel,
13    HASHES, MERGES
14);
15SELECT pg_describe_object(refclassid,refobjid,refobjsubid) as ref, deptype
16FROM pg_depend
17WHERE classid = 'pg_operator'::regclass AND
18      objid = '===(bool,bool)'::regoperator
19ORDER BY 1;
20                          ref                          | deptype
21-------------------------------------------------------+---------
22 function alter_op_test_fn(boolean,boolean)            | n
23 function customcontsel(internal,oid,internal,integer) | n
24 schema public                                         | n
25(3 rows)
26
27--
28-- Reset and set params
29--
30ALTER OPERATOR === (boolean, boolean) SET (RESTRICT = NONE);
31ALTER OPERATOR === (boolean, boolean) SET (JOIN = NONE);
32SELECT oprrest, oprjoin FROM pg_operator WHERE oprname = '==='
33  AND oprleft = 'boolean'::regtype AND oprright = 'boolean'::regtype;
34 oprrest | oprjoin
35---------+---------
36 -       | -
37(1 row)
38
39SELECT pg_describe_object(refclassid,refobjid,refobjsubid) as ref, deptype
40FROM pg_depend
41WHERE classid = 'pg_operator'::regclass AND
42      objid = '===(bool,bool)'::regoperator
43ORDER BY 1;
44                    ref                     | deptype
45--------------------------------------------+---------
46 function alter_op_test_fn(boolean,boolean) | n
47 schema public                              | n
48(2 rows)
49
50ALTER OPERATOR === (boolean, boolean) SET (RESTRICT = contsel);
51ALTER OPERATOR === (boolean, boolean) SET (JOIN = contjoinsel);
52SELECT oprrest, oprjoin FROM pg_operator WHERE oprname = '==='
53  AND oprleft = 'boolean'::regtype AND oprright = 'boolean'::regtype;
54 oprrest |   oprjoin
55---------+-------------
56 contsel | contjoinsel
57(1 row)
58
59SELECT pg_describe_object(refclassid,refobjid,refobjsubid) as ref, deptype
60FROM pg_depend
61WHERE classid = 'pg_operator'::regclass AND
62      objid = '===(bool,bool)'::regoperator
63ORDER BY 1;
64                    ref                     | deptype
65--------------------------------------------+---------
66 function alter_op_test_fn(boolean,boolean) | n
67 schema public                              | n
68(2 rows)
69
70ALTER OPERATOR === (boolean, boolean) SET (RESTRICT = NONE, JOIN = NONE);
71SELECT oprrest, oprjoin FROM pg_operator WHERE oprname = '==='
72  AND oprleft = 'boolean'::regtype AND oprright = 'boolean'::regtype;
73 oprrest | oprjoin
74---------+---------
75 -       | -
76(1 row)
77
78SELECT pg_describe_object(refclassid,refobjid,refobjsubid) as ref, deptype
79FROM pg_depend
80WHERE classid = 'pg_operator'::regclass AND
81      objid = '===(bool,bool)'::regoperator
82ORDER BY 1;
83                    ref                     | deptype
84--------------------------------------------+---------
85 function alter_op_test_fn(boolean,boolean) | n
86 schema public                              | n
87(2 rows)
88
89ALTER OPERATOR === (boolean, boolean) SET (RESTRICT = customcontsel, JOIN = contjoinsel);
90SELECT oprrest, oprjoin FROM pg_operator WHERE oprname = '==='
91  AND oprleft = 'boolean'::regtype AND oprright = 'boolean'::regtype;
92    oprrest    |   oprjoin
93---------------+-------------
94 customcontsel | contjoinsel
95(1 row)
96
97SELECT pg_describe_object(refclassid,refobjid,refobjsubid) as ref, deptype
98FROM pg_depend
99WHERE classid = 'pg_operator'::regclass AND
100      objid = '===(bool,bool)'::regoperator
101ORDER BY 1;
102                          ref                          | deptype
103-------------------------------------------------------+---------
104 function alter_op_test_fn(boolean,boolean)            | n
105 function customcontsel(internal,oid,internal,integer) | n
106 schema public                                         | n
107(3 rows)
108
109--
110-- Test invalid options.
111--
112ALTER OPERATOR === (boolean, boolean) SET (COMMUTATOR = ====);
113ERROR:  operator attribute "commutator" cannot be changed
114ALTER OPERATOR === (boolean, boolean) SET (NEGATOR = ====);
115ERROR:  operator attribute "negator" cannot be changed
116ALTER OPERATOR === (boolean, boolean) SET (RESTRICT = non_existent_func);
117ERROR:  function non_existent_func(internal, oid, internal, integer) does not exist
118ALTER OPERATOR === (boolean, boolean) SET (JOIN = non_existent_func);
119ERROR:  function non_existent_func(internal, oid, internal, smallint, internal) does not exist
120ALTER OPERATOR === (boolean, boolean) SET (COMMUTATOR = !==);
121ERROR:  operator attribute "commutator" cannot be changed
122ALTER OPERATOR === (boolean, boolean) SET (NEGATOR = !==);
123ERROR:  operator attribute "negator" cannot be changed
124-- invalid: non-lowercase quoted identifiers
125ALTER OPERATOR & (bit, bit) SET ("Restrict" = _int_contsel, "Join" = _int_contjoinsel);
126ERROR:  operator attribute "Restrict" not recognized
127--
128-- Test permission check. Must be owner to ALTER OPERATOR.
129--
130CREATE USER regress_alter_op_user;
131SET SESSION AUTHORIZATION regress_alter_op_user;
132ALTER OPERATOR === (boolean, boolean) SET (RESTRICT = NONE);
133ERROR:  must be owner of operator ===
134-- Clean up
135RESET SESSION AUTHORIZATION;
136DROP USER regress_alter_op_user;
137DROP OPERATOR === (boolean, boolean);
138DROP FUNCTION customcontsel(internal, oid, internal, integer);
139DROP FUNCTION alter_op_test_fn(boolean, boolean);
140