Skip to content

Commit 0144cc4

Browse files
author
otsuka.knj@gmail.com
committed
- Fix possible broken backup which is getting from standby.
Use --standby-host and --standby-port, if backup is getting from standby. - Add --hard-copy restore option. The option can be used to copy archive WAL to archive directory instead of symlink. git-svn-id: http://pg-rman.googlecode.com/svn/trunk@77 182aca00-e38e-11de-a668-6fd11605f5ce
1 parent 40fb356 commit 0144cc4

File tree

15 files changed

+345
-95
lines changed

15 files changed

+345
-95
lines changed

SPECS/pg_rman90.spec

Lines changed: 4 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
# SPEC file for pg_rman
2-
# Copyright(C) 2009-2010 NIPPON TELEGRAPH AND TELEPHONE CORPORATION
2+
# Copyright(C) 2009-2013 NIPPON TELEGRAPH AND TELEPHONE CORPORATION
33

44
%define _pgdir /usr/pgsql-9.0
55
%define _bindir %{_pgdir}/bin
@@ -9,7 +9,7 @@
99
## Set general information for pg_rman.
1010
Summary: Backup and Recovery Tool for PostgreSQL
1111
Name: pg_rman
12-
Version: 1.2.5
12+
Version: 1.2.6
1313
Release: 1%{?dist}
1414
License: BSD
1515
Group: Applications/Databases
@@ -58,7 +58,8 @@ rm -rf %{buildroot}
5858

5959
# History of pg_rman.
6060
%changelog
61+
* Mon Sep 2 2013 - NTT OSS Center <otsuka.kenji@lab.ntt.co.jp> 1.2.6-1
62+
- Update to 1.2.6
6163
* Wed Nov 10 2010 - NTT OSS Center <tomonari.katsumata@oss.ntt.co.jp> 1.2.0-1
6264
* Wed Dec 9 2009 - NTT OSS Center <itagaki.takahiro@oss.ntt.co.jp> 1.1.1-1
6365
- Initial cut for 1.1.1
64-

SPECS/pg_rman91.spec

Lines changed: 4 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
# SPEC file for pg_rman
2-
# Copyright(C) 2009-2011 NIPPON TELEGRAPH AND TELEPHONE CORPORATION
2+
# Copyright(C) 2009-2013 NIPPON TELEGRAPH AND TELEPHONE CORPORATION
33

44
%define _pgdir /usr/pgsql-9.1
55
%define _bindir %{_pgdir}/bin
@@ -9,7 +9,7 @@
99
## Set general information for pg_rman.
1010
Summary: Backup and Recovery Tool for PostgreSQL
1111
Name: pg_rman
12-
Version: 1.2.5
12+
Version: 1.2.6
1313
Release: 1%{?dist}
1414
License: BSD
1515
Group: Applications/Databases
@@ -58,7 +58,8 @@ rm -rf %{buildroot}
5858

5959
# History of pg_rman.
6060
%changelog
61+
* Mon Sep 2 2013 - NTT OSS Center <otsuka.kenji@lab.ntt.co.jp> 1.2.6-1
62+
- Update to 1.2.6
6163
* Wed Nov 10 2010 - NTT OSS Center <tomonari.katsumata@oss.ntt.co.jp> 1.2.0-1
6264
* Wed Dec 9 2009 - NTT OSS Center <itagaki.takahiro@oss.ntt.co.jp> 1.1.1-1
6365
- Initial cut for 1.1.1
64-

SPECS/pg_rman92.spec

Lines changed: 4 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
# SPEC file for pg_rman
2-
# Copyright(C) 2009-2012 NIPPON TELEGRAPH AND TELEPHONE CORPORATION
2+
# Copyright(C) 2009-2013 NIPPON TELEGRAPH AND TELEPHONE CORPORATION
33

44
%define _pgdir /usr/pgsql-9.2
55
%define _bindir %{_pgdir}/bin
@@ -9,7 +9,7 @@
99
## Set general information for pg_rman.
1010
Summary: Backup and Recovery Tool for PostgreSQL
1111
Name: pg_rman
12-
Version: 1.2.5
12+
Version: 1.2.6
1313
Release: 1%{?dist}
1414
License: BSD
1515
Group: Applications/Databases
@@ -58,7 +58,8 @@ rm -rf %{buildroot}
5858

5959
# History of pg_rman.
6060
%changelog
61+
* Mon Sep 2 2013 - NTT OSS Center <otsuka.kenji@lab.ntt.co.jp> 1.2.6-1
62+
- Update to 1.2.6
6163
* Wed Nov 10 2010 - NTT OSS Center <tomonari.katsumata@oss.ntt.co.jp> 1.2.0-1
6264
* Wed Dec 9 2009 - NTT OSS Center <itagaki.takahiro@oss.ntt.co.jp> 1.1.1-1
6365
- Initial cut for 1.1.1
64-

backup.c

Lines changed: 149 additions & 21 deletions
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,7 @@
22
*
33
* backup.c: backup DB cluster, archived WAL, serverlog.
44
*
5-
* Copyright (c) 2009-2011, NIPPON TELEGRAPH AND TELEPHONE CORPORATION
5+
* Copyright (c) 2009-2013, NIPPON TELEGRAPH AND TELEPHONE CORPORATION
66
*
77
*-------------------------------------------------------------------------
88
*/
@@ -33,20 +33,22 @@ static void delete_old_files(const char *root, parray *files, int keep_files,
3333
int keep_days, int server_version, bool is_arclog);
3434
static void backup_files(const char *from_root, const char *to_root,
3535
parray *files, parray *prev_files, const XLogRecPtr *lsn, bool compress, const char *prefix);
36-
static parray *do_backup_database(parray *backup_list, bool smooth_checkpoint);
36+
static parray *do_backup_database(parray *backup_list, pgBackupOption bkupopt);
3737
static parray *do_backup_arclog(parray *backup_list);
3838
static parray *do_backup_srvlog(parray *backup_list);
39+
static void remove_stopinfo_from_backup_label(char *history_file, char *bkup_label);
40+
static void make_backup_label(parray *backup_list);
3941
static void confirm_block_size(const char *name, int blcksz);
4042
static void pg_start_backup(const char *label, bool smooth, pgBackup *backup);
4143
static void pg_stop_backup(pgBackup *backup);
4244
static void pg_switch_xlog(pgBackup *backup);
4345
static void get_lsn(PGresult *res, TimeLineID *timeline, XLogRecPtr *lsn);
4446
static void get_xid(PGresult *res, uint32 *xid);
47+
static bool execute_restartpoint(pgBackupOption bkupopt);
4548

4649
static void delete_arclog_link(void);
4750
static void delete_online_wal_backup(void);
4851

49-
static bool fileExists(const char *path);
5052
static bool dirExists(const char *path);
5153

5254
static void execute_freeze(void);
@@ -65,7 +67,7 @@ static void create_file_list(parray *files, const char *root, const char *prefix
6567
* Take a backup of database.
6668
*/
6769
static parray *
68-
do_backup_database(parray *backup_list, bool smooth_checkpoint)
70+
do_backup_database(parray *backup_list, pgBackupOption bkupopt)
6971
{
7072
int i;
7173
parray *files; /* backup file list from non-snapshot */
@@ -75,6 +77,11 @@ do_backup_database(parray *backup_list, bool smooth_checkpoint)
7577
char label[1024];
7678
XLogRecPtr *lsn = NULL;
7779
char prev_file_txt[MAXPGPATH]; /* path of the previous backup list file */
80+
bool has_backup_label = true; /* flag if backup_label is there */
81+
bool has_recovery_conf = false; /* flag if recovery.conf is there */
82+
83+
/* repack the options */
84+
bool smooth_checkpoint = bkupopt.smooth_checkpoint;
7885

7986
if (!HAVE_DATABASE(&current)) {
8087
/* check if arclog backup. if arclog backup and no suitable full backup, */
@@ -112,14 +119,34 @@ do_backup_database(parray *backup_list, bool smooth_checkpoint)
112119
snprintf(path, lengthof(path), "%s/backup_label", pgdata);
113120
make_native_path(path);
114121
if (!fileExists(path)) {
115-
snprintf(path, lengthof(path), "%s/recovery.conf", pgdata);
116-
make_native_path(path);
117-
if (!fileExists(path)) {
118-
if (verbose)
119-
printf(_("backup_label does not exist, stop backup\n"));
122+
has_backup_label = false;
123+
}
124+
snprintf(path, lengthof(path), "%s/recovery.conf", pgdata);
125+
make_native_path(path);
126+
if (fileExists(path)) {
127+
has_recovery_conf = true;
128+
}
129+
if (!has_backup_label && !has_recovery_conf)
130+
{
131+
if (verbose)
132+
printf(_("backup_label does not exist, stop backup\n"));
133+
pg_stop_backup(NULL);
134+
elog(ERROR_SYSTEM, _("backup_label does not exist in PGDATA."));
135+
}
136+
else if (has_recovery_conf)
137+
{
138+
139+
if (!bkupopt.standby_host || !bkupopt.standby_port)
140+
{
120141
pg_stop_backup(NULL);
121-
elog(ERROR_SYSTEM, _("backup_label does not exist in PGDATA."));
142+
elog(ERROR_SYSTEM, _("could not specified standby host or port."));
122143
}
144+
if (!execute_restartpoint(bkupopt))
145+
{
146+
pg_stop_backup(NULL);
147+
elog(ERROR_SYSTEM, _("could not execute restartpoint."));
148+
}
149+
current.is_from_standby = true;
123150
}
124151

125152
/*
@@ -411,6 +438,11 @@ do_backup_database(parray *backup_list, bool smooth_checkpoint)
411438
/* notify end of backup */
412439
pg_stop_backup(&current);
413440

441+
/* if backup is from standby, making backup_label from */
442+
/* backup.history file. */
443+
if (current.is_from_standby)
444+
make_backup_label(files);
445+
414446
/* create file list */
415447
create_file_list(files, pgdata, NULL, false);
416448
}
@@ -437,6 +469,25 @@ do_backup_database(parray *backup_list, bool smooth_checkpoint)
437469
return files;
438470
}
439471

472+
static bool
473+
execute_restartpoint(pgBackupOption bkupopt)
474+
{
475+
PGconn *sby_conn = NULL;
476+
const char *tmp_host;
477+
const char *tmp_port;
478+
tmp_host = pgut_get_host();
479+
tmp_port = pgut_get_port();
480+
pgut_set_host(bkupopt.standby_host);
481+
pgut_set_port(bkupopt.standby_port);
482+
sby_conn = reconnect_elevel(ERROR_PG_CONNECT);
483+
if (!sby_conn)
484+
return false;
485+
command("CHECKPOINT", 0, NULL);
486+
pgut_set_host(tmp_host);
487+
pgut_set_port(tmp_port);
488+
return true;
489+
}
490+
440491
/*
441492
* backup archived WAL incrementally.
442493
*/
@@ -653,13 +704,7 @@ do_backup_srvlog(parray *backup_list)
653704
}
654705

655706
int
656-
do_backup(bool smooth_checkpoint,
657-
int keep_arclog_files,
658-
int keep_arclog_days,
659-
int keep_srvlog_files,
660-
int keep_srvlog_days,
661-
int keep_data_generations,
662-
int keep_data_days)
707+
do_backup(pgBackupOption bkupopt)
663708
{
664709
parray *backup_list;
665710
parray *files_database;
@@ -668,6 +713,14 @@ do_backup(bool smooth_checkpoint,
668713
int server_version;
669714
int ret;
670715

716+
/* repack the necesary options */
717+
int keep_arclog_files = bkupopt.keep_arclog_files;
718+
int keep_arclog_days = bkupopt.keep_arclog_days;
719+
int keep_srvlog_files = bkupopt.keep_srvlog_files;
720+
int keep_srvlog_days = bkupopt.keep_srvlog_days;
721+
int keep_data_generations = bkupopt.keep_data_generations;
722+
int keep_data_days = bkupopt.keep_data_days;
723+
671724
/* PGDATA and BACKUP_MODE are always required */
672725
if (pgdata == NULL)
673726
elog(ERROR_ARGS, _("required parameter not specified: PGDATA (-D, --pgdata)"));
@@ -731,8 +784,9 @@ do_backup(bool smooth_checkpoint,
731784
current.write_bytes = 0; /* write_bytes is valid always */
732785
current.block_size = BLCKSZ;
733786
current.wal_block_size = XLOG_BLCKSZ;
734-
current.recovery_xid = 0;
735-
current.recovery_time = (time_t) 0;
787+
current.recovery_xid = 0;
788+
current.recovery_time = (time_t) 0;
789+
current.is_from_standby = false;
736790

737791
/* create backup directory and backup.ini */
738792
if (!check)
@@ -754,7 +808,7 @@ current.recovery_time = (time_t) 0;
754808
pgut_atexit_push(backup_cleanup, NULL);
755809

756810
/* backup data */
757-
files_database = do_backup_database(backup_list, smooth_checkpoint);
811+
files_database = do_backup_database(backup_list, bkupopt);
758812

759813
/* backup archived WAL */
760814
files_arclog = do_backup_arclog(backup_list);
@@ -822,6 +876,80 @@ current.recovery_time = (time_t) 0;
822876
return 0;
823877
}
824878

879+
void
880+
remove_stopinfo_from_backup_label(char *history_file, char *bkup_label)
881+
{
882+
FILE *read;
883+
FILE *write;
884+
char buf[MAXPGPATH * 2];
885+
886+
if ((read = fopen(history_file, "r")) == NULL)
887+
elog(ERROR_SYSTEM,
888+
_("can't open backup history file for standby backup."));
889+
if ((write = fopen(bkup_label, "w")) == NULL)
890+
elog(ERROR_SYSTEM,
891+
_("can't open backup_label file for standby backup."));
892+
while (fgets(buf, lengthof(buf), read) != NULL)
893+
{
894+
if (strstr(buf, "STOP") - buf == 0)
895+
continue;
896+
fputs(buf, write);
897+
}
898+
fclose(write);
899+
fclose(read);
900+
}
901+
902+
/*
903+
* creating backup_label from backup.history for standby backup.
904+
*/
905+
void
906+
make_backup_label(parray *backup_list)
907+
{
908+
char dest_path[MAXPGPATH];
909+
char src_bkup_history_file[MAXPGPATH];
910+
char dst_bkup_label_file[MAXPGPATH];
911+
char original_bkup_label_file[MAXPGPATH];
912+
parray *bkuped_arc_files = NULL;
913+
int i;
914+
915+
pgBackupGetPath(&current, dest_path, lengthof(dest_path), DATABASE_DIR);
916+
bkuped_arc_files = parray_new();
917+
dir_list_file(bkuped_arc_files, arclog_path, NULL, true, false);
918+
919+
for (i = parray_num(bkuped_arc_files) - 1; i >= 0; i--)
920+
{
921+
char *current_arc_fname;
922+
pgFile *current_arc_file;
923+
924+
current_arc_file = (pgFile *) parray_get(bkuped_arc_files, i);
925+
current_arc_fname = last_dir_separator(current_arc_file->path) + 1;
926+
927+
if(strlen(current_arc_fname) <= 24) continue;
928+
929+
copy_file(arclog_path, dest_path, current_arc_file, NO_COMPRESSION);
930+
join_path_components(src_bkup_history_file, dest_path, current_arc_fname);
931+
join_path_components(dst_bkup_label_file, dest_path, PG_BACKUP_LABEL_FILE);
932+
join_path_components(original_bkup_label_file, pgdata, PG_BACKUP_LABEL_FILE);
933+
remove_stopinfo_from_backup_label(src_bkup_history_file, dst_bkup_label_file);
934+
935+
dir_list_file(backup_list, dst_bkup_label_file, NULL, false, true);
936+
for (i = 0; i < parray_num(backup_list); i++)
937+
{
938+
pgFile *file = (pgFile *)parray_get(backup_list, i);
939+
if (strcmp(file->path, dst_bkup_label_file) == 0)
940+
{
941+
struct stat st;
942+
stat(dst_bkup_label_file, &st);
943+
file->write_size = st.st_size;
944+
file->crc = pgFileGetCRC(file);
945+
strcpy(file->path, original_bkup_label_file);
946+
}
947+
}
948+
parray_qsort(backup_list, pgFileComparePath);
949+
break;
950+
}
951+
}
952+
825953
/*
826954
* get server version and confirm block sizes.
827955
*/
@@ -1030,7 +1158,7 @@ get_xid(PGresult *res, uint32 *xid)
10301158
/*
10311159
* Return true if the path is a existing regular file.
10321160
*/
1033-
static bool
1161+
bool
10341162
fileExists(const char *path)
10351163
{
10361164
struct stat buf;

data.c

Lines changed: 1 addition & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,7 @@
22
*
33
* data.c: compress / uncompress data pages
44
*
5-
* Copyright (c) 2009-2011, NIPPON TELEGRAPH AND TELEPHONE CORPORATION
5+
* Copyright (c) 2009-2013, NIPPON TELEGRAPH AND TELEPHONE CORPORATION
66
*
77
*-------------------------------------------------------------------------
88
*/
@@ -755,14 +755,6 @@ restore_data_file(const char *from_root,
755755
elog(ERROR_SYSTEM, _("can't change mode of \"%s\": %s"), to_path,
756756
strerror(errno_tmp));
757757
}
758-
//aaa if (chown(to_path, file->uid, file->gid) == -1)
759-
//aaa {
760-
//aaa int errno_tmp = errno;
761-
//aaa fclose(in);
762-
//aaa fclose(out);
763-
//aaa elog(ERROR_SYSTEM, _("can't change owner of \"%s\": %s"), to_path,
764-
//aaa strerror(errno_tmp));
765-
//aaa }
766758

767759
fclose(in);
768760
fclose(out);
@@ -998,14 +990,6 @@ copy_file(const char *from_root, const char *to_root, pgFile *file,
998990
elog(ERROR_SYSTEM, _("can't change mode of \"%s\": %s"), to_path,
999991
strerror(errno_tmp));
1000992
}
1001-
//aaa if (chown(to_path, file->uid, file->gid) == -1)
1002-
//aaa {
1003-
//aaa errno_tmp = errno;
1004-
//aaa fclose(in);
1005-
//aaa fclose(out);
1006-
//aaa elog(ERROR_SYSTEM, _("can't change owner of \"%s\": %s"), to_path,
1007-
//aaa strerror(errno_tmp));
1008-
//aaa }
1009993

1010994
fclose(in);
1011995
fclose(out);

0 commit comments

Comments
 (0)