15

I am trying to get a list of currently plugged in USB devices in Ubuntu 10.10 and monitor changes that happen, like devices being plugged in or out using UDev and D-BUS. I'm fairly new to programming using D-BUS. I saw one example: Linux : How to detect is usb keyboard is plugged and unplugged only that one uses HAL and I know that HAL is deprecated. I found some working code, modified it a bit, only it doesn't work for any device only storage devices such as usb sticks, media players or cd-rom devices. I want the whole thing mice, keyboards, usb cameras chargers anything that is plugged in to the USB I want my program to know about it. This is basically what I have ( http://moserei.de/2010/01/08/accessing-devicekit-with-dbus-and-python.html ):

import dbus
import gobject
from dbus.mainloop.glib import DBusGMainLoop

def device_added_callback(device):
    print 'Device %s was added' % (device)

def device_changed_callback(device):
    print 'Device %s was changed' % (device)

#must be done before connecting to DBus
DBusGMainLoop(set_as_default=True)

bus = dbus.SystemBus()

proxy = bus.get_object("org.freedesktop.UDisks", 
                       "/org/freedesktop/UDisks")
iface = dbus.Interface(proxy, "org.freedesktop.UDisks.Device")

devices = iface.get_dbus_method('EnumerateDevices')()

print '%s' % (devices)

#addes two signal listeners
iface.connect_to_signal('DeviceAdded', device_added_callback)
iface.connect_to_signal('DeviceChanged', device_changed_callback)

#start the main loop
mainloop = gobject.MainLoop()
mainloop.run()

Any help would be apreciated. Thank you in advance, Calota Romeo

Community
  • 1
  • 1
Calota Romeo
  • 153
  • 1
  • 1
  • 4
  • 1
    For the future reference (I was looking for exactly this code, not a generic usb handler), you need to change: iface = dbus.Interface(proxy, "org.freedesktop.UDisks.Device") to iface = dbus.Interface(proxy, "org.freedesktop.UDisks") at least when udisks 1.0.4 is used. – Miro Kropacek Nov 27 '12 at 10:26

2 Answers2

10

The udisks D-Bus service, obviously, only reports disks.

Just monitor udev directly (through libudev, through pyudev).

import pyudev
context = pyudev.Context()
monitor = pyudev.Monitor.from_netlink(context)
observer = pyudev.pygtk.GUDevMonitorObserver(monitor)
observer.connect('device-added', device_added_callback)
observer.connect('device-changed', device_changed_callback)
monitor.enable_receiving()
mainloop = gobject.MainLoop()
mainloop.run()
ephemient
  • 180,829
  • 34
  • 259
  • 378
  • Thanks for the help I managed to get something working based on your answer. – Calota Romeo Feb 26 '11 at 14:20
  • How would callback function actually look like? I don't find information on the parameters the `device-added` and `device-changed` signals pass to the callback. I want to see if a device with a specific `idVendor` and `idProduct` is connected and could use some help. Thanks in advance. – con-f-use Aug 31 '12 at 22:48
  • @con-f-use As listed on [pyudev.glib](http://pyudev.readthedocs.org/en/latest/api/glib.html), those two signals will invoke their callbacks with two arguments, the second of which is a [device](http://pyudev.readthedocs.org/en/latest/api/pyudev.html#pyudev.Device) with attributes in [`device.attributes`](http://pyudev.readthedocs.org/en/latest/api/pyudev.html#pyudev.Device.attributes). – ephemient Aug 31 '12 at 23:10
  • 1
    I get `AttributeError: 'module' object has no attribute 'pygtk'`. Can you elaborate on this answer a little bit? Is it possible to get the drive `UUID` from this, so you can perform an action only when a specific drive is added? – Redsandro Jan 03 '13 at 14:18
  • @Redsandro http://pyudev.readthedocs.org/en/latest/api/pyudev.html#monitorobserver-asynchronous-device-monitoring – mlt Jul 16 '13 at 02:05
2

This is what I use to list already plugged flash sticks. You can modify script to your needs

import dbus  
bus = dbus.SystemBus()

proxy = bus.get_object("org.freedesktop.Hal", "/org/freedesktop/Hal/Manager")
iface = dbus.Interface(proxy, "org.freedesktop.Hal.Manager")

devices = iface.GetAllDevices ()

for device in devices:
  try:
      proxy1 = bus.get_object("org.freedesktop.Hal", device)
      iface1 = dbus.Interface(proxy1, "org.freedesktop.Hal.Device")
      props = iface1.GetAllProperties()

      removable = iface1.GetProperty("storage.removable")
      usb = iface1.GetProperty("storage.bus")
      if usb== "usb":
        print "\n".join(("%s: %s" % (k, props[k]) for k in props)) # shows available properties
  except:
    pass

And this is what I use to see if any usb plugged :

#!/usr/bin/python
import dbus
import gobject

class DeviceAddedListener:
                def __init__(self):
                                self.bus = dbus.SystemBus()
                                self.hal_manager_obj = self.bus.get_object("org.freedesktop.Hal", "/org/freedesktop/Hal/Manager")
                                self.hal_manager = dbus.Interface(self.hal_manager_obj,"org.freedesktop.Hal.Manager")

                                self.hal_manager.connect_to_signal("DeviceAdded", self._filter) 

                def _filter(self, udi):
                                device_obj = self.bus.get_object ("org.freedesktop.Hal", udi)
                                device = dbus.Interface(device_obj, "org.freedesktop.Hal.Device")
                                self.do_something(device)

                def do_something(self, device):
                                try:

                                                usb = device.GetProperty("storage.bus")
                                                info = device.GetProperty("info.product")
                                                removable = device.GetProperty("storage.removable")
                                                print info
                                except:
                                                pass#blah blah


if __name__ == '__main__':
                from dbus.mainloop.glib import DBusGMainLoop
                DBusGMainLoop(set_as_default=True)
                loop = gobject.MainLoop()
                DeviceAddedListener()
                loop.run()

Here is the example of UDisks : python udisks - enumerating device information

Community
  • 1
  • 1
savruk
  • 535
  • 5
  • 20
  • 2
    Relies on HAL, which is deprecated and no longer present in the newest Linux distributions. – ephemient Feb 25 '11 at 17:19
  • @ephemient yes you are right. But I think using "UDisks" cannot be so different.@Calota I hope this works for you – savruk Feb 28 '11 at 07:39