Python 3 Windows 服务仅在 Debug模式下启动

标签 python windows python-3.x debugging service

我首先在 this post 中发布了一个答案,但不符合论坛标准。我希望这次的回答符合论坛标准。这段代码应该更清晰易读。

在 Python 3+ 中,我使用以下类来构建 Windows 服务(它什么都不做,只是写入一个日志文件):

#MyWindowsService.py
import win32serviceutil
import servicemanager
import win32service
import win32event
import sys
import logging
import win32api


class MyWindowsService(win32serviceutil.ServiceFramework):
    _svc_name_          = 'ServiceName'
    _svc_display_name_  = 'Service Display Name'
    _svc_description_   = 'Service Full Description'
    logging.basicConfig(
        filename    = 'c:\\Temp\\{}.log'.format(_svc_name_),
        level       = logging.DEBUG,
        format      = '%(levelname)-7.7s @ %(asctime)s: %(message)s'
    )

    def __init__(self, *args):
        self.log('Initializing service {}'.format(self._svc_name_))
        win32serviceutil.ServiceFramework.__init__(self, *args)
        self.stop_event = win32event.CreateEvent(None, 0, 0, None)

    def SvcDoRun(self):
        self.ReportServiceStatus(win32service.SERVICE_START_PENDING)
        try:
            self.log('START: Service start')
            self.ReportServiceStatus(win32service.SERVICE_RUNNING)
            self.start()
            win32event.WaitForSingleObject(self.stop_event, win32event.INFINITE)
        except Exception as e:
            self.log('Exception: {}'.format(e))
            self.SvcStop()

    def SvcStop(self):
        self.log('STOP: Service stopping...')
        self.ReportServiceStatus(win32service.SERVICE_STOP_PENDING)
        self.stop()
        win32event.SetEvent(self.stop_event)
        self.ReportServiceStatus(win32service.SERVICE_STOPPED)

    def log(self, msg):
        servicemanager.LogInfoMsg(str(msg))  #system log
        logging.info(str(msg))               #text log

    def start(self):
        self.runflag = True
        while self.runflag:
            win32api.Sleep((2*1000), True)
            self.log('Service alive')
    def stop(self): 
        self.runflag = False
        self.log('Stop received')




if __name__ == '__main__':
    win32serviceutil.HandleCommandLine(MyWindowsService)

在脚本中,我使用日志文件来检查它是否正常工作。我在 Windows 7 上运行 python3.6(也尝试过 python3.4),我遇到了以下问题。当我运行 python MyWindowsService.py install 时,提示说服务已经安装(但日志文件中没有任何内容)。如果我尝试启动该服务,我会收到 Service Error: 1 - More info NET HELPMSG 3547 并没有说明该错误。如果我运行 python MyWindowsService.py debug,程序运行得很好(日志文件已写入),但我仍然无法控制该服务:如果我打开另一个提示并尝试停止/启动服务我仍然得到与上述相同的结果。

我还尝试在 init 函数中插入一些调试代码,当我运行 python MyWindowsService.py install 时,它似乎没有被调用。可能吗?

我在网上查找了多种解决方案和变通方法,但没有找到合适的。我错过了什么?

最佳答案

正如 eriksun 在对第一篇文章的评论中指出的那样,问题出在 python 脚本的位置,即在映射有 UNC 路径的驱动器中 - 我正在使用虚拟机。将 python 脚本移动到与 python 安装相同的驱动器中完成了这项工作。 总结一下以备将来使用,如果服务无法启动并且您对自己的代码非常确定,这些是尝试解决问题的有用操作:

  • 使用 sc start ServiceNamesc query ServiceNamesc stop ServiceName 获取有关服务的信息。
  • 检查您的文件是在物理驱动器中还是在 UNC 映射驱动器中。如果后者尝试使用 UNC 路径运行脚本(例如 python\\Server\share\python\your-folder\script.py)或将脚本移动到与 python 相同的驱动器中安装
  • 确保“python36.dll”、“vcruntime140.dll”和“pywintypes36.dll”已符号链接(symbolic link)到具有 PythonService.exe 的目录;或符号链接(symbolic link)到 System32 目录;或者具有这些 DLL 的目录在系统(而非用户)路径中
  • 使用命令 reg query HKLM\System\CurrentControlSet\Services\your_service_name/s 检查系统寄存器以获取有关脚本的更多信息

请随时完成、更改、修改最后一个,以便它对像我一样遇到此问题的任何人都有用。

编辑:还有一件事......我的项目被认为实际上可以与网络文件夹(和 UNC 映射的驱动器)一起工作,但当我试图让它作为服务运行时它失败了。我用来让它工作的一个非常有用的(节省一天的)资源是 SysinternalsSuite by Mark Russinovich我在 this post 中找到的.希望这可以帮助。

关于Python 3 Windows 服务仅在 Debug模式下启动,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/42599705/

相关文章:

python - Windows 10 pip 安装 'Failed Connection'

python - 在 flask 登录当前用户中设置属性以供以后访问

python - 如何本地附加到 python 进程?

mysql - 使用 MySQL Workbench 从 Windows 连接到远程 MySQL DB (Linux)。远程数据库连接需要本地套接字

c++ - 无法使用 C++ 程序禁用设备管理器

python - 如何在 Windows 7 中运行 python

python - Pandas date_range 和闰年

python - 在 Flask 应用程序中使用 uwsgi 部署时,keras 预测会卡住

Python:for循环+break与while+flag性能

python - 从消息中获取图片