From: <di...@us...> - 2007-06-17 22:37:45
|
Revision: 528 http://safekeep.svn.sourceforge.net/safekeep/?rev=528&view=rev Author: dimi Date: 2007-06-17 15:37:43 -0700 (Sun, 17 Jun 2007) Log Message: ----------- Update version to 1.0.1 Modified Paths: -------------- safekeep/trunk/safekeep Modified: safekeep/trunk/safekeep =================================================================== --- safekeep/trunk/safekeep 2007-06-17 22:36:53 UTC (rev 527) +++ safekeep/trunk/safekeep 2007-06-17 22:37:43 UTC (rev 528) @@ -16,7 +16,7 @@ base_dir = None PROTOCOL = "1.0" -VERSION = "1.0.0" +VERSION = "1.0.1" VEBOSITY_BY_CLASS = {'DBG': 3, 'INFO': 2, 'WARN': 1, 'ERR': 0} ###################################################################### This was sent by the SourceForge.net collaborative development platform, the world's largest Open Source development site. |
From: <st...@us...> - 2007-10-09 11:44:29
|
Revision: 548 http://safekeep.svn.sourceforge.net/safekeep/?rev=548&view=rev Author: stelian Date: 2007-10-09 04:44:27 -0700 (Tue, 09 Oct 2007) Log Message: ----------- Better error handling and logging in spawn() Modified Paths: -------------- safekeep/trunk/safekeep Modified: safekeep/trunk/safekeep =================================================================== --- safekeep/trunk/safekeep 2007-10-09 11:43:58 UTC (rev 547) +++ safekeep/trunk/safekeep 2007-10-09 11:44:27 UTC (rev 548) @@ -78,13 +78,30 @@ def spawn(args): if isinstance(args, str) or isinstance(args, unicode): debug('Run [' + args + ']') + cmd = args.split(' ')[0] else: debug('Run [' + ' '.join(args) + ']') - (cout, cin) = popen2.popen4(args) - cin.close() - for line in cout: + cmd = args[0] + proc = popen2.Popen4(args) + proc.tochild.close() + for line in proc.fromchild: info(line.rstrip()) - cout.close() + proc.fromchild.close() + rc = proc.wait() + if os.WIFEXITED(rc): + if os.WEXITSTATUS(rc) == 0: + ret = None + else: + ret = 'exited with non zero status: %d' % os.WEXITSTATUS(rc) + elif os.WIFSIGNALED(rc): + ret = 'killed by signal: %d' % os.WTERMSIG(rc) + elif os.WCOREDUMP(rc): + ret = 'coredumped' + else: + ret = 'unknown exit status: %d' + rc + if ret: + error('%s failed: %s' % (cmd, ret)); + return ret def send_notification(email, smtp): info('Sending email to %s via %s' % (','.join(email), smtp)) @@ -394,7 +411,7 @@ continue ret = spawn(['umount', snapmnt]) if ret: - warn('umount %s returned %s' % (snapmnt, ret)) + warn('Can not umount the snapshot: %s' % snapmnt) ret = spawn(['lvremove', '--force', snapdev]) if ret: warn('Can not tear down snapshot: ' + device) @@ -427,7 +444,7 @@ bdir = tempfile.mkdtemp("-rbind", "safekeep-", "/mnt") ret = spawn(['mount', '--rbind', '/', bdir]) if ret: - warn('mount --rbind failed with %d, snapshotting will be disabled' % ret) + warn('mount --rbind failed, snapshotting will be disabled') try: os.rmdir(bdir) except Exception, e: @@ -537,7 +554,7 @@ args.extend([userhost + '::' + bdir, cfg['dir']]) ret = spawn(args) if ret: - raise Exception('rdiff-backup returned %d' % ret) + raise Exception('Failed to run rdiff-backup') def do_server_data_cleanup(cfg): args = ['rdiff-backup', '--force', '--remove-older-than', cfg['retention'], cfg['dir']] This was sent by the SourceForge.net collaborative development platform, the world's largest Open Source development site. |
From: <st...@us...> - 2007-10-09 11:45:07
|
Revision: 549 http://safekeep.svn.sourceforge.net/safekeep/?rev=549&view=rev Author: stelian Date: 2007-10-09 04:44:53 -0700 (Tue, 09 Oct 2007) Log Message: ----------- Give a clear backup status on job end Modified Paths: -------------- safekeep/trunk/safekeep Modified: safekeep/trunk/safekeep =================================================================== --- safekeep/trunk/safekeep 2007-10-09 11:44:27 UTC (rev 548) +++ safekeep/trunk/safekeep 2007-10-09 11:44:53 UTC (rev 549) @@ -52,6 +52,7 @@ def info_file(file, marker=None): info('## File: ' + file) + errs = 0; fin = open(file, 'r') try: for line in fin.readlines(): @@ -59,9 +60,12 @@ if line.startswith(marker): marker = None continue + if (line.startswith("Errors ")): + errs = int(line[6:]) info(line.rstrip()) finally: fin.close() + return errs def debug(msg): log(msg, 'DBG') @@ -575,7 +579,7 @@ id = cfg['id'] if ids and id not in ids: continue info('------------------------------------------------------------------') - info('Server backup starting for client: %s' % id) + info('Server backup starting for client %s' % id) try: if cfg['host']: @@ -632,12 +636,13 @@ do_server_rdiff(cfg, bdir, force) + errs = 0 if os.path.isdir(rdiff_logdir): info_file(backup_log, backup_marker) rdiff_logpost = os.listdir(rdiff_logdir) for lfn in rdiff_logpost: if lfn.startswith('session_statistics.') and lfn.endswith('.data') and lfn not in rdiff_logpre: - info_file(os.path.join(rdiff_logdir, lfn)) + errs += info_file(os.path.join(rdiff_logdir, lfn)) else: warn('Log dir does not exist.') @@ -645,11 +650,14 @@ cin.flush() do_server_getanswer(cout) - debug('Server backup done for client: %s' % id) + if errs == 0: + info('Server backup for client %s: OK' % id) + else: + info('Server backup for client %s: OK (%d WARNINGS)' % (id, errs)) except Exception, e: error(e) - error('Skipping backup for client: %s' % id) + error('Server backup for client %s: FAILED' % id) info('------------------------------------------------------------------') debug('Server backup done') This was sent by the SourceForge.net collaborative development platform, the world's largest Open Source development site. |
From: <di...@us...> - 2007-11-07 14:15:24
|
Revision: 561 http://safekeep.svn.sourceforge.net/safekeep/?rev=561&view=rev Author: dimi Date: 2007-11-07 06:15:06 -0800 (Wed, 07 Nov 2007) Log Message: ----------- Provide Python 2.2 compatibility based on a suggestion from Gert <ger...@ta...>. Modified Paths: -------------- safekeep/trunk/safekeep Modified: safekeep/trunk/safekeep =================================================================== --- safekeep/trunk/safekeep 2007-10-19 17:43:35 UTC (rev 560) +++ safekeep/trunk/safekeep 2007-11-07 14:15:06 UTC (rev 561) @@ -19,7 +19,30 @@ import commands, tempfile, time, traceback import getpass, pwd, xml.dom.minidom import socket, smtplib +from __future__ import generators +###################################################################### +# Python 2.2 compatibility +###################################################################### +# There is no guarantee that we'll continue supporting Python 2.2 +# indefinitely, but we make a reasonable effor to do so as long as +# it doesn't result in major complication/ugliness. + +try: + True, False +except NameError: + True, False = 1, 0 + +def enumerate(obj): + i = -1 + for item in obj: + i += 1 + yield i, item + +###################################################################### +# Global settings +###################################################################### + config_file = '/etc/safekeep/safekeep.conf' config_ext = '.backup' logbuf = [] This was sent by the SourceForge.net collaborative development platform, the world's largest Open Source development site. |
From: <di...@us...> - 2007-11-07 14:17:32
|
Revision: 562 http://safekeep.svn.sourceforge.net/safekeep/?rev=562&view=rev Author: dimi Date: 2007-11-07 06:17:30 -0800 (Wed, 07 Nov 2007) Log Message: ----------- Future import must come first. Modified Paths: -------------- safekeep/trunk/safekeep Modified: safekeep/trunk/safekeep =================================================================== --- safekeep/trunk/safekeep 2007-11-07 14:15:06 UTC (rev 561) +++ safekeep/trunk/safekeep 2007-11-07 14:17:30 UTC (rev 562) @@ -15,11 +15,11 @@ # You should have received a copy of the GNU General Public License # along with Safekeep. If not, see <http://www.gnu.org/licenses/>. +from __future__ import generators import getopt, os, os.path, popen2, re, sys import commands, tempfile, time, traceback import getpass, pwd, xml.dom.minidom import socket, smtplib -from __future__ import generators ###################################################################### # Python 2.2 compatibility This was sent by the SourceForge.net collaborative development platform, the world's largest Open Source development site. |
From: <di...@us...> - 2007-11-07 14:39:13
|
Revision: 565 http://safekeep.svn.sourceforge.net/safekeep/?rev=565&view=rev Author: dimi Date: 2007-11-07 06:39:07 -0800 (Wed, 07 Nov 2007) Log Message: ----------- Change version to a devel number Modified Paths: -------------- safekeep/trunk/safekeep Modified: safekeep/trunk/safekeep =================================================================== --- safekeep/trunk/safekeep 2007-11-07 14:36:06 UTC (rev 564) +++ safekeep/trunk/safekeep 2007-11-07 14:39:07 UTC (rev 565) @@ -54,7 +54,7 @@ base_dir = None PROTOCOL = "1.0" -VERSION = "1.0.3" +VERSION = "1.0.3.90" VEBOSITY_BY_CLASS = {'DBG': 3, 'INFO': 2, 'WARN': 1, 'ERR': 0} ###################################################################### This was sent by the SourceForge.net collaborative development platform, the world's largest Open Source development site. |
From: <di...@us...> - 2007-11-07 15:16:13
|
Revision: 571 http://safekeep.svn.sourceforge.net/safekeep/?rev=571&view=rev Author: dimi Date: 2007-11-07 07:16:12 -0800 (Wed, 07 Nov 2007) Log Message: ----------- Bit clearer snapshot handling. Modified Paths: -------------- safekeep/trunk/safekeep Modified: safekeep/trunk/safekeep =================================================================== --- safekeep/trunk/safekeep 2007-11-07 15:03:28 UTC (rev 570) +++ safekeep/trunk/safekeep 2007-11-07 15:16:12 UTC (rev 571) @@ -402,21 +402,22 @@ cout.close() cin.close() for line in lines: + (device, blah1, mountpoint, blah2, mounttype) = line.split(' ') if line.startswith('/dev/mapper/' + group + '-' + volume + ' '): - return (group, volume, line.split(' ')[2], line.split(' ')[4]) + return (group, volume, mountpoint, mounttype) elif line.startswith('/dev/' + group + '/' + volume + ' '): - return (group, volume, line.split(' ')[2], line.split(' ')[4]) + return (group, volume, mountpoint, mounttype) return (None, None, None, None) def gather_snap_information(device, bdir): - (group, volume, mp, mt) = gather_lvm_information(device) - if not mp: return (None, None, None, None) + (group, volume, mountpoint, mounttype) = gather_lvm_information(device) + if not mountpoint: return (None, None, None, None) lvmdev = os.path.join('/dev', group, volume) if bdir[-1] == '/': bdir = bdir[:-1] snapname = '%s_snap_%s' % (volume, os.path.basename(bdir)) snapdev = os.path.join('/dev', group, snapname) - if os.path.isabs(mp[0]): mp = mp[1:] - return (lvmdev, snapdev, os.path.join(bdir, mp), mt) + if os.path.isabs(mountpoint[0]): mountpoint = mountpoint[1:] + return (lvmdev, snapdev, os.path.join(bdir, mountpoint), mounttype) def do_client_snap(cfg, bdir): assert is_temp_root(bdir) This was sent by the SourceForge.net collaborative development platform, the world's largest Open Source development site. |
From: <di...@us...> - 2008-02-24 16:42:31
|
Revision: 573 http://safekeep.svn.sourceforge.net/safekeep/?rev=573&view=rev Author: dimi Date: 2008-02-24 08:42:27 -0800 (Sun, 24 Feb 2008) Log Message: ----------- Frank Crawford <fr...@cr...> * Fixed failure when mount table has extra options. * Tear down FS snapshots in reverse order to the setup order. * Load the LVM snapshot module, in case it is not already loaded. * Fixed a minor spelling mistake in an assert message. Modified Paths: -------------- safekeep/trunk/safekeep Modified: safekeep/trunk/safekeep =================================================================== --- safekeep/trunk/safekeep 2007-11-07 15:35:15 UTC (rev 572) +++ safekeep/trunk/safekeep 2008-02-24 16:42:27 UTC (rev 573) @@ -402,7 +402,7 @@ cout.close() cin.close() for line in lines: - (device, blah1, mountpoint, blah2, mounttype) = line.split(' ') + (device, blah1, mountpoint, blah2, mounttype, blah3) = line.split(' ', 5) if line.startswith('/dev/mapper/' + group + '-' + volume + ' '): return (group, volume, mountpoint, mounttype) elif line.startswith('/dev/' + group + '/' + volume + ' '): @@ -446,7 +446,9 @@ def do_client_snap_teardown(cfg, bdir): assert is_temp_root(bdir) debug('Tear down FS snapshots dumps') - for snap in cfg['snaps']: + snaps = list(cfg['snaps']) + snaps.reverse() + for snap in snaps: device = snap['device'] (lvmdev, snapdev, snapmnt, snaptyp) = gather_snap_information(device, bdir) if not snapmnt: @@ -484,6 +486,9 @@ do_client_dbdump(cfg) if len(cfg['snaps']) > 0: + ret = spawn(['modprobe', 'dm-snapshot']) + if ret: + warn('modprobe dm-snapshot failed, continuing') bdir = tempfile.mkdtemp("-rbind", "safekeep-", "/mnt") ret = spawn(['mount', '--rbind', '/', bdir]) if ret: @@ -1022,7 +1027,7 @@ keys_status = True do_keys(cfgs, args, identity, keys_status, keys_print, keys_deploy) else: - assert False, 'Unkown mode: ' + mode + assert False, 'Unknown mode: ' + mode except Exception, ex: traceback.print_exc(file=sys.stdout) error('ERROR: %s' % ex) This was sent by the SourceForge.net collaborative development platform, the world's largest Open Source development site. |
From: <di...@us...> - 2008-02-26 20:48:12
|
Revision: 581 http://safekeep.svn.sourceforge.net/safekeep/?rev=581&view=rev Author: dimi Date: 2008-02-26 12:48:09 -0800 (Tue, 26 Feb 2008) Log Message: ----------- Update version. Modified Paths: -------------- safekeep/trunk/safekeep Modified: safekeep/trunk/safekeep =================================================================== --- safekeep/trunk/safekeep 2008-02-26 20:46:50 UTC (rev 580) +++ safekeep/trunk/safekeep 2008-02-26 20:48:09 UTC (rev 581) @@ -54,7 +54,7 @@ base_dir = None PROTOCOL = "1.0" -VERSION = "1.0.3.90" +VERSION = "1.0.4" VEBOSITY_BY_CLASS = {'DBG': 3, 'INFO': 2, 'WARN': 1, 'ERR': 0} ###################################################################### This was sent by the SourceForge.net collaborative development platform, the world's largest Open Source development site. |
From: <di...@us...> - 2008-03-18 15:51:51
|
Revision: 593 http://safekeep.svn.sourceforge.net/safekeep/?rev=593&view=rev Author: dimi Date: 2008-03-18 08:51:44 -0700 (Tue, 18 Mar 2008) Log Message: ----------- Frank Crawford <fr...@cr...> * Patch client name output for --list --parsable-output option. Modified Paths: -------------- safekeep/trunk/safekeep Modified: safekeep/trunk/safekeep =================================================================== --- safekeep/trunk/safekeep 2008-03-18 15:47:01 UTC (rev 592) +++ safekeep/trunk/safekeep 2008-03-18 15:51:44 UTC (rev 593) @@ -835,8 +835,12 @@ for cfg in cfgs.itervalues(): id = cfg['id'] if ids and id not in ids: continue - info('------------------------------------------------------------------') - info('Server listing for client %s' % id) + if list_parsable: + info('Client: %s' % id) + else: + info('------------------------------------------------------------------') + info('Server listing for client %s' % id) + args = ['rdiff-backup'] @@ -859,7 +863,8 @@ if ret: raise Exception('Failed to run rdiff-backup') - info('------------------------------------------------------------------') + if not list_parsable: + info('------------------------------------------------------------------') debug('Server listing done') def do_keys(cfgs, ids, identity, status, dump, deploy): This was sent by the SourceForge.net collaborative development platform, the world's largest Open Source development site. |
From: <di...@us...> - 2008-06-27 12:54:45
|
Revision: 594 http://safekeep.svn.sourceforge.net/safekeep/?rev=594&view=rev Author: dimi Date: 2008-06-27 05:54:27 -0700 (Fri, 27 Jun 2008) Log Message: ----------- Frank Crawford <fr...@cr...> * Loosen restrictions on running --server --cleanup so no root parts will still execute. * Allow local rdiff-backup data cleanup to occur even if client is not accessible. Modified Paths: -------------- safekeep/trunk/safekeep Modified: safekeep/trunk/safekeep =================================================================== --- safekeep/trunk/safekeep 2008-03-18 15:51:44 UTC (rev 593) +++ safekeep/trunk/safekeep 2008-06-27 12:54:27 UTC (rev 594) @@ -567,69 +567,70 @@ if is_client: raise Exception('client not running as root') else: - error("--cleanup must be run as root") - sys.exit(2) - - scrubbed = False - if os.environ['PATH'][-1] == ':': - os.environ['PATH'] += '/sbin:/usr/sbin:/usr/local/sbin:' + warn('--cleanup should be run as root on client') + info('No cleanup performed') else: - os.environ['PATH'] += ':/sbin:/usr/sbin:/usr/local/sbin' + scrubbed = False - # Go through and unmount anythings that are still hanging around + if os.environ['PATH'][-1] == ':': + os.environ['PATH'] += '/sbin:/usr/sbin:/usr/local/sbin:' + else: + os.environ['PATH'] += ':/sbin:/usr/sbin:/usr/local/sbin' - debug("Cleaning up existing mounts") - for (device, mountpoint, mounttype, mountoptions) in mount_information(True): - if mountpoint.startswith('/mnt/safekeep-'): - info("Removing mount %s" % mountpoint) - if device == '/' and 'bind' in mountoptions.split(','): - info("Removing rbind directory %s" % mountpoint) - ret = spawn(['umount', '-l', mountpoint]) - if ret: - warn('Failed to unmount: ' + mountpoint) + # Go through and unmount anythings that are still hanging around + + debug("Cleaning up existing mounts") + for (device, mountpoint, mounttype, mountoptions) in mount_information(True): + if mountpoint.startswith('/mnt/safekeep-'): + info("Removing mount %s" % mountpoint) + if device == '/' and 'bind' in mountoptions.split(','): + info("Removing rbind directory %s" % mountpoint) + ret = spawn(['umount', '-l', mountpoint]) + if ret: + warn('Failed to unmount: ' + mountpoint) + else: + try: + os.rmdir(mountpoint) + except Exception, e: + warn('Failed to remove: ' + mountpoint) else: + ret = spawn(['umount', mountpoint]) + if ret: + warn('Can not unmount the snapshot: %s' % mountpoint) + if fnmatch.fnmatch(device, '*_snap_safekeep-*'): + info("Removing snapshot %s" % device) + ret = spawn(['lvremove', '--force', device]) + if ret: + warn('Can not tear down snapshot: ' + device) + scrubbed = True + + # Now cleanup any snapshots still hanging around + + debug("Cleaning up remaining snapshots") + for (volume, group) in lvm_snap_information(): + device = os.path.join('/dev', group, volume) + info("Removing snapshot %s" % device) + ret = spawn(['lvremove', '--force', device]) + if ret: + warn('Can not tear down snapshot: ' + device) + scrubbed = True + + # Now cleanup any safekeep directories still hanging around + + debug("Cleaning up remaining safekeep directories") + if os.path.isdir('/mnt'): + for ent in os.listdir('/mnt'): + mountpoint = os.path.join('/mnt', ent) + if ent.startswith('safekeep-') and os.path.isdir(mountpoint): + info("Removing rbind directory %s" % mountpoint) try: os.rmdir(mountpoint) except Exception, e: warn('Failed to remove: ' + mountpoint) - else: - ret = spawn(['umount', mountpoint]) - if ret: - warn('Can not unmount the snapshot: %s' % mountpoint) - if fnmatch.fnmatch(device, '*_snap_safekeep-*'): - info("Removing snapshot %s" % device) - ret = spawn(['lvremove', '--force', device]) - if ret: - warn('Can not tear down snapshot: ' + device) - scrubbed = True - # Now cleanup any snapshots still hanging around + if not scrubbed: + info('No cleanup required') - debug("Cleaning up remaining snapshots") - for (volume, group) in lvm_snap_information(): - device = os.path.join('/dev', group, volume) - info("Removing snapshot %s" % device) - ret = spawn(['lvremove', '--force', device]) - if ret: - warn('Can not tear down snapshot: ' + device) - scrubbed = True - - # Now cleanup any safekeep directories still hanging around - - debug("Cleaning up remaining safekeep directories") - if os.path.isdir('/mnt'): - for ent in os.listdir('/mnt'): - mountpoint = os.path.join('/mnt', ent) - if ent.startswith('safekeep-') and os.path.isdir(mountpoint): - info("Removing rbind directory %s" % mountpoint) - try: - os.rmdir(mountpoint) - except Exception, e: - warn('Failed to remove: ' + mountpoint) - - if not scrubbed: - info('No cleanup required') - def do_client(): debug("Do client main loop") should_cleanup = True @@ -741,6 +742,7 @@ info('------------------------------------------------------------------') info('Server backup starting for client %s' % id) + cleaned_up = 0 try: if cfg['host']: if not os.path.isfile(cfg['key_ctrl']): @@ -775,13 +777,13 @@ cin.write(cfg['text'] + '\n') cin.flush() do_server_getanswer(cout) - if cleanup: cin.write('SCRUB\n') cin.flush() do_server_getanswer(cout) bdir = '/' # Fake directory for the rest of the cleanup do_server_rdiff_cleanup(cfg) + cleaned_up = 1 errs = 0 else: cin.write('SETUP\n') @@ -824,8 +826,12 @@ info('Server backup for client %s: OK (%d WARNINGS)' % (id, errs)) except Exception, e: - error(e) - error('Server backup for client %s: FAILED' % id) + if cleanup and not cleaned_up: + info('Client-side cleanup for client %s: FAILED' % id) + do_server_rdiff_cleanup(cfg) + else: + error(e) + error('Server backup for client %s: FAILED' % id) info('------------------------------------------------------------------') debug('Server backup done') This was sent by the SourceForge.net collaborative development platform, the world's largest Open Source development site. |