1. 程式人生 > >Python程式封裝為win32服務

Python程式封裝為win32服務

# encoding=utf-8
import os
import sys
import winerror
import win32serviceutil
import win32service
import win32event
import servicemanager


class PythonService(win32serviceutil.ServiceFramework):

    # 服務名
    _svc_name_ = "PythonService1"
    # 服務顯示名稱
    _svc_display_name_ = "PythonServiceDemo"
    # 服務描述
    _svc_description_ = "Python service demo."

    def __init__(self, args):
        win32serviceutil.ServiceFramework.__init__(self, args)
        self.hWaitStop = win32event.CreateEvent(None, 0, 0, None)
        self.logger = self._getLogger()
        self.isAlive = True

    def _getLogger(self):
        import logging
        import os
        import inspect

        logger = logging.getLogger('[PythonService]')

        this_file = inspect.getfile(inspect.currentframe())
        dirpath = os.path.abspath(os.path.dirname(this_file))
        handler = logging.FileHandler(os.path.join(dirpath, "service.log"))

        formatter = logging.Formatter('%(asctime)s %(name)-12s %(levelname)-8s %(message)s')
        handler.setFormatter(formatter)

        logger.addHandler(handler)
        logger.setLevel(logging.INFO)

        return logger

    def SvcDoRun(self):
        import time
        self.logger.error("svc do run....")
        try:
            while self.isAlive:
                self.logger.error("I am alive.")
                time.sleep(1)
                # 等待服務被停止
                # win32event.WaitForSingleObject(self.hWaitStop, win32event.INFINITE)
        except Exception as e:
            self.logger.error(e)
            time.sleep(60)

    def SvcStop(self):
        # 先告訴SCM停止這個過程
        self.logger.error("svc do stop....")
        self.ReportServiceStatus(win32service.SERVICE_STOP_PENDING)
        # 設定事件
        win32event.SetEvent(self.hWaitStop)
        self.isAlive = False


if __name__ == '__main__':
    if len(sys.argv) == 1:
        try:
            src_dll = os.path.abspath(servicemanager.__file__)
            servicemanager.PrepareToHostSingle(PythonService)
            servicemanager.Initialize("PythonService", src_dll)
            servicemanager.StartServiceCtrlDispatcher()
        except Exception as e:
            print(e)
            #if details[0] == winerror.ERROR_FAILED_SERVICE_CONTROLLER_CONNECT:
                #win32serviceutil.usage()
    else:
        win32serviceutil.HandleCommandLine(PythonService)  # 引數和上述定義類名一致

#pip install pywin32

# 安裝服務
# python PythonService.py install
# 讓服務自動啟動
# python PythonService.py --startup auto install
# 啟動服務
# python PythonService.py start
# 重啟服務
# python PythonService.py restart
# 停止服務
# python PythonService.py stop
# 刪除/解除安裝服務
# python PythonService.py remove


# 在使用者變數處去掉python路徑,然後在環境變數加入python路徑
# C:\Users\zhongjianhui\AppData\Local\Programs\Python\Python36\Lib\site-packages\pywin32_system32;
# C:\Users\zhongjianhui\AppData\Local\Programs\Python\Python36\Lib\site-packages\win32;
# C:\Users\zhongjianhui\AppData\Local\Programs\Python\Python36\Scripts\;
#C:\Users\zhongjianhui\AppData\Local\Programs\Python\Python36\