#!/usr/bin/env python '''Bcfg2 Client''' __revision__ = '$Revision$' from getopt import getopt, GetoptError from os import popen, chmod, unlink from sys import argv, exit as sysexit from tempfile import mktemp from elementtree.ElementTree import Element, XML, tostring from sss.ssslib import comm_lib from Bcfg2.Client.Debian import Debian def RunProbe(probe): '''Execute probe''' ret = Element("probe-data", name=probe.attrib['name'], source=probe.attrib['source']) script = open(mktemp(), 'w+') script.write("#!%s\n"%(probe.attrib.get('interpreter', '/bin/sh'))) script.write(probe.text) script.close() chmod(script.name, 0755) ret.text = popen(script.name).read() unlink(script.name) return ret def dgetopt(arglist, opt, vopt): '''parse options into a dictionary''' ret = {} for optname in opt.values() + vopt.values(): ret[optname] = False gstr = "".join(opt.keys()) + "".join([xy+':' for xy in vopt.keys()]) try: (o, a) = getopt(arglist, gstr) except GetoptError, gerr: print gerr print "bcfg2 Usage:" for arg in opt.iteritems(): print " -%s %s" % arg for arg in vopt.iteritems(): print " -%s <%s>" % arg sysexit(1) for (gopt, garg) in o: option = gopt[1:] if opt.has_key(option): ret[opt[option]] = True else: ret[vopt[option]] = garg return ret if __name__ == '__main__': # parse command line options options = {'v':'verbose', 'q':'quick', 'd':'debug', 'n':'dryrun', 'B':'build', 'p':'paranoid'} doptions = {'b':'bundle', 'f':'file', 'c':'cache', 'p':'profile', 'i':'image'} setup = dgetopt(argv[1:], options, doptions) # connect to bcfg2d comm = comm_lib() h = comm.ClientInit("bcfg2") # get probes comm.SendMessage(h, "") data = comm.RecvMessage(h) #if setup['verbose']: print data probes = XML(data) # execute probes cpd = Element("probe-data") [cpd.append(RunProbe(x)) for x in probes.findall(".//probe")] # upload probe responses comm.SendMessage(h, tostring(cpd)) r = comm.RecvMessage(h) msg = Element("get-config") if setup['profile']: msg.attrib['profile'] = setup['profile'] if setup['image']: msg.attrib['image'] = setup['image'] # get config comm.SendMessage(h, tostring(msg)) r = comm.RecvMessage(h) if setup['cache']: try: open(setup['cache'], 'w').write(r) except IOError: print "failed to write config cache file %s" % (setup['cache']) cfg = XML(r) if cfg.tag == 'error': print "got error from server" sysexit(1) if setup['bundle']: c = XML(" %s of %s config elements correct" % (correct, total)) # install incorrect aspects of configuration client.Install() client.CondPrint('verbose', "--> %s of %s config elements correct"%(client.states.values().count(True), total)) print "Failing Entries:" for k, v in client.states.iteritems(): if not v: print "%s:%s" % (k.tag, k.attrib['name']) else: client.CondPrint("verbose", "All entries correct") # upload statistics m = Element("upload-statistics") stats = client.GenerateStats() m.append(stats) comm.SendMessage(h, tostring(m)) r = comm.RecvMessage(h) # clean up comm.ClientClose(h)