summaryrefslogtreecommitdiffstats
path: root/src/lib/Bcfg2/Client
diff options
context:
space:
mode:
Diffstat (limited to 'src/lib/Bcfg2/Client')
-rw-r--r--src/lib/Bcfg2/Client/Client.py18
-rw-r--r--src/lib/Bcfg2/Client/Frame.py26
-rw-r--r--src/lib/Bcfg2/Client/Tools/POSIX/File.py10
-rw-r--r--src/lib/Bcfg2/Client/Tools/POSIX/base.py16
-rw-r--r--src/lib/Bcfg2/Client/Tools/RcUpdate.py24
-rw-r--r--src/lib/Bcfg2/Client/Tools/SELinux.py31
-rw-r--r--src/lib/Bcfg2/Client/Tools/YUM.py93
-rw-r--r--src/lib/Bcfg2/Client/__init__.py4
8 files changed, 129 insertions, 93 deletions
diff --git a/src/lib/Bcfg2/Client/Client.py b/src/lib/Bcfg2/Client/Client.py
index 5633764a8..1676ee717 100644
--- a/src/lib/Bcfg2/Client/Client.py
+++ b/src/lib/Bcfg2/Client/Client.py
@@ -91,7 +91,10 @@ class Client(object):
try:
script.write("#!%s\n" %
(probe.attrib.get('interpreter', '/bin/sh')))
- script.write(probe.text)
+ if sys.hexversion >= 0x03000000:
+ script.write(probe.text)
+ else:
+ script.write(probe.text.encode('utf-8'))
script.close()
os.chmod(scriptname,
stat.S_IRUSR | stat.S_IRGRP | stat.S_IROTH |
@@ -105,7 +108,10 @@ class Client(object):
self._probe_failure(name, "Return value %s" % rv)
self.logger.info("Probe %s has result:" % name)
self.logger.info(rv.stdout)
- ret.text = rv.stdout
+ if sys.hexversion >= 0x03000000:
+ ret.text = rv.stdout
+ else:
+ ret.text = rv.stdout.decode('utf-8')
finally:
os.unlink(scriptname)
except SystemExit:
@@ -167,7 +173,7 @@ class Client(object):
self.proxy.RecvProbeData(
Bcfg2.Client.XML.tostring(
probedata,
- xml_declaration=False).decode('UTF-8'))
+ xml_declaration=False).decode('utf-8'))
except Bcfg2.Proxy.ProxyError:
err = sys.exc_info()[1]
self.fatal_error("Failed to upload probe data: %s" % err)
@@ -229,7 +235,7 @@ class Client(object):
self.fatal_error("Failed to get decision list: %s" % err)
try:
- rawconfig = self.proxy.GetConfig().encode('UTF-8')
+ rawconfig = self.proxy.GetConfig().encode('utf-8')
except Bcfg2.Proxy.ProxyError:
err = sys.exc_info()[1]
self.fatal_error("Failed to download configuration from "
@@ -247,7 +253,7 @@ class Client(object):
self.logger.info("Starting Bcfg2 client run at %s" % times['start'])
- rawconfig = self.get_config(times=times)
+ rawconfig = self.get_config(times=times).decode('utf-8')
if self.setup['cache']:
try:
@@ -324,7 +330,7 @@ class Client(object):
self.proxy.RecvStats(
Bcfg2.Client.XML.tostring(
feedback,
- xml_declaration=False).decode('UTF-8'))
+ xml_declaration=False).decode('utf-8'))
except Bcfg2.Proxy.ProxyError:
err = sys.exc_info()[1]
self.logger.error("Failed to upload configuration statistics: "
diff --git a/src/lib/Bcfg2/Client/Frame.py b/src/lib/Bcfg2/Client/Frame.py
index ada5320b8..850e58d9d 100644
--- a/src/lib/Bcfg2/Client/Frame.py
+++ b/src/lib/Bcfg2/Client/Frame.py
@@ -417,15 +417,18 @@ class Frame(object):
bundle.get('name') not in self.setup['bundle']):
# prune out unspecified bundles when running with -b
continue
+ if bundle in mbundles:
+ self.logger.debug("Bundle %s was modified" % bundle)
+ func = "BundleUpdated"
+ else:
+ self.logger.debug("Bundle %s was not modified" % bundle)
+ func = "BundleNotUpdated"
for tool in self.tools:
try:
- if bundle in mbundles:
- tool.BundleUpdated(bundle, self.states)
- else:
- tool.BundleNotUpdated(bundle, self.states)
+ getattr(tool, func)(bundle, self.states)
except:
- self.logger.error("%s.BundleNotUpdated() call failed:" %
- tool.name, exc_info=1)
+ self.logger.error("%s.%s() call failed:" %
+ (tool.name, func), exc_info=1)
def Remove(self):
"""Remove extra entries."""
@@ -447,15 +450,16 @@ class Frame(object):
self.logger.info('Incorrect entries: %d' %
list(self.states.values()).count(False))
if phase == 'final' and list(self.states.values()).count(False):
- for entry in self.states.keys():
+ for entry in sorted(self.states.keys(), key=lambda e: e.tag + ":" +
+ e.get('name')):
if not self.states[entry]:
etype = entry.get('type')
if etype:
self.logger.info("%s:%s:%s" % (entry.tag, etype,
entry.get('name')))
else:
- self.logger.info(" %s:%s" % (entry.tag,
- entry.get('name')))
+ self.logger.info("%s:%s" % (entry.tag,
+ entry.get('name')))
self.logger.info('Total managed entries: %d' %
len(list(self.states.values())))
self.logger.info('Unmanaged entries: %d' % len(self.extra))
@@ -467,8 +471,8 @@ class Frame(object):
self.logger.info("%s:%s:%s" % (entry.tag, etype,
entry.get('name')))
else:
- self.logger.info(" %s:%s" % (entry.tag,
- entry.get('name')))
+ self.logger.info("%s:%s" % (entry.tag,
+ entry.get('name')))
if ((list(self.states.values()).count(False) == 0) and not self.extra):
self.logger.info('All entries correct.')
diff --git a/src/lib/Bcfg2/Client/Tools/POSIX/File.py b/src/lib/Bcfg2/Client/Tools/POSIX/File.py
index 9b95d2234..168c35c98 100644
--- a/src/lib/Bcfg2/Client/Tools/POSIX/File.py
+++ b/src/lib/Bcfg2/Client/Tools/POSIX/File.py
@@ -34,13 +34,11 @@ class POSIXFile(POSIXTool):
def _get_data(self, entry):
""" Get a tuple of (<file data>, <is binary>) for the given entry """
- is_binary = False
- if entry.get('encoding', 'ascii') == 'base64':
- tempdata = b64decode(entry.text)
- is_binary = True
-
- elif entry.get('empty', 'false') == 'true':
+ is_binary = entry.get('encoding', 'ascii') == 'base64'
+ if entry.get('empty', 'false') == 'true' or not entry.text:
tempdata = ''
+ elif is_binary:
+ tempdata = b64decode(entry.text)
else:
tempdata = entry.text
if isinstance(tempdata, unicode) and unicode != str:
diff --git a/src/lib/Bcfg2/Client/Tools/POSIX/base.py b/src/lib/Bcfg2/Client/Tools/POSIX/base.py
index 11f331ddb..16fe0acb5 100644
--- a/src/lib/Bcfg2/Client/Tools/POSIX/base.py
+++ b/src/lib/Bcfg2/Client/Tools/POSIX/base.py
@@ -275,7 +275,7 @@ class POSIXTool(Bcfg2.Client.Tools.Tool):
if path is None:
path = entry.get("name")
context = entry.get("secontext")
- if context is None:
+ if not context:
# no context listed
return True
@@ -520,13 +520,19 @@ class POSIXTool(Bcfg2.Client.Tools.Tool):
"Current mtime is %s but should be %s" %
(path, mtime, entry.get('mtime')))
- if HAS_SELINUX and entry.get("secontext"):
+ if HAS_SELINUX:
+ wanted_secontext = None
if entry.get("secontext") == "__default__":
- wanted_secontext = \
- selinux.matchpathcon(path, 0)[1].split(":")[2]
+ try:
+ wanted_secontext = \
+ selinux.matchpathcon(path, 0)[1].split(":")[2]
+ except OSError:
+ errors.append("%s has no default SELinux context" %
+ entry.get("name"))
else:
wanted_secontext = entry.get("secontext")
- if attrib['current_secontext'] != wanted_secontext:
+ if (wanted_secontext and
+ attrib['current_secontext'] != wanted_secontext):
errors.append("SELinux context for path %s is incorrect. "
"Current context is %s but should be %s" %
(path, attrib['current_secontext'],
diff --git a/src/lib/Bcfg2/Client/Tools/RcUpdate.py b/src/lib/Bcfg2/Client/Tools/RcUpdate.py
index 552b27842..4b78581f7 100644
--- a/src/lib/Bcfg2/Client/Tools/RcUpdate.py
+++ b/src/lib/Bcfg2/Client/Tools/RcUpdate.py
@@ -12,6 +12,15 @@ class RcUpdate(Bcfg2.Client.Tools.SvcTool):
__handles__ = [('Service', 'rc-update')]
__req__ = {'Service': ['name', 'status']}
+ def get_enabled_svcs(self):
+ """
+ Return a list of all enabled services.
+ """
+ return [line.split()[0]
+ for line in self.cmd.run(['/bin/rc-status',
+ '-s']).stdout.splitlines()
+ if 'started' in line]
+
def VerifyService(self, entry, _):
"""
Verify Service status for entry.
@@ -21,9 +30,12 @@ class RcUpdate(Bcfg2.Client.Tools.SvcTool):
if entry.get('status') == 'ignore':
return True
+ # get a list of all started services
+ allsrv = self.get_enabled_svcs()
+
# check if service is enabled
- result = self.cmd.run(["/sbin/rc-update", "show", "default"])
- is_enabled = entry.get("name") in result.stdout
+ result = self.cmd.run(["/sbin/rc-update", "show", "default"]).stdout
+ is_enabled = entry.get("name") in result
# check if init script exists
try:
@@ -34,8 +46,7 @@ class RcUpdate(Bcfg2.Client.Tools.SvcTool):
return False
# check if service is enabled
- result = self.cmd.run(self.get_svc_command(entry, "status"))
- is_running = "started" in result.stdout
+ is_running = entry.get('name') in allsrv
if entry.get('status') == 'on' and not (is_enabled and is_running):
entry.set('current_status', 'off')
@@ -70,10 +81,7 @@ class RcUpdate(Bcfg2.Client.Tools.SvcTool):
def FindExtra(self):
"""Locate extra rc-update services."""
- allsrv = [line.split()[0]
- for line in self.cmd.run(['/bin/rc-status',
- '-s']).stdout.splitlines()
- if 'started' in line]
+ allsrv = self.get_enabled_svcs()
self.logger.debug('Found active services:')
self.logger.debug(allsrv)
specified = [srv.get('name') for srv in self.getSupportedEntries()]
diff --git a/src/lib/Bcfg2/Client/Tools/SELinux.py b/src/lib/Bcfg2/Client/Tools/SELinux.py
index 0041ce61a..0b4aba60d 100644
--- a/src/lib/Bcfg2/Client/Tools/SELinux.py
+++ b/src/lib/Bcfg2/Client/Tools/SELinux.py
@@ -204,7 +204,16 @@ class SELinuxEntryHandler(object):
type, if the records object supports the customized() method
"""
if hasattr(self.records, "customized") and self.custom_re:
- return dict([(k, self.all_records[k]) for k in self.custom_keys])
+ rv = dict()
+ for key in self.custom_keys:
+ if key in self.all_records:
+ rv[key] = self.all_records[key]
+ else:
+ self.logger.warning("SELinux %s %s customized, but no "
+ "record found. This may indicate an "
+ "error in your SELinux policy." %
+ (self.etype, key))
+ return rv
else:
# ValueError is really a pretty dumb exception to raise,
# but that's what the seobject customized() method raises
@@ -491,7 +500,8 @@ class SELinuxSeportHandler(SELinuxEntryHandler):
def _defaultargs(self, entry):
""" argument list for adding and modifying entries """
(port, proto) = entry.get("name").split("/")
- return (port, proto, '', entry.get("selinuxtype"))
+ return (port, proto, entry.get("mlsrange", ""),
+ entry.get("selinuxtype"))
def _deleteargs(self, entry):
return tuple(entry.get("name").split("/"))
@@ -564,7 +574,7 @@ class SELinuxSefcontextHandler(SELinuxEntryHandler):
""" argument list for adding, modifying, and deleting entries """
return (entry.get("name"), entry.get("selinuxtype"),
self.filetypeargs[entry.get("filetype", "all")],
- '', '')
+ entry.get("mlsrange", ""), '')
def primarykey(self, entry):
return ":".join([entry.tag, entry.get("name"),
@@ -599,7 +609,7 @@ class SELinuxSenodeHandler(SELinuxEntryHandler):
def _defaultargs(self, entry):
""" argument list for adding, modifying, and deleting entries """
(addr, netmask) = entry.get("name").split("/")
- return (addr, netmask, entry.get("proto"), "",
+ return (addr, netmask, entry.get("proto"), entry.get("mlsrange", ""),
entry.get("selinuxtype"))
@@ -611,7 +621,8 @@ class SELinuxSeloginHandler(SELinuxEntryHandler):
def _defaultargs(self, entry):
""" argument list for adding, modifying, and deleting entries """
- return (entry.get("name"), entry.get("selinuxuser"), "")
+ return (entry.get("name"), entry.get("selinuxuser"),
+ entry.get("mlsrange", ""))
class SELinuxSeuserHandler(SELinuxEntryHandler):
@@ -651,15 +662,16 @@ class SELinuxSeuserHandler(SELinuxEntryHandler):
# prefix. see the comment in Install() above for more
# details.
rv = [entry.get("name"),
- entry.get("roles", "").replace(" ", ",").split(",")]
+ entry.get("roles", "").replace(" ", ",").split(","),
+ '', entry.get("mlsrange", "")]
if self.needs_prefix:
- rv.extend(['', '', entry.get("prefix")])
+ rv.append(entry.get("prefix"))
else:
key = self._key(entry)
if key in self.all_records:
attrs = self._key2attrs(key)
if attrs['prefix'] != entry.get("prefix"):
- rv.extend(['', '', entry.get("prefix")])
+ rv.append(entry.get("prefix"))
return tuple(rv)
@@ -671,7 +683,8 @@ class SELinuxSeinterfaceHandler(SELinuxEntryHandler):
def _defaultargs(self, entry):
""" argument list for adding, modifying, and deleting entries """
- return (entry.get("name"), '', entry.get("selinuxtype"))
+ return (entry.get("name"), entry.get("mlsrange", ""),
+ entry.get("selinuxtype"))
class SELinuxSepermissiveHandler(SELinuxEntryHandler):
diff --git a/src/lib/Bcfg2/Client/Tools/YUM.py b/src/lib/Bcfg2/Client/Tools/YUM.py
index c9fae7fc7..c30c0a13a 100644
--- a/src/lib/Bcfg2/Client/Tools/YUM.py
+++ b/src/lib/Bcfg2/Client/Tools/YUM.py
@@ -131,10 +131,12 @@ class YUM(Bcfg2.Client.Tools.PkgTool):
def __init__(self, logger, setup, config):
self.yumbase = self._loadYumBase(setup=setup, logger=logger)
Bcfg2.Client.Tools.PkgTool.__init__(self, logger, setup, config)
- self.ignores = [entry.get('name') for struct in config \
- for entry in struct \
- if entry.tag == 'Path' and \
- entry.get('type') == 'ignore']
+ self.ignores = []
+ for struct in config:
+ self.ignores.extend([entry.get('name')
+ for entry in struct
+ if (entry.tag == 'Path' and
+ entry.get('type') == 'ignore')])
self.instance_status = {}
self.extra_instances = []
self.modlists = {}
@@ -293,8 +295,8 @@ class YUM(Bcfg2.Client.Tools.PkgTool):
group. """
missing = Bcfg2.Client.Tools.PkgTool.missing_attrs(self, entry)
- if entry.get('name', None) == None and \
- entry.get('group', None) == None:
+ if (entry.get('name', None) is None and
+ entry.get('group', None) is None):
missing += ['name', 'group']
return missing
@@ -422,10 +424,10 @@ class YUM(Bcfg2.Client.Tools.PkgTool):
if entry.get('group'):
self.logger.debug("Verifying packages for group %s" %
- entry.get('group'))
+ entry.get('group'))
else:
self.logger.debug("Verifying package instances for %s" %
- entry.get('name'))
+ entry.get('name'))
self.verify_cache = dict() # Used for checking multilib packages
self.modlists[entry] = modlist
@@ -434,10 +436,10 @@ class YUM(Bcfg2.Client.Tools.PkgTool):
package_fail = False
qtext_versions = []
virt_pkg = False
- pkg_checks = self.pkg_checks and \
- entry.get('pkg_checks', 'true').lower() == 'true'
- pkg_verify = self.pkg_verify and \
- entry.get('pkg_verify', 'true').lower() == 'true'
+ pkg_checks = (self.pkg_checks and
+ entry.get('pkg_checks', 'true').lower() == 'true')
+ pkg_verify = (self.pkg_verify and
+ entry.get('pkg_verify', 'true').lower() == 'true')
yum_group = False
if entry.get('name') == 'gpg-pubkey':
@@ -455,15 +457,13 @@ class YUM(Bcfg2.Client.Tools.PkgTool):
if d]
group_type = entry.get('choose', 'default')
if group_type in ['default', 'optional', 'all']:
- group_packages += [p
- for p, d in
- group.default_packages.items()
- if d]
+ group_packages += [
+ p for p, d in group.default_packages.items()
+ if d]
if group_type in ['optional', 'all']:
- group_packages += [p
- for p, d in
- group.optional_packages.items()
- if d]
+ group_packages += [
+ p for p, d in group.optional_packages.items()
+ if d]
if len(group_packages) == 0:
self.logger.error("No packages found for group %s" %
entry.get("group"))
@@ -489,7 +489,7 @@ class YUM(Bcfg2.Client.Tools.PkgTool):
else:
all_pkg_objs = \
self.yumbase.rpmdb.searchNevra(name=entry.get('name'))
- if len(all_pkg_objs) == 0 and yum_group != True:
+ if len(all_pkg_objs) == 0 and yum_group is not True:
# Some sort of virtual capability? Try to resolve it
all_pkg_objs = self.yumbase.rpmdb.searchProvides(entry.get('name'))
if len(all_pkg_objs) > 0:
@@ -567,9 +567,9 @@ class YUM(Bcfg2.Client.Tools.PkgTool):
pkg_objs = [po for po in all_pkg_objs]
else:
pkg_objs = [po for po in all_pkg_objs
- if po.checkPrco('provides',
- (nevra["name"], 'EQ',
- tuple(vlist)))]
+ if po.checkPrco('provides',
+ (nevra["name"], 'EQ',
+ tuple(vlist)))]
elif entry.get('name') == 'gpg-pubkey':
if 'version' not in nevra:
self.logger.warning("Skipping verify: gpg-pubkey without "
@@ -622,7 +622,7 @@ class YUM(Bcfg2.Client.Tools.PkgTool):
if self.setup.get('quick', False):
# Passed -q on the command line
continue
- if not (pkg_verify and \
+ if not (pkg_verify and
inst.get('pkg_verify', 'true').lower() == 'true'):
continue
@@ -648,8 +648,8 @@ class YUM(Bcfg2.Client.Tools.PkgTool):
# Now take out the Yum specific objects / modlists / unproblems
ignores = [ig.get('name') for ig in entry.findall('Ignore')] + \
- [ig.get('name') for ig in inst.findall('Ignore')] + \
- self.ignores
+ [ig.get('name') for ig in inst.findall('Ignore')] + \
+ self.ignores
for fname, probs in list(vrfy_result.items()):
if fname in modlist:
self.logger.debug(" %s in modlist, skipping" % fname)
@@ -737,8 +737,9 @@ class YUM(Bcfg2.Client.Tools.PkgTool):
for pkg in pkg_objs:
self.logger.debug(" Extra Instance Found: %s" % str(pkg))
Bcfg2.Client.XML.SubElement(extra_entry, 'Instance',
- epoch=pkg.epoch, name=pkg.name, version=pkg.version,
- release=pkg.release, arch=pkg.arch)
+ epoch=pkg.epoch, name=pkg.name,
+ version=pkg.version,
+ release=pkg.release, arch=pkg.arch)
if pkg_objs == []:
return None
@@ -782,7 +783,7 @@ class YUM(Bcfg2.Client.Tools.PkgTool):
ver = yum.misc.keyIdToRPMVer(gpg['keyid'])
rel = yum.misc.keyIdToRPMVer(gpg['timestamp'])
if not (ver == inst.get('version') and rel == inst.get('release')):
- self.logger.info("GPG key file %s does not match gpg-pubkey-%s-%s"\
+ self.logger.info("GPG key file %s does not match gpg-pubkey-%s-%s"
% (key_file, inst.get('version'),
inst.get('release')))
return False
@@ -791,20 +792,21 @@ class YUM(Bcfg2.Client.Tools.PkgTool):
gpg['timestamp']) == 0:
result = tset.pgpImportPubkey(yum.misc.procgpgkey(rawkey))
else:
- self.logger.debug("gpg-pubkey-%s-%s already installed"\
- % (inst.get('version'),
- inst.get('release')))
+ self.logger.debug("gpg-pubkey-%s-%s already installed" %
+ (inst.get('version'), inst.get('release')))
return True
if result != 0:
- self.logger.debug("Unable to install %s-%s" % \
- (self.instance_status[inst].get('pkg').get('name'),
- nevra2string(inst)))
+ self.logger.debug(
+ "Unable to install %s-%s" %
+ (self.instance_status[inst].get('pkg').get('name'),
+ nevra2string(inst)))
return False
else:
- self.logger.debug("Installed %s-%s-%s" % \
- (self.instance_status[inst].get('pkg').get('name'),
- inst.get('version'), inst.get('release')))
+ self.logger.debug(
+ "Installed %s-%s-%s" %
+ (self.instance_status[inst].get('pkg').get('name'),
+ inst.get('version'), inst.get('release')))
return True
def _runYumTransaction(self):
@@ -898,7 +900,7 @@ class YUM(Bcfg2.Client.Tools.PkgTool):
# Remove extra instances.
# Can not reverify because we don't have a package entry.
if self.extra_instances is not None and len(self.extra_instances) > 0:
- if (self.setup.get('remove') == 'all' or \
+ if (self.setup.get('remove') == 'all' or
self.setup.get('remove') == 'packages'):
self.Remove(self.extra_instances)
else:
@@ -913,7 +915,7 @@ class YUM(Bcfg2.Client.Tools.PkgTool):
# Figure out which instances of the packages actually need something
# doing to them and place in the appropriate work 'queue'.
for pkg in packages:
- insts = [pinst for pinst in pkg \
+ insts = [pinst for pinst in pkg
if pinst.tag in ['Instance', 'Package']]
if insts:
for inst in insts:
@@ -1006,10 +1008,11 @@ class YUM(Bcfg2.Client.Tools.PkgTool):
if not self.setup['kevlar']:
for pkg_entry in [p for p in packages if self.canVerify(p)]:
- self.logger.debug("Reverifying Failed Package %s" \
- % (pkg_entry.get('name')))
- states[pkg_entry] = self.VerifyPackage(pkg_entry,
- self.modlists.get(pkg_entry, []))
+ self.logger.debug("Reverifying Failed Package %s" %
+ pkg_entry.get('name'))
+ states[pkg_entry] = \
+ self.VerifyPackage(pkg_entry,
+ self.modlists.get(pkg_entry, []))
for entry in [ent for ent in packages if states[ent]]:
self.modified.append(entry)
diff --git a/src/lib/Bcfg2/Client/__init__.py b/src/lib/Bcfg2/Client/__init__.py
index 8c8c4fd94..e40ef750b 100644
--- a/src/lib/Bcfg2/Client/__init__.py
+++ b/src/lib/Bcfg2/Client/__init__.py
@@ -3,9 +3,7 @@
import os
import sys
import select
-from Bcfg2.Compat import input, walk_packages # pylint: disable=W0622
-
-__all__ = [m[1] for m in walk_packages(path=__path__)]
+from Bcfg2.Compat import input # pylint: disable=W0622
def prompt(msg):