diff options
Diffstat (limited to 'src/bin/pg_dump/pg_dumpall.c')
-rw-r--r-- | src/bin/pg_dump/pg_dumpall.c | 78 |
1 files changed, 78 insertions, 0 deletions
diff --git a/src/bin/pg_dump/pg_dumpall.c b/src/bin/pg_dump/pg_dumpall.c index 44c33508877..773bbdd04c1 100644 --- a/src/bin/pg_dump/pg_dumpall.c +++ b/src/bin/pg_dump/pg_dumpall.c @@ -52,6 +52,8 @@ static PGconn *connectDatabase(const char *dbname, const char *connstr, const ch static char *constructConnStr(const char **keywords, const char **values); static PGresult *executeQuery(PGconn *conn, const char *query); static void executeCommand(PGconn *conn, const char *query); +static void expand_dbname_patterns(PGconn *conn, SimpleStringList *patterns, + SimpleStringList *names); static char pg_dump_bin[MAXPGPATH]; static const char *progname; @@ -87,6 +89,9 @@ static char role_catalog[10]; static FILE *OPF; static char *filename = NULL; +static SimpleStringList database_exclude_patterns = {NULL, NULL}; +static SimpleStringList database_exclude_names = {NULL, NULL}; + #define exit_nicely(code) exit(code) int @@ -123,6 +128,7 @@ main(int argc, char *argv[]) {"column-inserts", no_argument, &column_inserts, 1}, {"disable-dollar-quoting", no_argument, &disable_dollar_quoting, 1}, {"disable-triggers", no_argument, &disable_triggers, 1}, + {"exclude-database", required_argument, NULL, 6}, {"extra-float-digits", required_argument, NULL, 5}, {"if-exists", no_argument, &if_exists, 1}, {"inserts", no_argument, &inserts, 1}, @@ -324,6 +330,10 @@ main(int argc, char *argv[]) appendShellString(pgdumpopts, optarg); break; + case 6: + simple_string_list_append(&database_exclude_patterns, optarg); + break; + default: fprintf(stderr, _("Try \"%s --help\" for more information.\n"), progname); exit_nicely(1); @@ -340,6 +350,16 @@ main(int argc, char *argv[]) exit_nicely(1); } + if (database_exclude_patterns.head != NULL && + (globals_only || roles_only || tablespaces_only)) + { + fprintf(stderr, _("%s: option --exclude-database cannot be used together with -g/--globals-only, -r/--roles-only or -t/--tablespaces-only\n"), + progname); + fprintf(stderr, _("Try \"%s --help\" for more information.\n"), + progname); + exit_nicely(1); + } + /* Make sure the user hasn't specified a mix of globals-only options */ if (globals_only && roles_only) { @@ -455,6 +475,12 @@ main(int argc, char *argv[]) } /* + * Get a list of database names that match the exclude patterns + */ + expand_dbname_patterns(conn, &database_exclude_patterns, + &database_exclude_names); + + /* * Open the output file if required, otherwise use stdout */ if (filename) @@ -620,6 +646,7 @@ help(void) printf(_(" --column-inserts dump data as INSERT commands with column names\n")); printf(_(" --disable-dollar-quoting disable dollar quoting, use SQL standard quoting\n")); printf(_(" --disable-triggers disable triggers during data-only restore\n")); + printf(_(" --exclude-database=PATTERN exclude databases whose name matches PATTERN\n")); printf(_(" --extra-float-digits=NUM override default setting for extra_float_digits\n")); printf(_(" --if-exists use IF EXISTS when dropping objects\n")); printf(_(" --inserts dump data as INSERT commands, rather than COPY\n")); @@ -1358,6 +1385,48 @@ dumpUserConfig(PGconn *conn, const char *username) destroyPQExpBuffer(buf); } +/* + * Find a list of database names that match the given patterns. + * See also expand_table_name_patterns() in pg_dump.c + */ +static void +expand_dbname_patterns(PGconn *conn, + SimpleStringList *patterns, + SimpleStringList *names) +{ + PQExpBuffer query; + PGresult *res; + + if (patterns->head == NULL) + return; /* nothing to do */ + + query = createPQExpBuffer(); + + /* + * The loop below runs multiple SELECTs, which might sometimes result in + * duplicate entries in the name list, but we don't care, since all + * we're going to do is test membership of the list. + */ + + for (SimpleStringListCell *cell = patterns->head; cell; cell = cell->next) + { + appendPQExpBuffer(query, + "SELECT datname FROM pg_catalog.pg_database n\n"); + processSQLNamePattern(conn, query, cell->val, false, + false, NULL, "datname", NULL, NULL); + + res = executeQuery(conn, query->data); + for (int i = 0; i < PQntuples(res); i++) + { + simple_string_list_append(names, PQgetvalue(res, i, 0)); + } + + PQclear(res); + resetPQExpBuffer(query); + } + + destroyPQExpBuffer(query); +} /* * Dump contents of databases. @@ -1395,6 +1464,15 @@ dumpDatabases(PGconn *conn) if (strcmp(dbname, "template0") == 0) continue; + /* Skip any explicitly excluded database */ + if (simple_string_list_member(&database_exclude_names, dbname)) + { + if (verbose) + fprintf(stderr, _("%s: excluding database \"%s\"...\n"), + progname, dbname); + continue; + } + if (verbose) fprintf(stderr, _("%s: dumping database \"%s\"...\n"), progname, dbname); |