1
0
mirror of https://github.com/postgres/postgres.git synced 2025-07-05 07:21:24 +03:00

Reduce scope of changes for COPY FREEZE.

Allow support only for freezing tuples by explicit
command. Previous coding mistakenly extended
slightly beyond what was agreed as correct on -hackers.
So essentially a partial revoke of earlier work,
leaving just the COPY FREEZE command.
This commit is contained in:
Simon Riggs
2012-12-02 20:52:52 +00:00
parent 3114cb60a1
commit 5457a130d3
5 changed files with 57 additions and 47 deletions

View File

@ -1875,13 +1875,11 @@ FreeBulkInsertState(BulkInsertState bistate)
* The HEAP_INSERT_SKIP_FSM option is passed directly to * The HEAP_INSERT_SKIP_FSM option is passed directly to
* RelationGetBufferForTuple, which see for more info. * RelationGetBufferForTuple, which see for more info.
* *
* HEAP_INSERT_COMMITTED should only be specified for inserts into * HEAP_INSERT_FROZEN should only be specified for inserts into
* relfilenodes created during the current subtransaction and when * relfilenodes created during the current subtransaction and when
* there are no prior snapshots or pre-existing portals open. * there are no prior snapshots or pre-existing portals open.
* * This causes rows to be frozen, which is an MVCC violation and
* HEAP_INSERT_FROZEN only has meaning when HEAP_INSERT_COMMITTED is * requires explicit options chosen by user.
* also set. This causes rows to be frozen, which is an MVCC violation
* and requires explicit options chosen by user.
* *
* Note that these options will be applied when inserting into the heap's * Note that these options will be applied when inserting into the heap's
* TOAST table, too, if the tuple requires any out-of-line data. * TOAST table, too, if the tuple requires any out-of-line data.
@ -2086,10 +2084,9 @@ heap_prepare_insert(Relation relation, HeapTuple tup, TransactionId xid,
tup->t_data->t_infomask &= ~(HEAP_XACT_MASK); tup->t_data->t_infomask &= ~(HEAP_XACT_MASK);
tup->t_data->t_infomask2 &= ~(HEAP2_XACT_MASK); tup->t_data->t_infomask2 &= ~(HEAP2_XACT_MASK);
tup->t_data->t_infomask |= HEAP_XMAX_INVALID; tup->t_data->t_infomask |= HEAP_XMAX_INVALID;
if (options & HEAP_INSERT_COMMITTED) if (options & HEAP_INSERT_FROZEN)
{ {
tup->t_data->t_infomask |= HEAP_XMIN_COMMITTED; tup->t_data->t_infomask |= HEAP_XMIN_COMMITTED;
if (options & HEAP_INSERT_FROZEN)
HeapTupleHeaderSetXmin(tup->t_data, FrozenTransactionId); HeapTupleHeaderSetXmin(tup->t_data, FrozenTransactionId);
} }
else else

View File

@ -1994,15 +1994,12 @@ CopyFrom(CopyState cstate)
* which subtransaction created it is crucial for correctness * which subtransaction created it is crucial for correctness
* of this optimisation. * of this optimisation.
*/ */
if (ThereAreNoPriorRegisteredSnapshots() && if (cstate->freeze &&
ThereAreNoPriorRegisteredSnapshots() &&
ThereAreNoReadyPortals() && ThereAreNoReadyPortals() &&
cstate->rel->rd_newRelfilenodeSubid == GetCurrentSubTransactionId()) cstate->rel->rd_newRelfilenodeSubid == GetCurrentSubTransactionId())
{
hi_options |= HEAP_INSERT_COMMITTED;
if (cstate->freeze)
hi_options |= HEAP_INSERT_FROZEN; hi_options |= HEAP_INSERT_FROZEN;
} }
}
if (cstate->freeze && (hi_options & HEAP_INSERT_FROZEN) == 0) if (cstate->freeze && (hi_options & HEAP_INSERT_FROZEN) == 0)
ereport(NOTICE, ereport(NOTICE,

View File

@ -26,8 +26,7 @@
/* "options" flag bits for heap_insert */ /* "options" flag bits for heap_insert */
#define HEAP_INSERT_SKIP_WAL 0x0001 #define HEAP_INSERT_SKIP_WAL 0x0001
#define HEAP_INSERT_SKIP_FSM 0x0002 #define HEAP_INSERT_SKIP_FSM 0x0002
#define HEAP_INSERT_COMMITTED 0x0004 #define HEAP_INSERT_FROZEN 0x0004
#define HEAP_INSERT_FROZEN 0x0008
typedef struct BulkInsertStateData *BulkInsertState; typedef struct BulkInsertStateData *BulkInsertState;

View File

@ -260,8 +260,8 @@ TRUNCATE vistest;
COPY vistest FROM stdin CSV; COPY vistest FROM stdin CSV;
SELECT * FROM vistest; SELECT * FROM vistest;
a a
--- ----
a a1
b b
(2 rows) (2 rows)
@ -270,19 +270,26 @@ TRUNCATE vistest;
COPY vistest FROM stdin CSV; COPY vistest FROM stdin CSV;
SELECT * FROM vistest; SELECT * FROM vistest;
a a
--- ----
d d1
e e
(2 rows) (2 rows)
COMMIT; COMMIT;
SELECT * FROM vistest;
a
----
d1
e
(2 rows)
BEGIN; BEGIN;
TRUNCATE vistest; TRUNCATE vistest;
COPY vistest FROM stdin CSV FREEZE; COPY vistest FROM stdin CSV FREEZE;
SELECT * FROM vistest; SELECT * FROM vistest;
a a
--- ----
a a2
b b
(2 rows) (2 rows)
@ -291,12 +298,19 @@ TRUNCATE vistest;
COPY vistest FROM stdin CSV FREEZE; COPY vistest FROM stdin CSV FREEZE;
SELECT * FROM vistest; SELECT * FROM vistest;
a a
--- ----
d d2
e e
(2 rows) (2 rows)
COMMIT; COMMIT;
SELECT * FROM vistest;
a
----
d2
e
(2 rows)
BEGIN; BEGIN;
TRUNCATE vistest; TRUNCATE vistest;
COPY vistest FROM stdin CSV FREEZE; COPY vistest FROM stdin CSV FREEZE;
@ -320,11 +334,11 @@ COPY vistest FROM stdin CSV FREEZE;
NOTICE: FREEZE option specified but pre-conditions not met NOTICE: FREEZE option specified but pre-conditions not met
SELECT * FROM vistest; SELECT * FROM vistest;
a a
--- ----
p p
g g
z z
d d3
e e
(5 rows) (5 rows)
@ -332,10 +346,10 @@ COMMIT;
CREATE FUNCTION truncate_in_subxact() RETURNS VOID AS CREATE FUNCTION truncate_in_subxact() RETURNS VOID AS
$$ $$
BEGIN BEGIN
SELECT * FROM nonexistent; TRUNCATE vistest;
EXCEPTION EXCEPTION
WHEN OTHERS THEN WHEN OTHERS THEN
TRUNCATE vistest; INSERT INTO vistest VALUES ('subxact failure');
END; END;
$$ language plpgsql; $$ language plpgsql;
BEGIN; BEGIN;
@ -349,16 +363,16 @@ SELECT truncate_in_subxact();
COPY vistest FROM stdin CSV FREEZE; COPY vistest FROM stdin CSV FREEZE;
SELECT * FROM vistest; SELECT * FROM vistest;
a a
--- ----
d d4
e e
(2 rows) (2 rows)
COMMIT; COMMIT;
SELECT * FROM vistest; SELECT * FROM vistest;
a a
--- ----
d d4
e e
(2 rows) (2 rows)

View File

@ -183,34 +183,37 @@ CREATE TABLE vistest (LIKE testeoc);
BEGIN; BEGIN;
TRUNCATE vistest; TRUNCATE vistest;
COPY vistest FROM stdin CSV; COPY vistest FROM stdin CSV;
a a1
b b
\. \.
SELECT * FROM vistest; SELECT * FROM vistest;
SAVEPOINT s1; SAVEPOINT s1;
TRUNCATE vistest; TRUNCATE vistest;
COPY vistest FROM stdin CSV; COPY vistest FROM stdin CSV;
d d1
e e
\. \.
SELECT * FROM vistest; SELECT * FROM vistest;
COMMIT; COMMIT;
SELECT * FROM vistest;
BEGIN; BEGIN;
TRUNCATE vistest; TRUNCATE vistest;
COPY vistest FROM stdin CSV FREEZE; COPY vistest FROM stdin CSV FREEZE;
a a2
b b
\. \.
SELECT * FROM vistest; SELECT * FROM vistest;
SAVEPOINT s1; SAVEPOINT s1;
TRUNCATE vistest; TRUNCATE vistest;
COPY vistest FROM stdin CSV FREEZE; COPY vistest FROM stdin CSV FREEZE;
d d2
e e
\. \.
SELECT * FROM vistest; SELECT * FROM vistest;
COMMIT; COMMIT;
SELECT * FROM vistest;
BEGIN; BEGIN;
TRUNCATE vistest; TRUNCATE vistest;
COPY vistest FROM stdin CSV FREEZE; COPY vistest FROM stdin CSV FREEZE;
@ -230,7 +233,7 @@ SAVEPOINT s1;
TRUNCATE vistest; TRUNCATE vistest;
ROLLBACK TO SAVEPOINT s1; ROLLBACK TO SAVEPOINT s1;
COPY vistest FROM stdin CSV FREEZE; COPY vistest FROM stdin CSV FREEZE;
d d3
e e
\. \.
SELECT * FROM vistest; SELECT * FROM vistest;
@ -238,17 +241,17 @@ COMMIT;
CREATE FUNCTION truncate_in_subxact() RETURNS VOID AS CREATE FUNCTION truncate_in_subxact() RETURNS VOID AS
$$ $$
BEGIN BEGIN
SELECT * FROM nonexistent; TRUNCATE vistest;
EXCEPTION EXCEPTION
WHEN OTHERS THEN WHEN OTHERS THEN
TRUNCATE vistest; INSERT INTO vistest VALUES ('subxact failure');
END; END;
$$ language plpgsql; $$ language plpgsql;
BEGIN; BEGIN;
INSERT INTO vistest VALUES ('z'); INSERT INTO vistest VALUES ('z');
SELECT truncate_in_subxact(); SELECT truncate_in_subxact();
COPY vistest FROM stdin CSV FREEZE; COPY vistest FROM stdin CSV FREEZE;
d d4
e e
\. \.
SELECT * FROM vistest; SELECT * FROM vistest;