Press "Enter" to skip to content

Sending desktop notification in Linux with Python with D-Bus directly

I recently found a lot of third-party libraries that help send desktop notifications in Linux. I just don’t get it. Most of these libraries just wrap the call to libnotify‘s notify-send into a function or even an over-engineered class. You don’t really need these third-party libraries to do the job… You can do the same job with merely two or three new lines in your code. notify-send is a command-line tool. You can call the command-line tool through Python’s subprocess:

import subprocess

subprocess.run(
["notify-send", "-u", "normal", "-t", "3000",
"Hello world", "This is the notification body."],
check=True)
Using `subprocess` to call `notify-send`

notify-send is a quick solution but requires libnotify and a call to an external executable. I don’t like it. Therefore, I always send the notification directly with D-Bus’ Python binding. Most desktop notification servers follow a standard called Desktop Notifications Specification. It exposes a D-Bus interface at org.freedesktop.Notifications and a method org.freedesktop.Notifications.Notify to send notifications from users’ applications. It’s OK if you don’t know anything about D-Bus. Just remember that you can send a desktop notification through D-Bus’ Python binding:

import dbus

item = "org.freedesktop.Notifications"

notfy_intf = dbus.Interface(
dbus.SessionBus().get_object(item, "/"+item.replace(".", "/")), item)

notfy_intf.Notify(
"", 0, "", "Hello world!", "This is the notification body.",
[], {"urgency": 1}, 3000)
Sending a notification through D-Bus' Python binding

The D-Bus’ Python binding can be installed from PyPI:

$ pip install dbus-python
Installing D-Bus' Python binding

In notfy_intf.Notify, the fourth argument is the notification title, and the content body is at the fifth argument. Regarding the urgency, 0, 1, and 2 mean low, normal, and critical. The last argument indicates how long the notification box will be visible on the screen. The unit is milliseconds. So the 3000 here means 3 seconds. To understand the details of the arguments in the notfy_intf.Notify, refer to the documentation of org.freedesktop.Notifications.Notify.

You can now see that you don’t really need those third-party libraries to send simple desktop notifications.

4 Comments

  1. Hi, this sounds fine when notifications are sent by the same user that is logged in but when trying to run this from a Python script running as root it won’t work because the root user doesn’t have access to another user’s DBus. So, how to solve this issue elegantly? Is there a way to patch root notifications through a dispatcher that would relay them to user’s desktop, or is there an easier, safer and more consistent way? i’m talking about wide compatibility with most common desktops out there: Xfce, GNOME, MATE, Cinnamon, KDE Plasma, Trinity etc.

  2. Actually that’s not accurate. Having just tested the code in Mint 19.2 Cinnamon I noticed notifications are being delivered when run as root, but through a different daemon and/or settings than the regular user notification daemon. This is not elegant at all. It is also possible that a given system does not have any additional notification daemon installed and/or available.

    So the question remains: how to connect to the regular daemon in order to send notifications that match the user settings?

  3. Philstix Philstix

    What are the other parameters used for in the notfy_intf.Notify() call?

    I assume one is for an icon and another is for notification actions.

    Any pointers to a reference that details the requirements to use those other parameters?

Leave a Reply

Your email address will not be published. Required fields are marked *

This site uses Akismet to reduce spam. Learn how your comment data is processed.