0

我有一个工作进程,它在启动时加载一个特殊的数据结构,然后定期加载。

但是,数据结构——第三方 C++ 模块——存在内存泄漏。

我尝试使用 gunicorn "max_requests" 设置让工作人员在这么多请求后过期,这会清除他们的资源并重新加载数据结构。但是有一些我不会讨论的挑剔的问题。

我尝试添加一个 os._exit(0),迫使工作人员停止(并重新加载),但这意味着该请求得到了错误响应。

我想做的是向 gunicorn 发出信号以发送响应,然后杀死工作人员,就像触发了“max_requests”标志一样。

有没有一种机制可以做到这一点?

4

1 回答 1

0

reload 内置函数对于重新初始化模块很有用,但在该函数的文档中(http://docs.python.org/2/library/functions.html#reload),你会发现:“除了 sys, mainbuiltin之外,重新加载内置或动态加载的模块通常不是很有用,但这是合法的。然而,在许多情况下,扩展模块不会被设计为多次初始化,并且可能会以任意方式失败重新加载时。” 换句话说,它可能无法解决您的问题。

但是,如果您能够将对第三方模块的调用移动到子进程中,则很容易确保每次都重新加载它,因为您现在通过在单独的进程中执行脚本来使用该模块。只需创建一个单独的 py 文件,例如 do_something.py,您可以在其中完成您需要对子进程执行的所有操作。然后您可以使用以下命令运行此文件:

p = subprocess.Popen(
        [sys.executable, 'do_something.py', arg1, arg2 ...], 
        stdout=subprocess.PIPE
)

其中 'arg1, arg2, ...' 表示您可能需要传递给子进程的参数。如果您需要读取 C++ 模块的输出,您可以在 do_something.py 中打印它并在您的应用程序中使用:

p.stdout.read()

我承认这不是一个特别顺利的解决方案,但我认为它应该可以工作。

于 2013-05-07T21:05:06.723 回答