Package flumotion :: Package admin :: Package command :: Module worker
[hide private]

Source Code for Module flumotion.admin.command.worker

  1  # -*- Mode: Python -*- 
  2  # vi:si:et:sw=4:sts=4:ts=4 
  3  # 
  4  # Flumotion - a streaming media server 
  5  # Copyright (C) 2004,2005,2006,2007 Fluendo, S.L. (www.fluendo.com). 
  6  # All rights reserved. 
  7   
  8  # This file may be distributed and/or modified under the terms of 
  9  # the GNU General Public License version 2 as published by 
 10  # the Free Software Foundation. 
 11  # This file is distributed without any warranty; without even the implied 
 12  # warranty of merchantability or fitness for a particular purpose. 
 13  # See "LICENSE.GPL" in the source distribution for more information. 
 14   
 15  # Licensees having purchased or holding a valid Flumotion Advanced 
 16  # Streaming Server license may use this file in accordance with the 
 17  # Flumotion Advanced Streaming Server Commercial License Agreement. 
 18  # See "LICENSE.Flumotion" in the source distribution for more information. 
 19   
 20  # Headers in this file shall remain intact. 
 21   
 22  """ 
 23  worker commands 
 24  """ 
 25   
 26  import os 
 27  import time 
 28   
 29  from gettext import gettext as _ 
 30   
 31  from twisted.python import failure 
 32   
 33  from flumotion.configure import configure 
 34  from flumotion.common import errors, log, i18n, messages 
 35  from flumotion.monitor.nagios import util 
 36   
 37  from flumotion.admin.command import common 
 38   
 39  __version__ = "$Rev: 6562 $" 
 40   
 41   
42 -class Invoke(common.AdminCommand):
43 usage = "[method-name] [arguments]" 44 summary = "invoke a method on a worker" 45 description = """Invoke a method on a worker. 46 %s 47 For a list of methods that can be invoked, see the worker's medium class 48 in flumotion.worker.medium and its remote_* methods. 49 50 Examples: getFeedServerPort, killJob, getComponents, getVersions 51 52 checkElements [ss] oggmux vorbisenc 53 54 checkImport s sys""" % common.ARGUMENTS_DESCRIPTION 55
56 - def doCallback(self, args):
57 workerName = self.parentCommand.options.name 58 if not workerName: 59 common.errorRaise('Please specify a worker name with --name.') 60 61 try: 62 methodName = args[0] 63 except IndexError: 64 common.errorRaise('Please specify a method name.') 65 66 if len(args) > 1: 67 args = common.parseTypedArgs(args[1], args[2:]) 68 if args is None: 69 common.errorRaise('Could not parse arguments.') 70 else: 71 args = [] 72 73 p = self.parentCommand 74 d = self.getRootCommand().medium.callRemote( 75 'workerCallRemote', workerName, methodName, *args) 76 77 def cb(result): 78 import pprint 79 self.stdout.write("Invoking '%s' on '%s' returned:\n%s\n" % ( 80 methodName, workerName, pprint.pformat(result)))
81 82 def eb(failure): 83 # FIXME 84 if failure.check(errors.NoMethodError): 85 common.errorRaise("No method '%s' on worker '%s'." % ( 86 methodName, workerName)) 87 elif failure.check(errors.SleepingComponentError): 88 common.errorRaise("Component '%s' is sleeping." % 89 p.componentId) 90 elif failure.check(errors.RemoteRunError): 91 common.errorRaise(log.getFailureMessage(failure)) 92 else: 93 common.errorRaise(log.getFailureMessage(failure))
94 95 d.addCallback(cb) 96 d.addErrback(eb) 97 98 return d 99 100
101 -class List(common.AdminCommand):
102 description = "List workers." 103
104 - def doCallback(self, args):
105 s = self.parentCommand.workerHeavenState 106 workers = s.get('workers') 107 if not workers: 108 self.stdout.write('No workers logged in.\n') 109 return 110 111 for worker in workers: 112 self.stdout.write('%s: %s\n' % ( 113 worker.get('name'), worker.get('host')))
114 115
116 -class Run(common.AdminCommand):
117 usage = "[module-name] [method-name] [arguments]" 118 summary = "run a method on a worker" 119 description = """Run a method on a worker 120 %s 121 Any method that the worker can import can be run. 122 This is useful for testing worker checks. 123 124 Examples: 125 126 flumotion.worker.checks.video checkTVCard s /dev/video0 127 128 flumotion.worker.checks.audio checkMixerTracks ssi alsasrc hw:0 2 129 """ % common.ARGUMENTS_DESCRIPTION 130
131 - def doCallback(self, args):
132 try: 133 moduleName = args[0] 134 except IndexError: 135 common.errorRaise('Please specify a module name to invoke from.') 136 try: 137 methodName = args[1] 138 except IndexError: 139 common.errorRaise('Please specify a method name.') 140 141 if len(args) > 2: 142 args = common.parseTypedArgs(args[2], args[3:]) 143 if args is None: 144 common.errorRaise('Could not parse arguments.') 145 else: 146 args = [] 147 148 p = self.parentCommand 149 workerName = p.options.name 150 d = self.getRootCommand().medium.callRemote( 151 'workerCallRemote', workerName, 'runFunction', 152 moduleName, methodName, *args) 153 154 def cb(result): 155 i18n.installGettext() 156 # handle some results specifically, like Result 157 self.stdout.write("Invoking '%s' on '%s' returned:\n" % 158 (methodName, workerName)) 159 import pprint 160 self.stdout.write("%s\n" % pprint.pformat(result)) 161 162 if isinstance(result, messages.Result): 163 _headings = { 164 messages.ERROR: _('Error'), 165 messages.WARNING: _('Warning'), 166 messages.INFO: _('Note'), 167 } 168 169 for m in result.messages: 170 translator = i18n.Translator() 171 localedir = os.path.join(configure.localedatadir, 'locale') 172 # FIXME: add locales as messages from domains come in 173 translator.addLocaleDir(configure.PACKAGE, localedir) 174 self.stdout.write('%s:\n' % _headings[m.level]) 175 self.stdout.write(translator.translate(m) + '\n') 176 if hasattr(m, 'timestamp'): 177 self.stdout.write(_("\nPosted on %s.\n") % 178 time.strftime("%c", time.localtime(m.timestamp))) 179 if m.debug: 180 self.stdout.write("DEBUG:\n%s\n" % m.debug) 181 182 if result.failed: 183 self.stdout.write('Result failed.\n') 184 else: 185 self.stdout.write('Result successful:\n%s\n' % 186 pprint.pformat(result.value))
187 188 def eb(failure): 189 if failure.check(errors.NoMethodError): 190 common.errorRaise("No method '%s' on worker '%s'." % ( 191 methodName, workerName)) 192 elif failure.check(errors.SleepingComponentError): 193 common.errorRaise("Component '%s' is sleeping." % 194 p.componentId) 195 elif failure.check(errors.RemoteRunError): 196 common.errorRaise(log.getFailureMessage(failure)) 197 else: 198 common.errorRaise(log.getFailureMessage(failure))
199 200 d.addCallback(cb) 201 d.addErrback(eb) 202 203 return d 204 205
206 -class Worker(util.LogCommand):
207 """ 208 @param workerHeavenState: the planet state; set when logged in to manager. 209 @type workerHeavenState: L{flumotion.common.state.WorkerHeavenState} 210 """ 211 description = "Act on workers." 212 213 subCommandClasses = [Invoke, List, Run] 214
215 - def addOptions(self):
216 self.parser.add_option('-n', '--name', 217 action="store", dest="name", 218 help="name of the component")
219
220 - def handleOptions(self, options):
221 # call our callback after connecting 222 self.getRootCommand().loginDeferred.addCallback(self._callback)
223
224 - def _callback(self, result):
225 d = self.parentCommand.medium.callRemote('getWorkerHeavenState') 226 227 def gotWorkerHeavenStateCb(result): 228 self.workerHeavenState = result
229 d.addCallback(gotWorkerHeavenStateCb) 230 return d
231