Skip to content

Commit

Permalink
Fix a bug that valid tables/columns are removed by VACUUM/ANALYZE
Browse files Browse the repository at this point in the history
It's caused after you use REINDEX.

[groonga-dev,03850]

Reported by Naoki Takami. Thanks!!!
  • Loading branch information
kou committed Feb 2, 2016
1 parent 67d2eab commit ef48f9e
Show file tree
Hide file tree
Showing 5 changed files with 137 additions and 22 deletions.
62 changes: 62 additions & 0 deletions expected/reindex/analyze.out
Original file line number Diff line number Diff line change
@@ -0,0 +1,62 @@
CREATE TABLE memos (
id integer,
content text
);
INSERT INTO memos VALUES (1, 'PostgreSQL is a RDBMS.');
INSERT INTO memos VALUES (2, 'Groonga is fast full text search engine.');
INSERT INTO memos VALUES (3, 'PGroonga is a PostgreSQL extension that uses Groonga.');
CREATE INDEX pgrn_index ON memos USING pgroonga (content);
SELECT pgroonga.command(
'object_exist ' ||
'Sources' || (SELECT oid
FROM pg_class
WHERE relname = 'pgrn_index'))::jsonb->1;
?column?
----------
true
(1 row)

SELECT pgroonga.command(
'object_exist ' ||
'Sources' || (SELECT relfilenode
FROM pg_class
WHERE relname = 'pgrn_index'))::jsonb->1;
?column?
----------
true
(1 row)

REINDEX INDEX pgrn_index;
ANALYZE;
SELECT pgroonga.command(
'object_exist ' ||
'Sources' || (SELECT oid
FROM pg_class
WHERE relname = 'pgrn_index'))::jsonb->1;
?column?
----------
false
(1 row)

SELECT pgroonga.command(
'object_exist ' ||
'Sources' || (SELECT relfilenode
FROM pg_class
WHERE relname = 'pgrn_index'))::jsonb->1;
?column?
----------
true
(1 row)

SET enable_seqscan = off;
SET enable_indexscan = on;
SET enable_bitmapscan = off;
SELECT id, content
FROM memos
WHERE content %% 'PGroonga' AND content %% 'Groonga';
id | content
----+-------------------------------------------------------
3 | PGroonga is a PostgreSQL extension that uses Groonga.
(1 row)

DROP TABLE memos;
46 changes: 46 additions & 0 deletions sql/reindex/analyze.sql
Original file line number Diff line number Diff line change
@@ -0,0 +1,46 @@
CREATE TABLE memos (
id integer,
content text
);

INSERT INTO memos VALUES (1, 'PostgreSQL is a RDBMS.');
INSERT INTO memos VALUES (2, 'Groonga is fast full text search engine.');
INSERT INTO memos VALUES (3, 'PGroonga is a PostgreSQL extension that uses Groonga.');

CREATE INDEX pgrn_index ON memos USING pgroonga (content);

SELECT pgroonga.command(
'object_exist ' ||
'Sources' || (SELECT oid
FROM pg_class
WHERE relname = 'pgrn_index'))::jsonb->1;
SELECT pgroonga.command(
'object_exist ' ||
'Sources' || (SELECT relfilenode
FROM pg_class
WHERE relname = 'pgrn_index'))::jsonb->1;

REINDEX INDEX pgrn_index;

ANALYZE;

SELECT pgroonga.command(
'object_exist ' ||
'Sources' || (SELECT oid
FROM pg_class
WHERE relname = 'pgrn_index'))::jsonb->1;
SELECT pgroonga.command(
'object_exist ' ||
'Sources' || (SELECT relfilenode
FROM pg_class
WHERE relname = 'pgrn_index'))::jsonb->1;

SET enable_seqscan = off;
SET enable_indexscan = on;
SET enable_bitmapscan = off;

SELECT id, content
FROM memos
WHERE content %% 'PGroonga' AND content %% 'Groonga';

DROP TABLE memos;
20 changes: 10 additions & 10 deletions src/pgrn_jsonb.c
Original file line number Diff line number Diff line change
Expand Up @@ -1334,36 +1334,36 @@ PGrnRemoveJSONValueLexiconTable(const char *typeName, unsigned int relationID)
#endif

void
PGrnJSONBRemoveUnusedTables(Oid relationID)
PGrnJSONBRemoveUnusedTables(Oid relationFileNodeID)
{
#ifdef JSONBOID
PGrnRemoveJSONValueLexiconTable("FullTextSearch", relationID);
PGrnRemoveJSONValueLexiconTable("String", relationID);
PGrnRemoveJSONValueLexiconTable("Number", relationID);
PGrnRemoveJSONValueLexiconTable("Boolean", relationID);
PGrnRemoveJSONValueLexiconTable("Size", relationID);
PGrnRemoveJSONValueLexiconTable("FullTextSearch", relationFileNodeID);
PGrnRemoveJSONValueLexiconTable("String", relationFileNodeID);
PGrnRemoveJSONValueLexiconTable("Number", relationFileNodeID);
PGrnRemoveJSONValueLexiconTable("Boolean", relationFileNodeID);
PGrnRemoveJSONValueLexiconTable("Size", relationFileNodeID);

{
char name[GRN_TABLE_MAX_KEY_SIZE];

snprintf(name, sizeof(name),
PGrnJSONPathsTableNameFormat ".%s",
relationID, 0, PGrnIndexColumnName);
relationFileNodeID, 0, PGrnIndexColumnName);
PGrnRemoveObject(name);

snprintf(name, sizeof(name),
PGrnJSONValuesTableNameFormat,
relationID, 0);
relationFileNodeID, 0);
PGrnRemoveObject(name);

snprintf(name, sizeof(name),
PGrnJSONPathsTableNameFormat,
relationID, 0);
relationFileNodeID, 0);
PGrnRemoveObject(name);

snprintf(name, sizeof(name),
PGrnJSONTypesTableNameFormat,
relationID, 0);
relationFileNodeID, 0);
PGrnRemoveObject(name);
}
#endif
Expand Down
2 changes: 1 addition & 1 deletion src/pgrn_jsonb.h
Original file line number Diff line number Diff line change
Expand Up @@ -42,4 +42,4 @@ void PGrnJSONBBulkDeleteInit(PGrnJSONBBulkDeleteData *data);
void PGrnJSONBBulkDeleteRecord(PGrnJSONBBulkDeleteData *data);
void PGrnJSONBBulkDeleteFin(PGrnJSONBBulkDeleteData *data);

void PGrnJSONBRemoveUnusedTables(Oid relationID);
void PGrnJSONBRemoveUnusedTables(Oid relationFileNodeID);
29 changes: 18 additions & 11 deletions src/pgroonga.c
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,7 @@
#include <utils/array.h>
#include <utils/builtins.h>
#include <utils/lsyscache.h>
#include <utils/relfilenodemap.h>
#include <utils/selfuncs.h>
#include <utils/syscache.h>
#include <utils/timestamp.h>
Expand Down Expand Up @@ -3134,42 +3135,48 @@ PGrnRemoveUnusedTables(void)
char *name;
char *nameEnd;
int nameSize;
Oid relationFileNodeID;
Oid relationID;
Relation relation;
unsigned int i;

nameSize = grn_table_cursor_get_key(ctx, cursor, (void **)&name);
nameEnd = name + nameSize;
relationID = strtol(name + strlen(min), &nameEnd, 10);
relationFileNodeID = strtol(name + strlen(min), &nameEnd, 10);
if (nameEnd[0] == '.')
continue;

LockRelationOid(relationID, AccessShareLock);
relation = RelationIdGetRelation(relationID);
if (RelationIsValid(relation))
relationID = RelidByRelfilenode(MyDatabaseTableSpace,
relationFileNodeID);
if (OidIsValid(relationID))
{
RelationClose(relation);
UnlockRelationOid(relationID, AccessShareLock);
continue;
Relation relation;
LockRelationOid(relationID, AccessShareLock);
relation = RelationIdGetRelation(relationID);
if (RelationIsValid(relation))
{
RelationClose(relation);
UnlockRelationOid(relationID, AccessShareLock);
continue;
}
}

for (i = 0; true; i++)
{
char tableName[GRN_TABLE_MAX_KEY_SIZE];
snprintf(tableName, sizeof(tableName),
PGrnLexiconNameFormat, relationID, i);
PGrnLexiconNameFormat, relationFileNodeID, i);
if (!PGrnRemoveObject(tableName))
break;
}

{
char tableName[GRN_TABLE_MAX_KEY_SIZE];
snprintf(tableName, sizeof(tableName),
PGrnSourcesTableNameFormat, relationID);
PGrnSourcesTableNameFormat, relationFileNodeID);
PGrnRemoveObject(tableName);
}

PGrnJSONBRemoveUnusedTables(relationID);
PGrnJSONBRemoveUnusedTables(relationFileNodeID);
}
grn_table_cursor_close(ctx, cursor);
}
Expand Down

0 comments on commit ef48f9e

Please sign in to comment.