win32service + pillow
• Python 3.12.6
• pillow 11.1.0
• pywin32 308
Пытаюсь сделать сервис для формирования скриншотов рабочего стола пользователя. На сейчас добился того, что сервис устанавливается и даже работает, но только в режиме debug при запуске сервиса, через PowerShell с правами Администратора:
python.exe .\service.py debug
Попытка запустить сервис используя:
python.exe .\service.py start
Ведет к ошибке:
screen grab failed
Журнал Windows, при попытке выполнить start сервиса сообщает об ошибке:
Служба завершена из-за следующей внутренней ошибки:
%%536870913
Код сервиса:
import socket
import win32serviceutil
import servicemanager
import win32event
import win32service
import time
import datetime
import configparser
import os
config = configparser.ConfigParser()
PATH_SCRIPT = os.path.dirname(os.path.realpath(__file__))
class SMWinservice(win32serviceutil.ServiceFramework):
_svc_name_ = 'name_my_service'
_svc_display_name_ = "display_name_my_service"
_svc_description_ = 'description_my_service'
@classmethod
def parse_command_line(cls):
win32serviceutil.HandleCommandLine(cls)
def __init__(self, args):
win32serviceutil.ServiceFramework.__init__(self, args)
self.hWaitStop = win32event.CreateEvent(None, 0, 0, None)
socket.setdefaulttimeout(60)
def SvcStop(self):
self.stop()
self.ReportServiceStatus(win32service.SERVICE_STOP_PENDING)
win32event.SetEvent(self.hWaitStop)
def SvcDoRun(self):
self.start()
servicemanager.LogMsg(servicemanager.EVENTLOG_INFORMATION_TYPE,
servicemanager.PYS_SERVICE_STARTED,
(self._svc_name_, ''))
self.main()
def start(self):
self.isrunning = True
def stop(self):
self.isrunning = False
def main(self):
while self.isrunning:
with open(f'{PATH_SCRIPT}\\config\\setting.ini', 'r', encoding='utf8') as file_object:
config.read_file(file_object)
try:
from PIL import ImageGrab
screenshot = ImageGrab.grab()
screenshot.save(f'{config["file"]["path_save_screen"]}\\{datetime.datetime.now().strftime("%d_%m_%Y__%H_%M_%S__screenshot")}.png', 'PNG')
except Exception as e:
with open(f'{PATH_SCRIPT}\\logs\\logging.log', 'a+', encoding='utf8') as log_file:
log_file.write(f'{datetime.datetime.now().strftime("%d/%m/%Y %H:%M:%S")} {e.__str__()}\n')
time.sleep(int(config["time"]["pause"]))
if __name__ == '__main__':
SMWinservice.parse_command_line()
Читал о подобных проблемах у людей: попробовал переместить скрипт в корень диска C: - чтобы он был на одном диске с python, пробовал добавить в переменные среды PATH до python - не помогло.
По идее скрипт запускается от имени администратора, а скриншот требуется сделать на учетке пользователя - возможно мне нужно выполнить что-то вроде запуска части скрипта от имени авторизованного в системе пользователя. Пока не нашел вариантов как это сделать внутри сервиса.
Буду благодарен за любые идеи.