9 import termios, fcntl, os
14 from dbus.mainloop.glib import DBusGMainLoop
31 def __init__(self, n, d):
40 self.commands.append(Autocomplete.Cmd('help', 'Prints help data (also see COMMAND help)'))
41 self.commands.append(Autocomplete.Cmd('list', 'List supported ObjectNames'))
42 self.commands.append(Autocomplete.Cmd('get', 'Get properties from an ObjectName'))
43 self.commands.append(Autocomplete.Cmd('listen', 'Listen for changes on an ObjectName'))
44 self.commands.append(Autocomplete.Cmd('set', 'Set a property for an ObjectName'))
45 self.commands.append(Autocomplete.Cmd('getHistory', 'Get logged data within a time range'))
46 self.commands.append(Autocomplete.Cmd('plugin', 'enable, disable and get info on a plugin'))
47 self.commands.append(Autocomplete.Cmd('quit', 'Exit ambctl'))
50 bus = dbus.SystemBus()
51 managerObject = bus.get_object("org.automotive.message.broker", "/");
52 managerInterface = dbus.Interface(managerObject, "org.automotive.Manager")
53 self.properties = managerInterface.List()
54 except dbus.exceptions.DBusException, error:
57 def complete(self, partialString, commandsOnly = False):
62 for cmd in self.commands:
63 if not (len(partialString)) or cmd.name.startswith(partialString):
64 results.append(cmd.name)
67 for property in self.properties:
68 if not(len(partialString)) or property.startswith(partialString):
69 results.append(str(property))
71 if len(results) > 1 and len(results[0]) > 0:
72 for i in range(len(results[0])):
73 for j in range(len(results[0])-i+1):
74 if j > len(sameString) and all(results[0][i:i+j] in x for x in results):
75 sameString = results[0][i:i+j]
76 elif len(results) == 1:
77 sameString = results[0]
79 return results, sameString
83 help = ("Available commands:\n")
84 autocomplete = Autocomplete()
85 for cmd in autocomplete.commands:
86 help += bcolors.HEADER + cmd.name + bcolors.WHITE
87 for i in range(1, 15 - len(cmd.name)):
89 help += cmd.description + "\n"
93 def changed(interface, properties, invalidated):
94 print json.dumps(properties, indent=2)
98 for root, dirs, files in os.walk('@PLUGIN_SEGMENT_INSTALL_PATH@'):
100 fullpath = root + "/" + file;
101 pluginFile = open(fullpath)
103 data = json.load(pluginFile)
105 data['segmentPath'] = fullpath
107 except ValueError, e:
108 print "error parsing json file", file, ":", e
109 traceback.print_stack()
110 finally: pluginFile.close()
113 def enablePlugin(pluginName, enabled):
114 return setPluginProperty(pluginName, "enabled", enabled);
116 def setPluginProperty(pluginName, key, value):
120 if plugin["name"] == pluginName:
122 if key not in plugin:
123 print "Key not found: ", key
125 type = plugin[key].__class__
127 value = value.lower() == "true"
130 file = open(plugin["segmentPath"], 'rw+')
131 plugin.pop('segmentPath', None)
132 fixedData = json.dumps(plugin, separators=(', ', ' : '), indent=4)
133 fixedData = fixedData.replace(' ','\t');
135 file.write(fixedData)
138 except IOError, error:
144 def processCommand(command, commandArgs, noMain=True):
146 if command == 'help':
153 bus = dbus.SystemBus()
154 managerObject = bus.get_object("org.automotive.message.broker", "/");
155 managerInterface = dbus.Interface(managerObject, "org.automotive.Manager")
156 return managerInterface, bus
158 print "Error connecting to AMB. is AMB running?"
161 if command == "list" :
162 managerInterface, bus = getManager()
163 if managerInterface == None:
165 supportedList = managerInterface.List()
166 for objectName in supportedList:
169 elif command == "get":
170 if len(commandArgs) == 0:
171 commandArgs = ['help']
172 if commandArgs[0] == "help":
173 print "ObjectName [ObjectName...]"
175 managerInterface, bus = getManager()
176 if managerInterface == None:
178 for objectName in commandArgs:
179 objects = managerInterface.FindObject(objectName)
182 propertiesInterface = dbus.Interface(bus.get_object("org.automotive.message.broker", o),"org.freedesktop.DBus.Properties")
183 print json.dumps(propertiesInterface.GetAll("org.automotive."+objectName), indent=2)
185 elif command == "listen":
187 if len(commandArgs) == 0:
188 commandArgs = ['help']
189 if commandArgs[0] == "help":
190 print "[help] [off] ObjectName [ObjectName...]"
192 elif commandArgs[0] == "off":
194 commandArgs=commandArgs[1:]
195 managerInterface, bus = getManager()
196 if managerInterface == None:
198 for objectName in commandArgs:
199 objects = managerInterface.FindObject(objectName)
202 signalMatch = bus.add_signal_receiver(changed, dbus_interface="org.freedesktop.DBus.Properties", signal_name="PropertiesChanged", path=o)
203 Subscribe.subscriptions[o] = signalMatch
206 signalMatch = Subscribe.subscriptions.get(o)
208 del Subscribe.subscriptions[o]
210 print "not lisenting to object at: ", o
212 if not noMain == True:
214 main_loop = gobject.MainLoop(None, False)
216 except KeyboardInterrupt:
219 traceback.print_stack()
220 elif command == "set":
221 if len(commandArgs) == 0:
222 commandArgs = ['help']
223 if len(commandArgs) and commandArgs[0] == "help":
224 print "ObjectName PropertyName VALUE [ZONE]"
226 if len(commandArgs) < 3:
227 print "set requires more arguments (see set help)"
229 objectName = commandArgs[0]
230 propertyName = commandArgs[1]
231 value = commandArgs[2]
233 if len(commandArgs) == 4:
234 zone = int(commandArgs[3])
235 managerInterface, bus = getManager()
236 if managerInterface == None:
238 object = managerInterface.FindObjectForZone(objectName, zone)
239 propertiesInterface = dbus.Interface(bus.get_object("org.automotive.message.broker", object),"org.freedesktop.DBus.Properties")
240 property = propertiesInterface.Get("org.automotive."+objectName, propertyName)
241 if property.__class__ == dbus.Boolean:
242 value = value.lower() == "true"
243 realValue = property.__class__(value)
244 propertiesInterface.Set("org.automotive."+objectName, propertyName, realValue)
245 property = propertiesInterface.Get("org.automotive."+objectName, propertyName)
246 if property == realValue:
247 print propertyName + " = ", property
249 print "Error setting property. Expected value: ", realValue, " Received: ", property
251 elif command == "getHistory":
252 if len(commandArgs) == 0:
253 commandArgs = ['help']
254 if commandArgs[0] == "help":
255 print "ObjectName [ZONE] [STARTTIME] [ENDTIME] "
257 if len(commandArgs) < 1:
258 print "getHistory requires more arguments (see getHistory help)"
260 objectName = commandArgs[0]
262 if len(commandArgs) >= 3:
263 start = float(commandArgs[2])
265 if len(commandArgs) >= 4:
266 end = float(commandArgs[3])
268 if len(commandArgs) >= 2:
269 zone = int(commandArgs[1])
270 managerInterface, bus = getManager()
271 if managerInterface == None:
273 object = managerInterface.FindObjectForZone(objectName, zone);
274 propertiesInterface = dbus.Interface(bus.get_object("org.automotive.message.broker", object),"org.automotive."+objectName)
275 print json.dumps(propertiesInterface.GetHistory(start, end), indent=2)
276 elif command == "plugin":
277 if len(commandArgs) == 0:
278 commandArgs = ['help']
279 if commandArgs[0] == 'help':
280 print "[list] [pluginName] [key value]"
282 elif commandArgs[0] == 'list':
283 for plugin in listPlugins():
286 elif len(commandArgs) == 1:
287 for plugin in listPlugins():
288 if plugin['name'] == commandArgs[0]:
289 print json.dumps(plugin, indent=4)
292 print "name: " + plugin['name'] + "==?" + commandArgs[0]
293 print "plugin not found: ", commandArgs[0]
296 if len(commandArgs) < 3:
298 plugin = commandArgs[0]
300 value = commandArgs[2]
302 if not setPluginProperty(plugin, key, value):
303 print "Could not set property"
304 print plugin, key, ":", value
308 print "Invalid command"
313 parser = argparse.ArgumentParser(prog="ambctl", description='Automotive Message Broker DBus client tool', add_help=False)
314 parser.add_argument('command', metavar='COMMAND [help]', nargs='?', default='stdin', help='amb dbus command')
315 parser.add_argument('commandArgs', metavar='ARG', nargs='*',
316 help='amb dbus command arguments')
317 parser.add_argument('-h', '--help', help='print help', action='store_true')
319 args = parser.parse_args()
327 dbus.mainloop.glib.DBusGMainLoop(set_as_default=True)
329 if args.command == "stdin":
334 promptAmbctl = "[ambctl]"
336 fullprompt = promptAmbctl + promptEnd
339 autocomplete = Autocomplete()
340 def full_line_len(self):
341 return len(self.fullprompt) + len(self.line)
342 def insert(self, str):
343 if self.curpos == len(self.line):
345 self.curpos = len(self.line)
347 self.line = self.line[:self.curpos] + str + self.line[self.curpos:]
349 def arrow_back(self):
355 def arrow_forward(self):
356 if self.curpos < len(self.line):
361 def back_space(self):
364 self.line = self.line[:self.curpos] + self.line[self.curpos+1:]
368 if self.curpos < len(self.line):
369 self.line = self.line[:self.curpos] + self.line[self.curpos+2:]
374 if len(self.history)-1 == 0 or len(self.history)-1 != self.historypos:
376 self.templine = self.line
379 self.history.append(self.line)
380 self.historypos = len(self.history)-1
385 self.curpos = len(self.line)
387 def history_up(self):
388 if self.historypos >= 0:
389 self.line = self.history[self.historypos]
390 if self.historypos != 0:
395 def history_down(self):
396 if self.historypos >= 0 and self.historypos < len(self.history)-1:
398 self.line = self.history[self.historypos]
401 self.historypos = len(self.history)-1
402 self.set(self.templine)
411 sys.stdout.write('\x1b[2K\x1b[80D')
414 sys.stdout.write('\x1b[1D')
417 sys.stdout.write('\x1b[1C')
419 def display_prompt():
420 sys.stdout.write(bcolors.OKBLUE+Data.promptAmbctl+bcolors.WHITE+Data.promptEnd);
425 sys.stdout.write(data.line)
426 cursorpos = len(data.line) - data.curpos
427 for x in xrange(cursorpos):
431 def handle_keyboard(source, cond, data):
433 #print "char: ", ord(str)
436 if ord(str[0]) == 27 and ord(str[1]) == 91 and ord(str[2]) == 68:
438 if data.arrow_back():
441 elif ord(str[0]) == 27 and ord(str[1]) == 91 and ord(str[2]) == 67:
443 if data.arrow_forward():
446 elif ord(str[0]) == 27 and ord(str[1]) == 91 and ord(str[2]) == 70:
448 while data.arrow_forward():
451 elif ord(str[0]) == 27 and ord(str[1]) == 91 and ord(str[2]) == 72: #home
452 while data.arrow_back():
455 elif len(str) == 4 and ord(str[0]) == 27 and ord(str[1]) == 91 and ord(str[2]) == 51 and ord(str[3]) == 126:
459 elif ord(str[0]) == 27 and ord(str[1]) == 91 and ord(str[2]) == 65:
463 while data.arrow_forward():
466 elif ord(str[0]) == 27 and ord(str[1]) == 91 and ord(str[2]) == 66:
469 while data.arrow_forward():
477 words = data.line.split(' ')
478 if words[0] == "quit":
479 termios.tcsetattr(fd, termios.TCSAFLUSH, old)
480 fcntl.fcntl(fd, fcntl.F_SETFL, oldflags)
484 processCommand(words[0], words[1:])
486 processCommand(words[0], [])
487 except dbus.exceptions.DBusException, error:
490 print "Error running command ", sys.exc_info()[0]
491 traceback.print_stack()
495 elif ord(str) == 127: #backspace
501 wordsList = data.line.split(' ')
502 toComplete = wordsList[-1]
503 results, samestring = data.autocomplete.complete(toComplete)
504 if len(samestring) and len(samestring) > len(toComplete) and not (samestring == toComplete):
505 if len(wordsList) > 1:
506 data.line = ' '.join(wordsList[0:-1]) + ' ' + samestring
508 data.line = samestring
509 while data.arrow_forward():
512 elif len(results) and not results[0] == toComplete:
514 if len(results) <= 3:
515 print ' '.join(results)
519 if len(r) > longestLen:
522 while i < len(results):
525 if len(results) < i+3:
526 numCols = len(results) - i
527 for n in xrange(numCols):
529 for n in xrange((longestLen + 5) - len(results[i])):
535 elif curses.ascii.isprint(ord(str)) or ord(str) == curses.ascii.SP: #regular text
540 print "@PROJECT_PRETTY_NAME@ @PROJECT_VERSION@"
543 fd = sys.stdin.fileno()
544 old = termios.tcgetattr(fd)
545 new = termios.tcgetattr(fd)
546 new[3] = new[3] & ~termios.ICANON & ~termios.ECHO
547 termios.tcsetattr(fd, termios.TCSANOW, new)
549 oldflags = fcntl.fcntl(fd, fcntl.F_GETFL)
550 fcntl.fcntl(fd, fcntl.F_SETFL, oldflags | os.O_NONBLOCK)
552 io_stdin = glib.IOChannel(fd)
553 io_stdin.add_watch(glib.IO_IN, handle_keyboard, data)
559 main_loop = gobject.MainLoop(None, False)
561 except KeyboardInterrupt:
564 traceback.print_stack()
566 termios.tcsetattr(fd, termios.TCSAFLUSH, old)
567 fcntl.fcntl(fd, fcntl.F_SETFL, oldflags)
573 processCommand(args.command, args.commandArgs, False)
574 except dbus.exceptions.DBusException, error: