2

我正在从 Windows 服务(在 python 中创建,使用 pyinstaller 转换为 exe 并使用 sc 安装)启动一个 python 应用程序(使用 pyInstaller 创建的 exe 版本),但我的应用程序生成的日志文件没有得到轮换。

所以我实际上使用了一个 logger.conf 文件,该文件具有记录器配置和旋转文件处理程序,以在每 10KB 后旋转文件(用于测试目的)。conf 文件中的配置如下所示:

...
[handler_fileRotationHandler]
class=logging.handlers.RotatingFileHandler
level=NOTSET
formatter=simpleFormatter
args=('<absolute path of log file>','a',10240,5)
...

在 python 代码中,我使用这个配置来创建和轮换日志文件。

以下是正确的日志文件轮换工作的情况列表:

1- python 版本使用 python 命令启动
2- exe 版本(使用 PyInstaller 创建)在直接双击启动时工作正常
3- 从 Windows 服务启动时的 exe 版本也使用 python 创建,如果服务是使用 python 命令安装的如下所示:

MyService.py install

现在是它不起作用的时候:
我正在将 Windows 服务代码转换为 exe(再次使用 pyInstaller)并使用以下命令使用 sc 安装服务:

sc create MyService binPath= "<absolute path of service exe file>"

开始使用此服务时,应用程序运行良好,并且也生成了日志文件,但在达到 fileHandler 中为日志定义的最大大小后,它不会创建另一个日志文件,因此只会卡在那里的日志。该应用程序一直运行良好,只是没有记录日志。

这是我尝试并观察到的:
1- 在这两种情况下,我都使用 subprocess.Popen() 命令启动了我的应用程序 exe 版本,并且我的应用程序没有任何 UI 元素,因此它在后台的 Windows 会话 0 中完美运行。仅供参考,以防万一。
2-如果我删除现有的日志语句并清空日志文件,则日志开始记录到文件中,并在达到最大大小时再次停止。
3-我已经使用 os.getcwd() 命令来获取我的应用程序在启动时运行的目录,在这两种情况下我都在以下目录中找到:

在使用 python 案例安装的 python 服务中,应用程序在 "C:\Users\\AppData\Local\Programs\Python\Python36\lib\site-packages\win32" 中运行

在从使用 sc 案例安装的服务启动的 exe 版本中,应用程序在“C:\Windows\system32”中运行

虽然在这两种情况下,logging.conf 文件都提供了日志文件的创建路径,所以我假设这不应该是任何问题(事实上,日志文件确实是在预期的位置创建的,只是文件轮换不起作用,所以我猜测不相关)

我只需要使用 sc 安装的 exe 版本,而不是 python 服务版本。如何解决这个问题,任何帮助或指导或方向表示赞赏。

4

1 回答 1

2

[对于任何有兴趣了解解决方案的人]

因此,我面临的问题是 RotationFileHandler 中的一个常见问题,即两个处理程序同时处理同一个文件,从而阻碍了 RotationFileHandler 重命名填充的日志文件。

为了详细说明,我将异常处理放在 RotationFileHandler 源代码的 handler.py 中,并将异常打印在一个文件中。从那里我得到的问题是:

...
[WinError 32] The process cannot access the file because it is being used by another process: 'C:\\Users\\<path to log>\\test.log' -> 'C:\\Users\\<path to log>\\test.log.1'
...

在搜索更多内容时,我发现这是 Windows 记录器中 FileRotationHandler 的常见情况,有时由于多种原因,多个句柄对同一个日志文件打开,因此,旋转文件处理程序无法重命名文件。

偶然发现这个线程解释了许多可能的场景

我使用 procexp 工具检查我的日志文件是否有多个句柄(由其他应用程序打开)。我发现,因为我对服务代码和应用程​​序代码都使用了相同的 logging.conf,所以它们都有打开的句柄来记录两者的文件。我为服务代码创建了一个单独的配置文件,问题就消失了。:)

我唯一不知道的是为什么这只发生在服务和应用程序的 exe 版本中而不是 python 版本中,因为理想情况下,问题也应该在作为 python 代码运行时发生。

于 2019-06-14T15:55:13.390 回答