Как я могу поймать событие приостановки системы в Python?

Я использую убунту 12.04. Есть ли способ поймать событие приостановки в Python, то есть, если ноутбук собирается приостановить работу, сделайте это...? Тот же вопрос для перехвата события выключения.


person koogee    schedule 23.11.2012    source источник
comment
Это касается перехвата события выхода из системы. но может вам помочь: stackoverflow.com/questions/2490166/   -  person theAlse    schedule 23.11.2012
comment
спасибо... посмотрю на gnome.ui   -  person koogee    schedule 23.11.2012
comment
Я бы попросил systemd записать файл в /tmp во время приостановки и другой файл во время возобновления, который моя программа будет опрашивать каждые 3-5 децисекунд. Кроме того, если бы моя программа имела доступ к Интернету, у меня был бы сетевой менеджер, создающий файл во время приостановки и возобновления, который моя программа будет опрашивать. DBUS сложный.   -  person WinEunuuchs2Unix    schedule 24.08.2020


Ответы (3)


я думаю, что самым простым методом было бы использовать интерфейс DBUS python и слушать для событий «AboutToSleep» и/или «Sleeping» в интерфейсе «org.freedesktop.UPower»

person Raber    schedule 23.11.2012
comment
тоже не могу его найти, раньше этим занимался HALd, но сейчас он устарел - person Raber; 27.11.2012
comment
я поместил сценарий оболочки в /etc/init.d/ и запустил его во время завершения работы. Скрипт выполняет ту работу, которую я хотел сделать на питоне. Мне бы хотелось, чтобы все события обрабатывались в одной программе на Python, но я соглашусь на использование разных скриптов. - person koogee; 27.11.2012

Если кто-то наткнется на ту же проблему, вот код:

#!/usr/bin/env python

import dbus      # for dbus communication (obviously)
import gobject   # main loop
from dbus.mainloop.glib import DBusGMainLoop # integration into the main loop

def handle_resume_callback():
    print "System just resumed from hibernate or suspend"

def handle_suspend_callback():
    print "System about to hibernate or suspend"

DBusGMainLoop(set_as_default=True) # integrate into main loob
bus = dbus.SystemBus()             # connect to dbus system wide
bus.add_signal_receiver(           # defince the signal to listen to
    handle_resume_callback,            # name of callback function
    'Resuming',                        # singal name
    'org.freedesktop.UPower',          # interface
    'org.freedesktop.UPower'           # bus name
)

bus.add_signal_receiver(           # defince the signal to listen to
    handle_suspend_callback,            # name of callback function
    'Sleeping',                        # singal name
    'org.freedesktop.UPower',          # interface
    'org.freedesktop.UPower'           # bus name
)

loop = gobject.MainLoop()          # define mainloop
loop.run()                         # run main loop
person koogee    schedule 25.11.2012
comment
за исключением того, что только настольные системы имеют dbus - person LtWorf; 03.02.2014
comment
Начиная с более новых версий upower, сигнал переместился на systemd logind, новый интерфейс — org.freedesktop.login1.Manager, новое имя шины — org.freedesktop.login1, а новый сигнал — PrepareForSleep с аргументом: True для приостановки. , False для возобновления. Дополнительная информация здесь: serverfault.com/questions/573379/ - person totaam; 17.03.2014

Вы можете расширить этот код, он прослушивает события от acpid, попробуйте просто напечатать полученную строку, сгенерировать нужное событие и посмотреть, как выглядит строка.

s = socket.socket(socket.AF_UNIX, socket.SOCK_STREAM)
s.connect("/var/run/acpid.socket")
print "Connected to acpid"
while 1:
    for event in s.recv(4096).split('\n'):
        event=event.split(' ')
        if len(event)<2: continue
        print event
        if event[0]=='ac_adapter':
            if event[3]=='00000001': #plugged
                plugged() #Power plugged event
            else: #unplugged
                unplugged() #Power unplugged event
        elif event[0]=='button/power':
            power_button() #Power button pressed
        elif event[0]=='button/lid':
            if event[2]=='open':
                lid_open() #Laptop lid opened
            elif event[2]=='close':
                lid_close() #Laptop lid closed
person LtWorf    schedule 23.11.2012
comment
благодаря. это то, что я искал. Кстати, где вы можете получить список того, что означают эти коды? например 000000081? - person koogee; 23.11.2012
comment
Хм, честно говоря, понятия не имею, я получил их, сгенерировав события и посмотрев, как выглядела строка, вы можете попытаться увидеть в документации acpid, который является демоном, отправляющим эти строки. - person LtWorf; 23.11.2012
comment
это странно. Кажется, я получаю только один из сигналов открытия/закрытия крышки после приостановки/возобновления. ['процессор', 'CPU0', '00000081', '00000000'] ['кнопка/крышка', 'LID0', '00000080', '00000003'] ['процессор', 'CPU0 ', '00000081', '00000000'] ['ac_adapter', 'ADP0', '00000080', '00000000'] ['аккумулятор', 'BAT0', '00000080', '00000001'] ['процессор', ' ЦП0", "00000081", "00000000"] - person koogee; 23.11.2012
comment
Возможно, другой не генерируется как событие ACPI или не на вашем ноутбуке, или если вы приостанавливаете работу при закрытии крышки, когда вы открываете, она все еще приостановлена, и вы теряете событие. - person LtWorf; 24.11.2012