Skip to content

Commit ad75dcf

Browse files
schmiddydvarrazzo
authored andcommitted
Allow multiple --table options to be specified on the command-line.
Per Issue #18. SimpleStringList code borrowed from pg_dump and a pending patch to add similar functionality to pg_restore, clusterdb, vacuumdb, and reindexdb. The error handling in reorg_one_table() could still be much improved, so that an error processing a single table doesn't cause pg_reorg to necessarily bail out and skip further tables, but I'll leave that for another day.
1 parent ad00eb1 commit ad75dcf

File tree

5 files changed

+83
-16
lines changed

5 files changed

+83
-16
lines changed

bin/pg_repack.c

Lines changed: 20 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -125,12 +125,12 @@ static bool sqlstate_equals(PGresult *res, const char *state)
125125
return strcmp(PQresultErrorField(res, PG_DIAG_SQLSTATE), state) == 0;
126126
}
127127

128-
static bool analyze = true;
129-
static bool alldb = false;
130-
static bool noorder = false;
131-
static char *table = NULL;
132-
static char *orderby = NULL;
133-
static int wait_timeout = 60; /* in seconds */
128+
static bool analyze = true;
129+
static bool alldb = false;
130+
static bool noorder = false;
131+
static SimpleStringList table_list = {NULL, NULL};
132+
static char *orderby = NULL;
133+
static int wait_timeout = 60; /* in seconds */
134134

135135
/* buffer should have at least 11 bytes */
136136
static char *
@@ -143,7 +143,7 @@ utoa(unsigned int value, char *buffer)
143143
static pgut_option options[] =
144144
{
145145
{ 'b', 'a', "all", &alldb },
146-
{ 's', 't', "table", &table },
146+
{ 'l', 't', "table", &table_list },
147147
{ 'b', 'n', "no-order", &noorder },
148148
{ 's', 'o', "order-by", &orderby },
149149
{ 'i', 'T', "wait-timeout", &wait_timeout },
@@ -154,7 +154,8 @@ static pgut_option options[] =
154154
int
155155
main(int argc, char *argv[])
156156
{
157-
int i;
157+
int i;
158+
SimpleStringListCell *cell;
158159

159160
i = pgut_getopt(argc, argv, options);
160161

@@ -170,18 +171,25 @@ main(int argc, char *argv[])
170171

171172
if (alldb)
172173
{
173-
if (table)
174+
if (table_list.head != NULL)
174175
ereport(ERROR,
175176
(errcode(EINVAL),
176177
errmsg("cannot repack a specific table in all databases")));
177178
repack_all_databases(orderby);
178179
}
179180
else
180181
{
181-
if (!repack_one_database(orderby, table))
182+
if (table_list.head != NULL)
183+
{
184+
for (cell = table_list.head; cell; cell = cell->next)
185+
{
186+
repack_one_database(orderby, cell->val);
187+
}
188+
}
189+
else if (!repack_one_database(orderby, NULL))
182190
ereport(ERROR,
183-
(errcode(ENOENT),
184-
errmsg("%s is not installed", PROGRAM_NAME)));
191+
(errcode(ENOENT),
192+
errmsg("%s is not installed", PROGRAM_NAME)));
185193
}
186194

187195
return 0;

bin/pgut/pgut-fe.c

Lines changed: 9 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -144,9 +144,12 @@ pgut_setopt(pgut_option *opt, const char *optarg, pgut_optsrc src)
144144
/* high prior value has been set already. */
145145
return;
146146
}
147-
else if (src >= SOURCE_CMDLINE && opt->source >= src)
147+
else if (src >= SOURCE_CMDLINE && opt->source >= src && opt->type != 'l')
148148
{
149-
/* duplicated option in command line */
149+
/* duplicated option in command line -- don't worry if the option
150+
* type is 'l' i.e. SimpleStringList, since we are allowed to have
151+
* multiples of these.
152+
*/
150153
message = "specified only once";
151154
}
152155
else
@@ -177,6 +180,10 @@ pgut_setopt(pgut_option *opt, const char *optarg, pgut_optsrc src)
177180
return;
178181
message = "a 32bit signed integer";
179182
break;
183+
case 'l':
184+
message = "a List";
185+
simple_string_list_append(opt->var, optarg);
186+
return;
180187
case 'u':
181188
if (parse_uint32(optarg, opt->var))
182189
return;

bin/pgut/pgut-fe.h

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -25,13 +25,14 @@ typedef enum pgut_optsrc
2525
* type:
2626
* b: bool (true)
2727
* B: bool (false)
28-
* f: pgut_optfn
28+
* f: pgut_optfn
2929
* i: 32bit signed integer
30+
* l: StringList
3031
* u: 32bit unsigned integer
3132
* I: 64bit signed integer
3233
* U: 64bit unsigned integer
3334
* s: string
34-
* t: time_t
35+
* t: time_t
3536
* y: YesNo (YES)
3637
* Y: YesNo (NO)
3738
*/

bin/pgut/pgut.c

Lines changed: 34 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -384,6 +384,40 @@ parse_time(const char *value, time_t *time)
384384
return true;
385385
}
386386

387+
/* Append the given string `val` to the `list` */
388+
void
389+
simple_string_list_append(SimpleStringList *list, const char *val)
390+
{
391+
SimpleStringListCell *cell;
392+
393+
/* this calculation correctly accounts for the null trailing byte */
394+
cell = (SimpleStringListCell *)
395+
pgut_malloc(sizeof(SimpleStringListCell) + strlen(val));
396+
cell->next = NULL;
397+
strcpy(cell->val, val);
398+
399+
if (list->tail)
400+
list->tail->next = cell;
401+
else
402+
list->head = cell;
403+
list->tail = cell;
404+
}
405+
406+
/* Test whether `val` is in the given `list` */
407+
bool
408+
simple_string_list_member(SimpleStringList *list, const char *val)
409+
{
410+
SimpleStringListCell *cell;
411+
412+
for (cell = list->head; cell; cell = cell->next)
413+
{
414+
if (strcmp(cell->val, val) == 0)
415+
return true;
416+
}
417+
return false;
418+
}
419+
420+
387421
static char *
388422
prompt_for_password(void)
389423
{

bin/pgut/pgut.h

Lines changed: 17 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -171,6 +171,23 @@ extern bool parse_time(const char *value, time_t *time);
171171
#define ToLower(c) (tolower((unsigned char)(c)))
172172
#define ToUpper(c) (toupper((unsigned char)(c)))
173173

174+
/* linked list of string values and helper functions, stolen from pg_dump. */
175+
typedef struct SimpleStringListCell
176+
{
177+
struct SimpleStringListCell *next;
178+
char val[1]; /* VARIABLE LENGTH FIELD */
179+
} SimpleStringListCell;
180+
181+
typedef struct SimpleStringList
182+
{
183+
SimpleStringListCell *head;
184+
SimpleStringListCell *tail;
185+
} SimpleStringList;
186+
187+
extern void simple_string_list_append(SimpleStringList *list, const char *val);
188+
extern bool simple_string_list_member(SimpleStringList *list, const char *val);
189+
190+
174191
/*
175192
* socket operations
176193
*/

0 commit comments

Comments
 (0)