diff options
Diffstat (limited to 'xlators/features')
-rw-r--r-- | xlators/features/marker/utils/syncdaemon/gsyncd.py | 3 | ||||
-rw-r--r-- | xlators/features/marker/utils/syncdaemon/master.py | 28 | ||||
-rw-r--r-- | xlators/features/marker/utils/syncdaemon/resource.py | 18 |
3 files changed, 35 insertions, 14 deletions
diff --git a/xlators/features/marker/utils/syncdaemon/gsyncd.py b/xlators/features/marker/utils/syncdaemon/gsyncd.py index 17b10e5a6fd..9e946946932 100644 --- a/xlators/features/marker/utils/syncdaemon/gsyncd.py +++ b/xlators/features/marker/utils/syncdaemon/gsyncd.py @@ -159,6 +159,7 @@ def main_i(): op.add_option('-l', '--log-file', metavar='LOGF', type=str, action='callback', callback=store_abs) op.add_option('--state-file', metavar='STATF', type=str, action='callback', callback=store_abs) op.add_option('--ignore-deletes', default=False, action='store_true') + op.add_option('--use-rsync-xattrs', default=False, action='store_true') op.add_option('-L', '--log-level', metavar='LVL') op.add_option('-r', '--remote-gsyncd', metavar='CMD', default=os.path.abspath(sys.argv[0])) op.add_option('--volume-id', metavar='UUID') @@ -213,7 +214,7 @@ def main_i(): op.add_option('--canonicalize-escape-url', dest='url_print', action='callback', callback=store_local_curry('canon_esc')) tunables = [ norm(o.get_opt_string()[2:]) for o in op.option_list if o.callback in (store_abs, 'store_true', None) and o.get_opt_string() not in ('--version', '--help') ] - remote_tunables = [ 'listen', 'go_daemon', 'timeout', 'session_owner', 'config_file' ] + remote_tunables = [ 'listen', 'go_daemon', 'timeout', 'session_owner', 'config_file', 'use_rsync_xattrs' ] rq_remote_tunables = { 'listen': True } # precedence for sources of values: 1) commandline, 2) cfg file, 3) defaults diff --git a/xlators/features/marker/utils/syncdaemon/master.py b/xlators/features/marker/utils/syncdaemon/master.py index 945ebb75dd2..a6aeb53dce0 100644 --- a/xlators/features/marker/utils/syncdaemon/master.py +++ b/xlators/features/marker/utils/syncdaemon/master.py @@ -54,12 +54,13 @@ def gmaster_builder(): """produce the GMaster class variant corresponding to sync mode""" this = sys.modules[__name__] - mixin = gconf.special_sync_mode - if not mixin: - mixin = 'normal' - logging.info('setting up master for %s sync mode' % mixin) - mixin = getattr(this, mixin.capitalize() + 'Mixin') - class _GMaster(GMasterBase, mixin): + modemixin = gconf.special_sync_mode + if not modemixin: + modemixin = 'normal' + logging.info('setting up master for %s sync mode' % modemixin) + modemixin = getattr(this, modemixin.capitalize() + 'Mixin') + sendmarkmixin = boolify(gconf.use_rsync_xattrs) and SendmarkNormalMixin or SendmarkRsyncMixin + class _GMaster(GMasterBase, modemixin, sendmarkmixin): pass return _GMaster @@ -295,6 +296,19 @@ class BlindMixin(object): self.slave.server.set_xtime_vec(path, xtd) +# Further mixins for certain tunable behaviors + +class SendmarkNormalMixin(object): + + def sendmark_regular(self, *a, **kw): + return self.sendmark(self, *a, **kw) + +class SendmarkRsyncMixin(object): + + def sendmark_regular(self, *a, **kw): + pass + + class GMasterBase(object): """abstract class impementling master role""" @@ -753,7 +767,7 @@ class GMasterBase(object): def regjob(e, xte, pb): if pb.wait(): logging.debug("synced " + e) - self.sendmark(e, xte) + self.sendmark_regular(e, xte) return True else: logging.warn("failed to sync " + e) diff --git a/xlators/features/marker/utils/syncdaemon/resource.py b/xlators/features/marker/utils/syncdaemon/resource.py index 9ca226f9628..47e4748df30 100644 --- a/xlators/features/marker/utils/syncdaemon/resource.py +++ b/xlators/features/marker/utils/syncdaemon/resource.py @@ -19,7 +19,7 @@ import repce from repce import RepceServer, RepceClient from master import gmaster_builder import syncdutils -from syncdutils import GsyncdError, select, privileged +from syncdutils import GsyncdError, select, privileged, boolify UrlRX = re.compile('\A(\w+)://([^ *?[]*)\Z') HostRX = re.compile('[a-z\d](?:[a-z\d.-]*[a-z\d])?', re.I) @@ -472,6 +472,10 @@ class SlaveLocal(object): stop servicing if a timeout is configured and got no keep-alime in that inteval """ + + if boolify(gconf.use_rsync_xattrs) and not privileged(): + raise GsyncdError("using rsync for extended attributes is not supported") + repce = RepceServer(self.server, sys.stdin, sys.stdout, int(gconf.sync_jobs)) t = syncdutils.Thread(target=lambda: (repce.service_loop(), syncdutils.finalize())) @@ -498,12 +502,13 @@ class SlaveRemote(object): communicate throuh its stdio. """ slave = opts.get('slave', self.url) + extra_opts = [] so = getattr(gconf, 'session_owner', None) if so: - so_args = ['--session-owner', so] - else: - so_args = [] - po = Popen(rargs + gconf.remote_gsyncd.split() + so_args + \ + extra_opts += ['--session-owner', so] + if boolify(gconf.use_rsync_xattrs): + extra_opts.append('--use-rsync-xattrs') + po = Popen(rargs + gconf.remote_gsyncd.split() + extra_opts + \ ['-N', '--listen', '--timeout', str(gconf.timeout), slave], stdin=subprocess.PIPE, stdout=subprocess.PIPE, stderr=subprocess.PIPE) gconf.transport = po @@ -532,7 +537,8 @@ class SlaveRemote(object): raise GsyncdError("no files to sync") logging.debug("files: " + ", ".join(files)) argv = gconf.rsync_command.split() + ['-aR', '--super', '--numeric-ids', '--no-implied-dirs'] + \ - gconf.rsync_options.split() + files + list(args) + gconf.rsync_options.split() + (boolify(gconf.use_rsync_xattrs) and ['--xattrs'] or []) + \ + files + list(args) po = Popen(argv, stderr=subprocess.PIPE) po.wait() po.terminate_geterr(fail_on_err = False) |