我正在使用 uvicorn 和 python 的 subprocess.Popen 运行多个 FastAPI 实例。我有一个用 PySimpleGUI 制作的小型 GUI,我希望能够随意关闭服务器并重新启动它们。
我遇到的第一个问题是,至少在 Windows 中,启动 uvicorn 服务器似乎创建的不是一个,而是两个新进程,并调用Popen.terminate()
仅关闭这些进程之一,这不会释放与服务器关联的端口。我使用 psutil 包修复了这个问题,以检查实例化 Popen 对象后创建了哪些新进程,并使用 psutil 跟踪和终止第二个进程。
还有一个主要问题是调用psutil.terminate()
就进程不调用FastAPI函数而言@app.on_event("shutdown")
。过去,我们在单独的终端窗口中运行所有服务器,并发现这些终端窗口上的 ctrl-c 将调用关闭事件,但我没有找到其他方法来执行此操作。我界面上的 ctrl-c 显然会关闭界面和所有服务器,并且在命中所有服务器的关闭事件方面有些不可靠。我的另一个想法是使用psutil.send_signal(signal.CTRL_C_EVENT)
,但这与在终端中调用 ctrl-c 具有相同的效果。
所以我很茫然。我看到很多帖子说这是 uvicorn 的普遍缺点,但没有看到任何直接证实我自己的经验或提供解决方案的内容。我还知道 FastAPI 中的“关闭”和“启动”事件是从 Starlette 移植的,并且在这两个包中都没有很好的记录。我看到过使用 guvicorn 的建议,但我的简短调查证实它与 Windows 不兼容。有什么建议么?
TL;DR:
- API 是长期运行的进程
- 整个行业都围绕虚拟化来自动管理何时启动或停止服务的编排
- 还有“无服务器”基础设施,您可以挂起任何流程,而无需在该领域花费任何精力,因为它本来就不是一件事
- 如果您仍然想与其他人对抗并自己管理,您可以这样做这个回答了问题 https://stackoverflow.com/questions/68603658/how-to-terminate-a-uvicorn-fastapi-application-cleanly-with-workers-2-when
##### SOLUTION #####
pid = proc.pid
parent = psutil.Process(pid)
for child in parent.children(recursive=True):
child.kill()
##### SOLUTION END ####
一点解释:
从 Rest API 作为一种架构模式的概念来看,它意味着始终等待来自网络的用户请求。优雅地管理和开发产品来优雅地处理“本来应该永远运行”的事物的关闭从来都不是普遍的意图,我们构建流程来努力保持其作为一个行业 24/7/365 的运行。
如果您想利用在同一设备上同时启动或停止一对多 API 的能力,强烈建议您至少使用容器和 Kubernetes 之类的东西,并且只需针对 Kubernetes CLI 编写命令脚本即可实现此目的。作为额外努力的交换,您将获得与其他人和基础操作系统层的进程隔离(这仍然比您自己构建所有工具要省力。
我个人最喜欢的就是不这样做,而是直接使用 lambda,因为在很多方面都更容易、更好。不要从我的口中得知,而是从行业领先的公司之一 Cloudflare 和他们关于该主题的陈述 https://www.cloudflare.com/learning/serverless/why-use-serverless/
与传统的基于云或以服务器为中心的基础设施相比,无服务器计算具有许多优势。对于许多开发人员来说,无服务器架构提供了更大的可扩展性、更大的灵活性和更快的发布时间,而且成本更低。
本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)