Fix two bugs.

#1010789 : pg_reorg 1.1.0 and "unexpected toast relations"
#1010790 : reorg.get_index_keys() does not handle composite indexes
This commit is contained in:
Takahiro Itagaki 2010-04-21 09:25:20 +00:00
parent f3873ff55b
commit 78b0a0e374
9 changed files with 126 additions and 20 deletions

View File

@ -39,6 +39,13 @@ ALTER INDEX tbl_with_dropped_column_pkey SET (fillfactor = 75);
ALTER TABLE tbl_with_dropped_column CLUSTER ON tbl_with_dropped_column_pkey;
CREATE INDEX idx_c1c2 ON tbl_with_dropped_column (c1, c2) WITH (fillfactor = 75);
CREATE INDEX idx_c2c1 ON tbl_with_dropped_column (c2, c1);
CREATE TABLE tbl_with_dropped_toast (
i integer,
j integer,
t text,
PRIMARY KEY (i, j)
);
ALTER TABLE tbl_with_dropped_toast CLUSTER ON tbl_with_dropped_toast_pkey;
--
-- insert data
--
@ -59,6 +66,9 @@ ALTER TABLE tbl_with_dropped_column DROP COLUMN d1;
ALTER TABLE tbl_with_dropped_column DROP COLUMN d2;
ALTER TABLE tbl_with_dropped_column DROP COLUMN d3;
ALTER TABLE tbl_with_dropped_column ADD COLUMN c3 text;
INSERT INTO tbl_with_dropped_toast VALUES(1, 10, 'abc');
INSERT INTO tbl_with_dropped_toast VALUES(2, 20, sqrt(2::numeric(1000,999))::text || sqrt(3::numeric(1000,999))::text);
ALTER TABLE tbl_with_dropped_toast DROP COLUMN t;
--
-- before
--
@ -69,6 +79,13 @@ SELECT * FROM tbl_with_dropped_column;
c1 | 1 | c2 |
(2 rows)
SELECT * FROM tbl_with_dropped_toast;
i | j
---+----
1 | 10
2 | 20
(2 rows)
--
-- do reorg
--
@ -131,6 +148,15 @@ Indexes:
"idx_c1c2" btree (c1, c2) WITH (fillfactor=75)
"idx_c2c1" btree (c2, c1)
\d tbl_with_dropped_toast
Table "public.tbl_with_dropped_toast"
Column | Type | Modifiers
--------+---------+-----------
i | integer | not null
j | integer | not null
Indexes:
"tbl_with_dropped_toast_pkey" PRIMARY KEY, btree (i, j) CLUSTER
SELECT col1, to_char(col2, 'YYYY-MM-DD HH24:MI:SS'), ","")" FROM tbl_cluster;
col1 | to_char | ,")
------+---------------------+------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------
@ -169,6 +195,33 @@ SELECT * FROM tbl_with_dropped_column;
c1 | 2 | c2 |
(2 rows)
SELECT * FROM tbl_with_dropped_toast;
i | j
---+----
1 | 10
2 | 20
(2 rows)
--
-- check broken links or orphan toast relations
--
SELECT oid, relname
FROM pg_class
WHERE relkind = 't'
AND oid NOT IN (SELECT reltoastrelid FROM pg_class WHERE relkind = 'r');
oid | relname
-----+---------
(0 rows)
SELECT oid, relname
FROM pg_class
WHERE relkind = 'r'
AND reltoastrelid <> 0
AND reltoastrelid NOT IN (SELECT oid FROM pg_class WHERE relkind = 't');
oid | relname
-----+---------
(0 rows)
--
-- clean up
--

View File

@ -8,7 +8,7 @@
* @brief Client Modules
*/
const char *PROGRAM_VERSION = "1.1.0";
const char *PROGRAM_VERSION = "1.1.1";
const char *PROGRAM_URL = "http://reorg.projects.postgresql.org/";
const char *PROGRAM_EMAIL = "reorg-general@lists.pgfoundry.org";

View File

@ -273,6 +273,7 @@ parse_int64(const char *value, int64 *result)
#elif defined(HAVE_LONG_INT_64)
val = strtol(value, &endptr, 0);
#elif defined(HAVE_LONG_LONG_INT_64)
val = strtoll(value, &endptr, 0);
#else
val = strtol(value, &endptr, 0);
#endif

View File

@ -47,6 +47,14 @@ ALTER TABLE tbl_with_dropped_column CLUSTER ON tbl_with_dropped_column_pkey;
CREATE INDEX idx_c1c2 ON tbl_with_dropped_column (c1, c2) WITH (fillfactor = 75);
CREATE INDEX idx_c2c1 ON tbl_with_dropped_column (c2, c1);
CREATE TABLE tbl_with_dropped_toast (
i integer,
j integer,
t text,
PRIMARY KEY (i, j)
);
ALTER TABLE tbl_with_dropped_toast CLUSTER ON tbl_with_dropped_toast_pkey;
--
-- insert data
--
@ -72,11 +80,16 @@ ALTER TABLE tbl_with_dropped_column DROP COLUMN d1;
ALTER TABLE tbl_with_dropped_column DROP COLUMN d2;
ALTER TABLE tbl_with_dropped_column DROP COLUMN d3;
ALTER TABLE tbl_with_dropped_column ADD COLUMN c3 text;
INSERT INTO tbl_with_dropped_toast VALUES(1, 10, 'abc');
INSERT INTO tbl_with_dropped_toast VALUES(2, 20, sqrt(2::numeric(1000,999))::text || sqrt(3::numeric(1000,999))::text);
ALTER TABLE tbl_with_dropped_toast DROP COLUMN t;
--
-- before
--
SELECT * FROM tbl_with_dropped_column;
SELECT * FROM tbl_with_dropped_toast;
--
-- do reorg
@ -95,12 +108,28 @@ SELECT * FROM tbl_with_dropped_column;
\d tbl_only_ckey
\d tbl_only_pkey
\d tbl_with_dropped_column
\d tbl_with_dropped_toast
SELECT col1, to_char(col2, 'YYYY-MM-DD HH24:MI:SS'), ","")" FROM tbl_cluster;
SELECT * FROM tbl_only_ckey ORDER BY 1;
SELECT * FROM tbl_only_pkey ORDER BY 1;
SELECT * FROM tbl_gistkey ORDER BY 1;
SELECT * FROM tbl_with_dropped_column;
SELECT * FROM tbl_with_dropped_toast;
--
-- check broken links or orphan toast relations
--
SELECT oid, relname
FROM pg_class
WHERE relkind = 't'
AND oid NOT IN (SELECT reltoastrelid FROM pg_class WHERE relkind = 'r');
SELECT oid, relname
FROM pg_class
WHERE relkind = 'r'
AND reltoastrelid <> 0
AND reltoastrelid NOT IN (SELECT oid FROM pg_class WHERE relkind = 't');
--
-- clean up

View File

@ -46,7 +46,7 @@ VACUUM を行うスクリプトが付属しており、"より良い vacuumdb"
<h2>ドキュメント</h2>
<ul>
<li><a href="pg_reorg-ja.html">pg_reorg 1.1.0 ドキュメント</a></li>
<li><a href="pg_reorg-ja.html">pg_reorg 1.1.1 ドキュメント</a></li>
<li><a href="pg_batch-ja.html">pg_batch 1.2.0 ドキュメント</a></li>
</ul>

View File

@ -48,8 +48,8 @@ where you can find <a href="http://pgfoundry.org/frs/?group_id=1000411">download
<h2>Documentation</h2>
<ul>
<li><a href="pg_reorg.html">pg_reorg 1.1.0 documentation</a></li>
<li><a href="pg_batch-ja.html">pg_batch 1.2.0 documentation</a> (ja)</li>
<li><a href="pg_reorg.html">pg_reorg 1.1.1 documentation</a></li>
<li><a href="pg_batch.html">pg_batch 1.2.0 documentation</a></li>
</ul>
<h2>Execution time</h2>

View File

@ -8,7 +8,7 @@
</head>
<body>
<h1 id="pg_reorg">pg_reorg 1.1.0</h1>
<h1 id="pg_reorg">pg_reorg 1.1.1</h1>
<div class="navigation">
<a href="index-ja.html">Top</a> &gt;
<a href="pg_reorg-ja.html">pg_reorg</a>

View File

@ -8,7 +8,7 @@
</head>
<body>
<h1 id="pg_reorg">pg_reorg 1.1.0</h1>
<h1 id="pg_reorg">pg_reorg 1.1.1</h1>
<div class="navigation">
<a href="index.html">Top</a> &gt;
<a href="pg_reorg.html">pg_reorg</a>
@ -67,7 +67,7 @@ See also "<a href="#options">Options</a>" for details.</p>
<h2 id="description">Description</h2>
<p>pg_reorg is an utility program to reorganize tables in PostgreSQL databases.
Unlike <a href="http://www.postgresql.jp/document/current/html/app-clusterdb.html">clusterdb</a>, it doesn't block any selections and updates during reorganization.
Unlike <a href="http://developer.postgresql.org/pgdocs/postgres/app-clusterdb.html">clusterdb</a>, it doesn't block any selections and updates during reorganization.
You can choose one of the following methods to reorganize.</p>
<ul>
<li>Online CLUSTER (ordered by cluster index)</li>

View File

@ -75,7 +75,7 @@ static void RenameRelationInternal(Oid myrelid, const char *newrelname, Oid name
Datum
reorg_version(PG_FUNCTION_ARGS)
{
return CStringGetTextDatum("pg_reorg 1.1.0");
return CStringGetTextDatum("pg_reorg 1.1.1");
}
/**
@ -468,6 +468,12 @@ reorg_get_index_keys(PG_FUNCTION_ARGS)
int nattr;
parse_indexdef(&stmt, index, table);
elog(DEBUG2, "indexdef.create = %s", stmt.create);
elog(DEBUG2, "indexdef.index = %s", stmt.index);
elog(DEBUG2, "indexdef.table = %s", stmt.table);
elog(DEBUG2, "indexdef.type = %s", stmt.type);
elog(DEBUG2, "indexdef.columns = %s", stmt.columns);
elog(DEBUG2, "indexdef.options = %s", stmt.options);
/*
* FIXME: this is very unreliable implementation but I don't want to
@ -482,6 +488,8 @@ reorg_get_index_keys(PG_FUNCTION_ARGS)
char *opcname;
token = next;
while (isspace((unsigned char) *token))
token++;
next = skip_until(index, next, ',');
opcname = token + strlen(token);
@ -555,7 +563,7 @@ reorg_get_index_keys(PG_FUNCTION_ARGS)
else
appendStringInfoString(&str, token);
if (next)
appendStringInfoChar(&str, ',');
appendStringInfoString(&str, ", ");
}
if (indexRel != NULL)
@ -777,16 +785,6 @@ reorg_swap(PG_FUNCTION_ARGS)
natts1 = getint16(tuple, desc, 8);
natts2 = getint16(tuple, desc, 9);;
/* should be all-or-nothing */
if ((reltoastrelid1 == InvalidOid || reltoastidxid1 == InvalidOid ||
reltoastrelid2 == InvalidOid || reltoastidxid2 == InvalidOid) &&
(reltoastrelid1 != InvalidOid || reltoastidxid1 != InvalidOid ||
reltoastrelid2 != InvalidOid || reltoastidxid2 != InvalidOid))
{
elog(ERROR, "reorg_swap : unexpected toast relations (T1=%u, I1=%u, T2=%u, I2=%u",
reltoastrelid1, reltoastidxid1, reltoastrelid2, reltoastidxid2);
}
/* change owner of new relation to original owner */
if (owner1 != owner2)
{
@ -848,7 +846,32 @@ reorg_swap(PG_FUNCTION_ARGS)
}
/* swap names for toast tables and toast indexes */
if (reltoastrelid1 != InvalidOid)
if (reltoastrelid1 == InvalidOid)
{
if (reltoastidxid1 != InvalidOid ||
reltoastrelid2 != InvalidOid ||
reltoastidxid2 != InvalidOid)
elog(ERROR, "reorg_swap : unexpected toast relations (T1=%u, I1=%u, T2=%u, I2=%u",
reltoastrelid1, reltoastidxid1, reltoastrelid2, reltoastidxid2);
/* do nothing */
}
else if (reltoastrelid2 == InvalidOid)
{
char name[NAMEDATALEN];
if (reltoastidxid1 == InvalidOid ||
reltoastidxid2 != InvalidOid)
elog(ERROR, "reorg_swap : unexpected toast relations (T1=%u, I1=%u, T2=%u, I2=%u",
reltoastrelid1, reltoastidxid1, reltoastrelid2, reltoastidxid2);
/* rename X to Y */
snprintf(name, NAMEDATALEN, "pg_toast_%u", oid2);
RenameRelationInternal(reltoastrelid1, name, PG_TOAST_NAMESPACE);
snprintf(name, NAMEDATALEN, "pg_toast_%u_index", oid2);
RenameRelationInternal(reltoastidxid1, name, PG_TOAST_NAMESPACE);
CommandCounterIncrement();
}
else if (reltoastrelid1 != InvalidOid)
{
char name[NAMEDATALEN];
int pid = getpid();