Я пытаюсь создать сценарий, который прослушивает dbus уведомлений рабочего стола и выводит отправителя и сообщение в командную строку.... конечная цель - запустить определенную функцию, когда я получаю определенное уведомление.
Я пробовал использовать dbus-monitor --session, который распечатывает данные, когда я получаю уведомление, но я не вижу фактического уведомления. Я попросил Gemini AI написать код на Python, этот код работает, но когда я получаю уведомление, ничего не происходит.
Код: Выделить всё
import asyncioКод: Выделить всё
from dbus_next.aio import MessageBusКод: Выделить всё
from dbus_next.constants import BusType, MessageTypeКод: Выделить всё
from dbus_next import Message, VariantКод: Выделить всё
import loggingКод: Выделить всё
# Set up basic loggingКод: Выделить всё
# Note: We are only using INFO level for connection status, Код: Выделить всё
# message processing is handled via print() for clarity.Код: Выделить всё
logging.basicConfig(level=logging.INFO, format='%(levelname)s: %(message)s')Код: Выделить всё
# --- DBus Interface Constants ---Код: Выделить всё
# The D-Bus service name for notificationsКод: Выделить всё
NOTIF_SERVICE = 'org.freedesktop.Notifications'Код: Выделить всё
# The D-Bus object path for notificationsКод: Выделить всё
NOTIF_PATH = '/org/freedesktop/Notifications'Код: Выделить всё
# The D-Bus interface for notificationsКод: Выделить всё
NOTIF_INTERFACE = NOTIF_SERVICEКод: Выделить всё
# ANSI escape codes for bold textКод: Выделить всё
BOLD_START = '\033[1m'Код: Выделить всё
BOLD_END = '\033[0m'Код: Выделить всё
def message_handler(message):Код: Выделить всё
"""Код: Выделить всё
Generic handler for D-Bus messages, focusing only on new notificationsКод: Выделить всё
(Notify method calls) and printing the sender, summary, and message body.Код: Выделить всё
"""Код: Выделить всё
if message.interface == NOTIF_INTERFACE:Код: Выделить всё
Код: Выделить всё
# --- Handle New Notification (Method Call) ---Код: Выделить всё
if message.message_type == MessageType.METHOD_CALL and message.member == 'Notify':Код: Выделить всё
# Notify arguments: (app_name, replaces_id, app_icon, summary, body, actions, hints, expire_timeout)Код: Выделить всё
Код: Выделить всё
# Ensure we have enough arguments (at least app_name and body)Код: Выделить всё
if len(message.body) >= 8:Код: Выделить всё
app_name = message.body[0] # App Name (Sender)Код: Выделить всё
summary = message.body[3] # Notification Summary (Title)Код: Выделить всё
body_text = message.body[4] # Notification Body (Main message)Код: Выделить всё
Код: Выделить всё
# Combine summary and body for the messageКод: Выделить всё
# If both exist, use "Summary: Body". If only one exists, use that.Код: Выделить всё
if summary and body_text:Код: Выделить всё
message_content = f"{summary}: {body_text}"Код: Выделить всё
elif summary:Код: Выделить всё
message_content = summaryКод: Выделить всё
else:Код: Выделить всё
message_content = body_textКод: Выделить всё
output = f"[{app_name}] {message_content}"Код: Выделить всё
Код: Выделить всё
# Apply bold formatting if the sender is Discord (case-insensitive check)Код: Выделить всё
if app_name.lower() == 'discord':Код: Выделить всё
output = f"{BOLD_START}{output}{BOLD_END}"Код: Выделить всё
Код: Выделить всё
print(output)Код: Выделить всё
Код: Выделить всё
# Log other relevant messages (like replies to GetCapabilities)Код: Выделить всё
else:Код: Выделить всё
logging.debug(f"[D-Bus Message] Type: {message.message_type.name}, Member: {message.member}, Body: {message.body}")Код: Выделить всё
async def notification_listener(bus):Код: Выделить всё
"""Код: Выделить всё
Configures the bus to listen for all messages related to theКод: Выделить всё
org.freedesktop.Notifications interface.Код: Выделить всё
"""Код: Выделить всё
# 1. Add the generic message handlerКод: Выделить всё
bus.add_message_handler(message_handler)Код: Выделить всё
# 2. Use AddMatch to filter messages directed to this interfaceКод: Выделить всё
# This is crucial for catching the 'Notify' method call.Код: Выделить всё
# The rule is updated to match on the specific method call ('Notify') rather thanКод: Выделить всё
# relying solely on the destination service, which is a more robust way to captureКод: Выделить всё
# new notification requests.Код: Выделить всё
match_rule = f"type='method_call', interface='{NOTIF_INTERFACE}', member='Notify'"Код: Выделить всё
Код: Выделить всё
await bus.call(Код: Выделить всё
Message(Код: Выделить всё
destination='org.freedesktop.DBus',Код: Выделить всё
path='/org/freedesktop/DBus',Код: Выделить всё
interface='org.freedesktop.DBus',Код: Выделить всё
member='AddMatch',Код: Выделить всё
signature='s',Код: Выделить всё
body=[match_rule]Код: Выделить всё
)Код: Выделить всё
)Код: Выделить всё
logging.info("Listening for ALL D-Bus Messages on org.freedesktop.Notifications interface.")Код: Выделить всё
logging.info("To test, send a notification, e.g., 'notify-send Hello World'")Код: Выделить всё
Код: Выделить всё
# Keep the asyncio loop running indefinitelyКод: Выделить всё
await asyncio.get_running_loop().create_future()Код: Выделить всё
async def main():Код: Выделить всё
"""Код: Выделить всё
The main entry point for the script.Код: Выделить всё
"""Код: Выделить всё
try:Код: Выделить всё
logging.info(f"Attempting to connect to the D-Bus session bus...")Код: Выделить всё
bus = await MessageBus(bus_type=BusType.SESSION).connect()Код: Выделить всё
logging.info("Successfully connected to the D-Bus session bus.")Код: Выделить всё
Код: Выделить всё
# Attempt to call the GetCapabilities method to ensure the service is runningКод: Выделить всё
reply = await bus.call(Код: Выделить всё
Message(Код: Выделить всё
destination=NOTIF_SERVICE,Код: Выделить всё
path=NOTIF_PATH,Код: Выделить всё
interface=NOTIF_INTERFACE,Код: Выделить всё
member='GetCapabilities',Код: Выделить всё
signature='',Код: Выделить всё
body=[]Код: Выделить всё
)Код: Выделить всё
)Код: Выделить всё
Код: Выделить всё
if reply.message_type == MessageType.METHOD_RETURN:Код: Выделить всё
caps = reply.body[0]Код: Выделить всё
logging.info(f"Notification service capabilities retrieved: {caps}")Код: Выделить всё
await notification_listener(bus)Код: Выделить всё
else:Код: Выделить всё
# This often means no notification daemon (like dunst or a desktop environment's service) is running.Код: Выделить всё
logging.error("Could not retrieve notification service capabilities. Is a notification daemon running?")Код: Выделить всё
except Exception as e:Код: Выделить всё
logging.error(f"Error during D-Bus setup or initial capability check: {e}")Код: Выделить всё
if __name__ == "__main__":Код: Выделить всё
try:Код: Выделить всё
# Run the main coroutineКод: Выделить всё
asyncio.run(main())Код: Выделить всё
except KeyboardInterrupt:Код: Выделить всё
logging.info("Notification listener stopped by user.")Код: Выделить всё
except Exception as e:Код: Выделить всё
logging.error(f"An unexpected error occurred: {e}")Я нашел [это сообщение][1], в котором был скрипт Python, который мне пришлось обновить для работы с py3. Этот скрипт запускается, но ничего не происходит, когда я получаю уведомление или отправляю его через notify-send
Код: Выделить всё
import giКод: Выделить всё
gi.require_version("Gtk", "3.0") # or "4.0" depending on your target GTK versionКод: Выделить всё
from gi.repository import GtkКод: Выделить всё
import dbusКод: Выделить всё
from dbus.mainloop.glib import DBusGMainLoopКод: Выделить всё
def filter_cb(bus, message):Код: Выделить всё
# the NameAcquired message comes through before match string gets appliedКод: Выделить всё
if message.get_member() != "Notify":Код: Выделить всё
returnКод: Выделить всё
args = message.get_args_list()Код: Выделить всё
# args areКод: Выделить всё
# (app_name, notification_id, icon, summary, body, actions, hints, timeout)Код: Выделить всё
print("Notification from app '%s'" % args[0])Код: Выделить всё
print("Summary: %s" % args[3])Код: Выделить всё
print("Body: %s", args[4])Код: Выделить всё
DBusGMainLoop(set_as_default=True)Код: Выделить всё
bus = dbus.SessionBus()Код: Выделить всё
bus.add_match_string(Код: Выделить всё
"type='method_call',interface='org.freedesktop.Notifications',member='Notify'")Код: Выделить всё
bus.add_message_filter(filter_cb)Код: Выделить всё
Gtk.main()[1]: http://askubuntu.com/questions/38733/ho ... tor-output
Подробнее здесь: https://stackoverflow.com/questions/798 ... ian-ubuntu
Мобильная версия