Skip to content

Commit

Permalink
Merge pull request #2668 from dkliban/remove-rsync-password-auth
Browse files Browse the repository at this point in the history
Removes ability to use password authentication when rsync-ing
  • Loading branch information
dkliban committed Aug 1, 2016
2 parents fc6d449 + fd627ea commit 22aa7fa
Show file tree
Hide file tree
Showing 3 changed files with 6 additions and 119 deletions.
1 change: 0 additions & 1 deletion pulp.spec
Expand Up @@ -380,7 +380,6 @@ Requires: mod_xsendfile >= 0.12
Requires: m2crypto
Requires: genisoimage
Requires: kobo
Requires: sshpass
# RHEL6 ONLY
%if 0%{?rhel} == 6
Requires: nss >= 3.12.9
Expand Down
111 changes: 3 additions & 108 deletions server/pulp/plugins/rsync/configuration.py
Expand Up @@ -5,43 +5,6 @@
_LOG = logging.getLogger(__name__)


class OneOfValidation(object):
"""
Validates that the the value is one of possible values
"""
def __init__(self, values):
"""
:param values: list of valid values
"""
self.values = values

def __call__(self, value, config):
"""
:param value: value to validate
:type value: any
:param config: distributor config
:type config: PulpCallConfig object
:return: tuple indicating whether config value validates and error message or None
:rtype: (bool, str) or (bool, None)
"""
if value in self.values:
return (True, None)
else:
return (False, self._err(value))

def _err(self, value):
"""
:param value: value that did not pass validation
:type value: any
:return: error message
:rtype: str
"""
params = {'value': value, 'allowed_values': ", ".join(self.values)}
return _("%(value)s is not in allowed values: %(allowed_values)s") % params


class NonEmptyValidation(object):
"""
Validates that the value is not None
Expand Down Expand Up @@ -110,68 +73,6 @@ def _err(self, value):
return _("%(type)s type is not one of allowed types: %(allowed_types)s") % params


class RequireOptionalIf(object):
"""
Validates that if a particular config is present, other configs that are needed for it are also
present.
"""
def __init__(self, required_for_attr, condition):
"""
:param required_for_attr: a list of required config keys or dictionary with keys in the
config and values are lists of configs that need to be present
in the value of the key in config.
:type required_for_attr: list or dict
:param condition: callable that takes a config name and returns a boolean
:type condition: callable
"""
self.required_for_attr = required_for_attr
self.condition = condition

def __call__(self, value, config):
"""
:param value: config name that is being validated
:type value: str
:param config: configuration instance to validate
:type config: pulp.plugins.config.PluginCallConfiguration
:return: tuple indicating whether config value validates and error message or None
:rtype: (bool, str) or (bool, None)
"""

subconfig = config
path = []
if not self.condition(value):
return (True, None)

if isinstance(self.required_for_attr, list):
fifo = [(x, subconfig, path) for x in self.required_for_attr]
elif isinstance(self.required_for_attr, dict):
fifo = [(val, subconfig.get(key), [key])
for key, val in self.required_for_attr.iteritems()]
while fifo:
(required_for_attr, subconfig, path) = fifo.pop(0)
if isinstance(required_for_attr, list):
for x in required_for_attr:
fifo.insert(0, (x, subconfig, path))
elif isinstance(required_for_attr, dict):
for key, val in required_for_attr.iteritems():
fifo.insert(0, (val, subconfig.get(key)), path + [key])
elif isinstance(required_for_attr, basestring):
if required_for_attr not in subconfig:
return (False, self._err(path + [required_for_attr]))
return (True, None)

def _err(self, path):
"""
:param path: list of value that were missing
:type path: list
:return: error message
:rtype: str
"""
return _("%(attribute)s attribute is required") % {'attribute': "::".join(path)}


class RelativePathValidation(object):
"""
Validates that a path does not start with a forward slash.
Expand Down Expand Up @@ -200,20 +101,14 @@ def _err(self, value):
return _("attribute cannot start with a /")

REMOTE_MANDATORY_KEYS = {
"auth_type": [OneOfValidation(["publickey", "password"]),
RequireOptionalIf({"remote": ["ssh_password", "ssh_user"]},
lambda x: x == "password"),
RequireOptionalIf({"remote": ["ssh_identity_file", "ssh_user"]},
lambda x: x == "publickey")],
"ssh_identity_file": [TypeValidation([basestring]), NonEmptyValidation()],
"ssh_user": [TypeValidation([basestring]), NonEmptyValidation()],
"host": [TypeValidation([basestring]), NonEmptyValidation()],
"root": [TypeValidation([basestring]), NonEmptyValidation()]
}

REMOTE_OPTIONAL_KEYS = {
"remote_units_path": [TypeValidation([basestring]), RelativePathValidation()],
"ssh_identity_file": [TypeValidation([basestring]), NonEmptyValidation()],
"ssh_user": [TypeValidation([basestring]), NonEmptyValidation()],
"ssh_password": [TypeValidation([basestring]), NonEmptyValidation()]
"remote_units_path": [TypeValidation([basestring]), RelativePathValidation()]
}


Expand Down
13 changes: 3 additions & 10 deletions server/pulp/plugins/rsync/publish.py
Expand Up @@ -96,23 +96,16 @@ def make_ssh_cmd(self, args=None):
:rtype: list
"""
user = self.get_config().flatten()["remote"]['ssh_user']
auth_type = self.get_config().flatten()["remote"]['auth_type']

# -e 'ssh -l ssh_user -i ssh_identity_file'
# use shared ssh connection for other threads
cmd = ['ssh', '-l', user]
if auth_type == "publickey":
key = self.get_config().flatten()["remote"]['ssh_identity_file']
cmd += ['-i', key]
cmd += ['-o', 'StrictHostKeyChecking no',
key = self.get_config().flatten()["remote"]['ssh_identity_file']
cmd += ['-i', key,
'-o', 'StrictHostKeyChecking no',
'-o', 'UserKnownHostsFile /dev/null',
'-S', '/tmp/rsync_distributor-%r@%h:%p',
'-o', 'ControlMaster auto',
'-o', 'ControlPersist 10']
if self.get_config().flatten()["remote"]['auth_type'] == 'password':
password_file = os.path.join(self.get_working_dir(), str(uuid.uuid4()))
open(password_file, 'w').write(self.get_config().flatten()['remote']['ssh_password'])
cmd = ['sshpass', '-f', password_file] + cmd
if args:
cmd += args
return cmd
Expand Down

0 comments on commit 22aa7fa

Please sign in to comment.