summaryrefslogtreecommitdiffstats
path: root/src/lib/Client/Tools/launchd.py
diff options
context:
space:
mode:
authorSol Jerome <sol.jerome@gmail.com>2012-03-24 11:20:07 -0500
committerSol Jerome <sol.jerome@gmail.com>2012-03-24 11:20:07 -0500
commitdab1d03d81c538966d03fb9318a4588a9e803b44 (patch)
treef51e27fa55887e9fb961766805fe43f0da56c5b9 /src/lib/Client/Tools/launchd.py
parent5cd6238df496a3cea178e4596ecd87967cce1ce6 (diff)
downloadbcfg2-dab1d03d81c538966d03fb9318a4588a9e803b44.tar.gz
bcfg2-dab1d03d81c538966d03fb9318a4588a9e803b44.tar.bz2
bcfg2-dab1d03d81c538966d03fb9318a4588a9e803b44.zip
Allow to run directly from a git checkout (#1037)
Signed-off-by: Sol Jerome <sol.jerome@gmail.com>
Diffstat (limited to 'src/lib/Client/Tools/launchd.py')
-rw-r--r--src/lib/Client/Tools/launchd.py135
1 files changed, 0 insertions, 135 deletions
diff --git a/src/lib/Client/Tools/launchd.py b/src/lib/Client/Tools/launchd.py
deleted file mode 100644
index 700234cc8..000000000
--- a/src/lib/Client/Tools/launchd.py
+++ /dev/null
@@ -1,135 +0,0 @@
-"""launchd support for Bcfg2."""
-
-import os
-import popen2
-
-import Bcfg2.Client.Tools
-
-
-class launchd(Bcfg2.Client.Tools.Tool):
- """Support for Mac OS X launchd services."""
- __handles__ = [('Service', 'launchd')]
- __execs__ = ['/bin/launchctl', '/usr/bin/defaults']
- name = 'launchd'
- __req__ = {'Service': ['name', 'status']}
-
- '''
- Currently requires the path to the plist to load/unload,
- and Name is acually a reverse-fqdn (or the label).
- '''
-
- def __init__(self, logger, setup, config):
- Bcfg2.Client.Tools.Tool.__init__(self, logger, setup, config)
-
- '''Locate plist file that provides given reverse-fqdn name
- /Library/LaunchAgents Per-user agents provided by the administrator.
- /Library/LaunchDaemons System wide daemons provided by the administrator.
- /System/Library/LaunchAgents Mac OS X Per-user agents.
- /System/Library/LaunchDaemons Mac OS X System wide daemons.'''
- plistLocations = ["/Library/LaunchDaemons", "/System/Library/LaunchDaemons"]
- self.plistMapping = {}
- for directory in plistLocations:
- for daemon in os.listdir(directory):
- try:
- if daemon.endswith(".plist"):
- d = daemon[:-6]
- else:
- d = daemon
- (stdout, _) = popen2.popen2('defaults read %s/%s Label' % (directory, d))
- label = stdout.read().strip()
- self.plistMapping[label] = "%s/%s" % (directory, daemon)
- except KeyError: #perhaps this could be more robust
- pass
-
- def FindPlist(self, entry):
- return self.plistMapping.get(entry.get('name'), None)
-
- def os_version(self):
- version = ""
- try:
- vers = self.cmd.run('sw_vers')[1]
- except:
- return version
-
- for line in vers:
- if line.startswith("ProductVersion"):
- version = line.split()[-1]
- return version
-
- def VerifyService(self, entry, _):
- """Verify launchd service entry."""
- try:
- services = self.cmd.run("/bin/launchctl list")[1]
- except IndexError:#happens when no services are running (should be never)
- services = []
- # launchctl output changed in 10.5
- # It is now three columns, with the last column being the name of the # service
- version = self.os_version()
- if version.startswith('10.5') or version.startswith('10.6'):
- services = [s.split()[-1] for s in services]
- if entry.get('name') in services:#doesn't check if non-spawning services are Started
- return entry.get('status') == 'on'
- else:
- self.logger.debug("Didn't find service Loaded (launchd running under same user as bcfg)")
- return entry.get('status') == 'off'
-
- try: #Perhaps add the "-w" flag to load and unload to modify the file itself!
- self.cmd.run("/bin/launchctl load -w %s" % self.FindPlist(entry))
- except IndexError:
- return 'on'
- return False
-
- def InstallService(self, entry):
- """Enable or disable launchd item."""
- # don't take any actions for mode='manual'
- if entry.get('mode', 'default') == 'manual':
- self.logger.info("Service %s mode set to manual. Skipping "
- "installation." % (entry.get('name')))
- return False
- name = entry.get('name')
- if entry.get('status') == 'on':
- self.logger.error("Installing service %s" % name)
- cmdrc = self.cmd.run("/bin/launchctl load -w %s" % self.FindPlist(entry))
- cmdrc = self.cmd.run("/bin/launchctl start %s" % name)
- else:
- self.logger.error("Uninstalling service %s" % name)
- cmdrc = self.cmd.run("/bin/launchctl stop %s" % name)
- cmdrc = self.cmd.run("/bin/launchctl unload -w %s" % self.FindPlist(entry))
- return cmdrc[0] == 0
-
- def Remove(self, svcs):
- """Remove Extra launchd entries."""
- pass
-
- def FindExtra(self):
- """Find Extra launchd services."""
- try:
- allsrv = self.cmd.run("/bin/launchctl list")[1]
- except IndexError:
- allsrv = []
-
- [allsrv.remove(svc) for svc in [entry.get("name") for entry
- in self.getSupportedEntries()] if svc in allsrv]
- return [Bcfg2.Client.XML.Element("Service",
- type='launchd',
- name=name,
- status='on') for name in allsrv]
-
- def BundleUpdated(self, bundle, states):
- """Reload launchd plist."""
- for entry in [entry for entry in bundle if self.handlesEntry(entry)]:
- if not self.canInstall(entry):
- self.logger.error("Insufficient information to restart service %s" % (entry.get('name')))
- else:
- name = entry.get('name')
- if entry.get('status') == 'on' and self.FindPlist(entry):
- self.logger.info("Reloading launchd service %s" % name)
- #stop?
- self.cmd.run("/bin/launchctl stop %s" % name)
- self.cmd.run("/bin/launchctl unload -w %s" % (self.FindPlist(entry)))#what if it disappeared? how do we stop services that are currently running but the plist disappeared?!
- self.cmd.run("/bin/launchctl load -w %s" % (self.FindPlist(entry)))
- self.cmd.run("/bin/launchctl start %s" % name)
- else:
- #only if necessary....
- self.cmd.run("/bin/launchctl stop %s" % name)
- self.cmd.run("/bin/launchctl unload -w %s" % (self.FindPlist(entry)))