4 c text not null default 'stuff',
9 CREATE FUNCTION fn_x_before () RETURNS TRIGGER AS '
11 NEW.e := ''before trigger fired''::text;
16 CREATE FUNCTION fn_x_after () RETURNS TRIGGER AS '
18 UPDATE x set e=''after trigger fired'' where c=''stuff'';
23 CREATE TRIGGER trg_x_after AFTER INSERT ON x
24 FOR EACH ROW EXECUTE PROCEDURE fn_x_after();
26 CREATE TRIGGER trg_x_before BEFORE INSERT ON x
27 FOR EACH ROW EXECUTE PROCEDURE fn_x_before();
29 COPY x (a, b, c, d, e) from stdin;
34 COPY x (b, d) from stdin;
38 COPY x (b, d) from stdin;
45 COPY x (a, b, c, d, e) from stdin;
53 -- non-existent column in column list: should fail
54 COPY x (xyz) from stdin;
57 COPY x from stdin (format CSV, FORMAT CSV);
58 COPY x from stdin (freeze off, freeze on);
59 COPY x from stdin (delimiter ',', delimiter ',');
60 COPY x from stdin (null ' ', null ' ');
61 COPY x from stdin (header off, header on);
62 COPY x from stdin (quote ':', quote ':');
63 COPY x from stdin (escape ':', escape ':');
64 COPY x from stdin (force_quote (a), force_quote *);
65 COPY x from stdin (force_not_null (a), force_not_null (b));
66 COPY x from stdin (force_null (a), force_null (b));
67 COPY x from stdin (convert_selectively (a), convert_selectively (b));
68 COPY x from stdin (encoding 'sql_ascii', encoding 'sql_ascii');
69 COPY x from stdin (on_error ignore, on_error ignore);
70 COPY x from stdin (log_verbosity default, log_verbosity verbose);
73 COPY x from stdin (format BINARY, delimiter ',');
74 COPY x from stdin (format BINARY, null 'x');
75 COPY x from stdin (format BINARY, on_error ignore);
76 COPY x from stdin (on_error unsupported);
77 COPY x from stdin (format TEXT, force_quote(a));
78 COPY x from stdin (format TEXT, force_quote *);
79 COPY x from stdin (format CSV, force_quote(a));
80 COPY x from stdin (format CSV, force_quote *);
81 COPY x from stdin (format TEXT, force_not_null(a));
82 COPY x from stdin (format TEXT, force_not_null *);
83 COPY x to stdout (format CSV, force_not_null(a));
84 COPY x to stdout (format CSV, force_not_null *);
85 COPY x from stdin (format TEXT, force_null(a));
86 COPY x from stdin (format TEXT, force_null *);
87 COPY x to stdout (format CSV, force_null(a));
88 COPY x to stdout (format CSV, force_null *);
89 COPY x to stdout (format BINARY, on_error unsupported);
90 COPY x from stdin (log_verbosity unsupported);
91 COPY x from stdin with (reject_limit 1);
92 COPY x from stdin with (on_error ignore, reject_limit 0);
94 -- too many columns in column list: should fail
95 COPY x (a, b, c, d, e, d, c) from stdin;
97 -- missing data: should fail
108 -- extra data: should fail
110 2002 232 40 50 60 70 80
113 -- various COPY options: delimiters, oids, NULL string, encoding
114 COPY x (b, c, d, e) from stdin delimiter ',' null 'x';
120 COPY x from stdin WITH DELIMITER AS ';' NULL AS '';
124 COPY x from stdin WITH DELIMITER AS ':' NULL AS E'\\X' ENCODING 'sql_ascii';
128 4003:3:Backslash:\\:\\
129 4004:4:BackslashX:\\X:\\X
131 4006:6:BackslashN:\\N:\\N
133 4008:8:Delimiter:\::\:
136 COPY x TO stdout WHERE a = 1;
137 COPY x from stdin WHERE a = 50004;
143 COPY x from stdin WHERE a > 60003;
151 COPY x from stdin WHERE f > 60003;
153 COPY x from stdin WHERE a = max(x.b);
155 COPY x from stdin WHERE a IN (SELECT 1 FROM x);
157 COPY x from stdin WHERE a IN (generate_series(1,5));
159 COPY x from stdin WHERE a = row_number() over(b);
162 -- check results of copy in
167 COPY x (c, e) TO stdout;
168 COPY x (b, e) TO stdout WITH NULL 'I''m null';
170 CREATE TEMP TABLE y (
175 INSERT INTO y VALUES ('Jackson, Sam', E'\\h');
176 INSERT INTO y VALUES ('It is "perfect".',E'\t');
177 INSERT INTO y VALUES ('', NULL);
179 COPY y TO stdout WITH CSV;
180 COPY y TO stdout WITH CSV QUOTE '''' DELIMITER '|';
181 COPY y TO stdout WITH CSV FORCE QUOTE col2 ESCAPE E'\\' ENCODING 'sql_ascii';
182 COPY y TO stdout WITH CSV FORCE QUOTE *;
184 -- Repeat above tests with new 9.0 option syntax
186 COPY y TO stdout (FORMAT CSV);
187 COPY y TO stdout (FORMAT CSV, QUOTE '''', DELIMITER '|');
188 COPY y TO stdout (FORMAT CSV, FORCE_QUOTE (col2), ESCAPE E'\\');
189 COPY y TO stdout (FORMAT CSV, FORCE_QUOTE *);
191 \copy y TO stdout (FORMAT CSV)
192 \copy y TO stdout (FORMAT CSV, QUOTE '''', DELIMITER '|')
193 \copy y TO stdout (FORMAT CSV, FORCE_QUOTE (col2), ESCAPE E'\\')
194 \copy y TO stdout (FORMAT CSV, FORCE_QUOTE *)
196 --test that we read consecutive LFs properly
198 CREATE TEMP TABLE testnl (a int, b text, c int);
200 COPY testnl FROM stdin CSV;
201 1,"a field with two LFs
206 -- test end of copy marker
207 CREATE TEMP TABLE testeoc (a text);
209 COPY testeoc FROM stdin CSV;
216 COPY testeoc TO stdout CSV;
218 -- test handling of nonstandard null marker that violates escaping rules
220 CREATE TEMP TABLE testnull(a int, b text);
221 INSERT INTO testnull VALUES (1, E'\\0'), (NULL, NULL);
223 COPY testnull TO stdout WITH NULL AS E'\\0';
225 COPY testnull FROM stdin WITH NULL AS E'\\0';
230 SELECT * FROM testnull;
233 CREATE TABLE vistest (LIKE testeoc);
234 COPY vistest FROM stdin CSV;
239 SELECT * FROM vistest;
242 COPY vistest FROM stdin CSV;
246 SELECT * FROM vistest;
249 COPY vistest FROM stdin CSV;
253 SELECT * FROM vistest;
255 SELECT * FROM vistest;
259 COPY vistest FROM stdin CSV FREEZE;
263 SELECT * FROM vistest;
266 COPY vistest FROM stdin CSV FREEZE;
270 SELECT * FROM vistest;
272 SELECT * FROM vistest;
276 COPY vistest FROM stdin CSV FREEZE;
280 SELECT * FROM vistest;
283 COPY vistest FROM stdin CSV FREEZE;
290 COPY vistest FROM stdin CSV FREEZE;
296 INSERT INTO vistest VALUES ('z');
299 ROLLBACK TO SAVEPOINT s1;
300 COPY vistest FROM stdin CSV FREEZE;
305 CREATE FUNCTION truncate_in_subxact() RETURNS VOID AS
311 INSERT INTO vistest VALUES ('subxact failure');
315 INSERT INTO vistest VALUES ('z');
316 SELECT truncate_in_subxact();
317 COPY vistest FROM stdin CSV FREEZE;
321 SELECT * FROM vistest;
323 SELECT * FROM vistest;
324 -- Test FORCE_NOT_NULL and FORCE_NULL options
325 CREATE TEMP TABLE forcetest (
333 -- should succeed with no effect ("b" remains an empty string, "c" remains NULL)
335 COPY forcetest (a, b, c) FROM STDIN WITH (FORMAT csv, FORCE_NOT_NULL(b), FORCE_NULL(c));
339 SELECT b, c FROM forcetest WHERE a = 1;
340 -- should succeed, FORCE_NULL and FORCE_NOT_NULL can be both specified
342 COPY forcetest (a, b, c, d) FROM STDIN WITH (FORMAT csv, FORCE_NOT_NULL(c,d), FORCE_NULL(c,d));
346 SELECT c, d FROM forcetest WHERE a = 2;
347 -- should fail with not-null constraint violation
349 COPY forcetest (a, b, c) FROM STDIN WITH (FORMAT csv, FORCE_NULL(b), FORCE_NOT_NULL(c));
353 -- should fail with "not referenced by COPY" error
355 COPY forcetest (d, e) FROM STDIN WITH (FORMAT csv, FORCE_NOT_NULL(b));
357 -- should fail with "not referenced by COPY" error
359 COPY forcetest (d, e) FROM STDIN WITH (FORMAT csv, FORCE_NULL(b));
361 -- should succeed with no effect ("b" remains an empty string, "c" remains NULL)
363 COPY forcetest (a, b, c) FROM STDIN WITH (FORMAT csv, FORCE_NOT_NULL *, FORCE_NULL *);
367 SELECT b, c FROM forcetest WHERE a = 4;
368 -- should succeed with effect ("b" remains an empty string)
370 COPY forcetest (a, b, c) FROM STDIN WITH (FORMAT csv, FORCE_NOT_NULL *);
374 SELECT b, c FROM forcetest WHERE a = 5;
375 -- should succeed with effect ("c" remains NULL)
377 COPY forcetest (a, b, c) FROM STDIN WITH (FORMAT csv, FORCE_NULL *);
381 SELECT b, c FROM forcetest WHERE a = 6;
382 -- should fail with "conflicting or redundant options" error
384 COPY forcetest (a, b, c) FROM STDIN WITH (FORMAT csv, FORCE_NOT_NULL *, FORCE_NOT_NULL(b));
386 -- should fail with "conflicting or redundant options" error
388 COPY forcetest (a, b, c) FROM STDIN WITH (FORMAT csv, FORCE_NULL *, FORCE_NULL(b));
393 -- test case with whole-row Var in a check constraint
394 create table check_con_tbl (f1 int);
395 create function check_con_function(check_con_tbl) returns bool as $$
397 raise notice 'input = %', row_to_json($1);
399 end $$ language plpgsql immutable;
400 alter table check_con_tbl add check (check_con_function(check_con_tbl.*));
402 copy check_con_tbl from stdin;
406 copy check_con_tbl from stdin;
409 select * from check_con_tbl;
411 -- test with RLS enabled.
412 CREATE ROLE regress_rls_copy_user;
413 CREATE ROLE regress_rls_copy_user_colperms;
414 CREATE TABLE rls_t1 (a int, b int, c int);
416 COPY rls_t1 (a, b, c) from stdin;
423 CREATE POLICY p1 ON rls_t1 FOR SELECT USING (a % 2 = 0);
424 ALTER TABLE rls_t1 ENABLE ROW LEVEL SECURITY;
425 ALTER TABLE rls_t1 FORCE ROW LEVEL SECURITY;
427 GRANT SELECT ON TABLE rls_t1 TO regress_rls_copy_user;
428 GRANT SELECT (a, b) ON TABLE rls_t1 TO regress_rls_copy_user_colperms;
431 COPY rls_t1 TO stdout;
432 COPY rls_t1 (a, b, c) TO stdout;
435 COPY rls_t1 (a) TO stdout;
436 COPY rls_t1 (a, b) TO stdout;
439 COPY rls_t1 (b, a) TO stdout;
441 SET SESSION AUTHORIZATION regress_rls_copy_user;
444 COPY rls_t1 TO stdout;
445 COPY rls_t1 (a, b, c) TO stdout;
448 COPY rls_t1 (a) TO stdout;
449 COPY rls_t1 (a, b) TO stdout;
452 COPY rls_t1 (b, a) TO stdout;
454 RESET SESSION AUTHORIZATION;
456 SET SESSION AUTHORIZATION regress_rls_copy_user_colperms;
458 -- attempt all columns (should fail)
459 COPY rls_t1 TO stdout;
460 COPY rls_t1 (a, b, c) TO stdout;
462 -- try to copy column with no privileges (should fail)
463 COPY rls_t1 (c) TO stdout;
465 -- subset of columns (should succeed)
466 COPY rls_t1 (a) TO stdout;
467 COPY rls_t1 (a, b) TO stdout;
469 RESET SESSION AUTHORIZATION;
471 -- test with INSTEAD OF INSERT trigger on a view
472 CREATE TABLE instead_of_insert_tbl(id serial, name text);
473 CREATE VIEW instead_of_insert_tbl_view AS SELECT ''::text AS str;
475 COPY instead_of_insert_tbl_view FROM stdin; -- fail
479 CREATE FUNCTION fun_instead_of_insert_tbl() RETURNS trigger AS $$
481 INSERT INTO instead_of_insert_tbl (name) VALUES (NEW.str);
485 CREATE TRIGGER trig_instead_of_insert_tbl_view
486 INSTEAD OF INSERT ON instead_of_insert_tbl_view
487 FOR EACH ROW EXECUTE PROCEDURE fun_instead_of_insert_tbl();
489 COPY instead_of_insert_tbl_view FROM stdin;
493 SELECT * FROM instead_of_insert_tbl;
495 -- Test of COPY optimization with view using INSTEAD OF INSERT
496 -- trigger when relation is created in the same transaction as
497 -- when COPY is executed.
499 CREATE VIEW instead_of_insert_tbl_view_2 as select ''::text as str;
500 CREATE TRIGGER trig_instead_of_insert_tbl_view_2
501 INSTEAD OF INSERT ON instead_of_insert_tbl_view_2
502 FOR EACH ROW EXECUTE PROCEDURE fun_instead_of_insert_tbl();
504 COPY instead_of_insert_tbl_view_2 FROM stdin;
508 SELECT * FROM instead_of_insert_tbl;
511 -- tests for on_error option
512 CREATE TABLE check_ign_err (n int, m int[], k int);
513 COPY check_ign_err FROM STDIN WITH (on_error stop);
522 -- want context for notices
523 \set SHOW_CONTEXT always
525 COPY check_ign_err FROM STDIN WITH (on_error ignore, log_verbosity verbose);
537 -- tests for on_error option with log_verbosity and null constraint via domain
538 CREATE DOMAIN dcheck_ign_err2 varchar(15) NOT NULL;
539 CREATE TABLE check_ign_err2 (n int, m int[], k int, l dcheck_ign_err2);
540 COPY check_ign_err2 FROM STDIN WITH (on_error ignore, log_verbosity verbose);
544 COPY check_ign_err2 FROM STDIN WITH (on_error ignore, log_verbosity silent);
549 -- reset context choice
550 \set SHOW_CONTEXT errors
552 SELECT * FROM check_ign_err;
554 SELECT * FROM check_ign_err2;
556 -- test datatype error that can't be handled as soft: should fail
557 CREATE TABLE hard_err(foo widget);
558 COPY hard_err FROM STDIN WITH (on_error ignore);
562 -- test missing data: should fail
563 COPY check_ign_err FROM STDIN WITH (on_error ignore);
567 -- test extra data: should fail
568 COPY check_ign_err FROM STDIN WITH (on_error ignore);
572 -- tests for reject_limit option
573 COPY check_ign_err FROM STDIN WITH (on_error ignore, reject_limit 3);
582 COPY check_ign_err FROM STDIN WITH (on_error ignore, reject_limit 4);
592 DROP TABLE forcetest;
594 DROP FUNCTION truncate_in_subxact();
596 DROP TABLE rls_t1 CASCADE;
597 DROP ROLE regress_rls_copy_user;
598 DROP ROLE regress_rls_copy_user_colperms;
599 DROP FUNCTION fn_x_before();
600 DROP FUNCTION fn_x_after();
601 DROP TABLE instead_of_insert_tbl;
602 DROP VIEW instead_of_insert_tbl_view;
603 DROP VIEW instead_of_insert_tbl_view_2;
604 DROP FUNCTION fun_instead_of_insert_tbl();
605 DROP TABLE check_ign_err;
606 DROP TABLE check_ign_err2;
607 DROP DOMAIN dcheck_ign_err2;
611 -- COPY FROM ... DEFAULT
614 create temp table copy_default (
615 id integer primary key,
616 text_value text not null default 'test',
617 ts_value timestamp without time zone not null default '2022-07-05'
620 -- if DEFAULT is not specified, then the marker will be regular data
621 copy copy_default from stdin;
626 select id, text_value, ts_value from copy_default;
628 truncate copy_default;
630 copy copy_default from stdin with (format csv);
635 select id, text_value, ts_value from copy_default;
637 truncate copy_default;
639 -- DEFAULT cannot be used in binary mode
640 copy copy_default from stdin with (format binary, default '\D');
642 -- DEFAULT cannot be new line nor carriage return
643 copy copy_default from stdin with (default E'\n');
644 copy copy_default from stdin with (default E'\r');
646 -- DELIMITER cannot appear in DEFAULT spec
647 copy copy_default from stdin with (delimiter ';', default 'test;test');
649 -- CSV quote cannot appear in DEFAULT spec
650 copy copy_default from stdin with (format csv, quote '"', default 'test"test');
652 -- NULL and DEFAULT spec must be different
653 copy copy_default from stdin with (default '\N');
655 -- cannot use DEFAULT marker in column that has no DEFAULT value
656 copy copy_default from stdin with (default '\D');
657 \D value '2022-07-04'
661 copy copy_default from stdin with (format csv, default '\D');
666 -- The DEFAULT marker must be unquoted and unescaped or it's not recognized
667 copy copy_default from stdin with (default '\D');
673 select id, text_value, ts_value from copy_default;
675 truncate copy_default;
677 copy copy_default from stdin with (format csv, default '\D');
683 select id, text_value, ts_value from copy_default;
685 truncate copy_default;
687 -- successful usage of DEFAULT option in COPY
688 copy copy_default from stdin with (default '\D');
694 select id, text_value, ts_value from copy_default;
696 truncate copy_default;
698 copy copy_default from stdin with (format csv, default '\D');
704 select id, text_value, ts_value from copy_default;
706 truncate copy_default;
708 -- DEFAULT cannot be used in COPY TO
709 copy (select 1 as test) TO stdout with (default '\D');