请教一下 Gunicorn 的一些疑惑 - V2EX
V2EX = way to explore
V2EX 是一个关于分享和探索的地方
现在注册
已注册用户请  登录
推荐学习书目
Learn Python the Hard Way
Python Sites
PyPI - Python Package Index
http://diveintopython.org/toc/index.html
Pocoo
值得关注的项目
PyPy
Celery
Jinja2
Read the Docs
gevent
pyenv
virtualenv
Stackless Python
Beautiful Soup
结巴中文分词
Green Unicorn
Sentry
Shovel
Pyflakes
pytest
Python 编程
pep8 Checker
Styles
PEP 8
Google Python Style Guide
Code Style from The Hitchhiker's Guide
TcDhl
0.04D
V2EX    Python

请教一下 Gunicorn 的一些疑惑

  •  
  •   TcDhl 2022-06-02 16:48:27 +08:00 3361 次点击
    这是一个创建于 1302 天前的主题,其中的信息可能已经有所发展或是发生改变。
    如果 Flask + Gunicorn 长时间运行, gunicorn 的进程不释放,服务器内存就会一直增长, 会造成内存泄漏

    然后 gunicorn 有两个参数"--max-requestsINT"和"--max-requests-jitter INT", 这两个参数可以定期自动清理"gunicorn 的每个 worker"的进程, 避免服务器 GG

    但我有一些疑惑:
    1.如果在自动清理的过程中, 有新的请求动作 进行数据库的增删改查, 这个新的请求动作会不会被清理掉
    2.如果在自动清理的过程中, 已有的进程内正在进行数据库的增删改查, 这个已有的进程不知道会不会被清理
    如果 1. 2. 不会被清理掉, 那这套部署方式应该还比较完美
    有木有大佬知道我疑惑的这两点应该要担心么

    最终线上部署应该是可以弄成 Nginx + Gunicorn + Gevent + Flask 实现高并发
    第 1 条附言    2022-06-02 20:46:03 +08:00
    #1 和#3 的老哥完美解答 !
    有需要可以去参考
    8 条回复    2022-06-06 10:34:02 +08:00
    fgwmlhdkkkw
        2
    fgwmlhdkkkw  
       2022-06-02 17:53:27 +08:00
    这编译器铁定有问题,Microsoft 不过如此……()
    victorc
        3
    victorc  
       2022-06-02 18:02:22 +08:00   1
    这种细节问题,直接去翻代码啊,这是提升技术水平的好办法

    就你问题本身,workder 的 max request 到达上限之后,会把当前请求处理完,不接受新连接进来

    "Autorestarting worker after current request."
    TcDhl
        4
    TcDhl  
    OP
       2022-06-02 20:21:21 +08:00
    TcDhl
        5
    TcDhl  
    OP
       2022-06-02 20:21:38 +08:00
    @julyclyde #1
    @victorc #3
    谢谢两位哥
    Kobayashi
        6
    Kobayashi  
       2022-06-02 21:36:32 +08:00 via Android   3
    Gunicorn 采用 arbiter/manager + worker 管理进程。

    arbiter 作为管理者,不断循环,在每轮循环检测 worker 状态,比如杀死超时 worker ,创建新 worker 。
    而 worker 负责处理请求,多个 worker 监听在同一个 socket 上接受新请求。worker 模式多样,最简单的就是进程模式和线程模式。

    max request 被设计用来限制一个 worker 所能处理的做法请求数量。其初衷是担心代码中内存泄漏,worker 运行一段时间后能被杀死,回收掉内存。

    worker 里边也是循环处理新请求。在每次处理请求前,worker touch 一个 WorkerTmp 对象(好像是一个文件来着),更新其时间戳。而 arbiter 每轮循环检测到 worker.tmp ,就明白 worker 空闲有一定时间了,会干掉它。Arbiter.run() 是循环代码,Arbiter.murder_worker() 尝试清理 worker 。

    Arbiter 管理 worker 方式基于信号。Arbiter 和 Worker 实例化时都会初始化自己的信号管理函数。总之 arbiter 发送 abrt 或者 kill 信号给 worker ,空转 worker 接受到信号后自杀。( worker 空转是因为其达到最大请求数后不再处理新请求)根据 base worker 中 abrt 信号处理函数,worker 执行了 sys.exit(1) 直接退出。

    max requests jitter 是在最大请求数目上加点抖动值,避免所有 worker 同一时间停止接受新请求,服务摊了。不过我觉得请求耗时不大可能完全一样,加不加差不大多。

    Gunicorn vs Uvicorn vs Supervisor

    Gunicorn 很独特的一点是,它既是一个 wsgi 服务器(对标 Uvicorn ),也是一个进程管理器(对标 supervisor )。所以你看到过 Gunicorn+ Uvicorn 部署 asgi 应用,Uvicorn 作为一个 gunicorn 运行。和 supervisor 相比,Gunicorn 进程管理方式相对较弱,完全基于信号,好像 supervisor 基于 RPC 调用啥的,交互式 shell 管理进程、web page 管理进程一应全。

    主要相关代码参考 arbiter.py 和 workers/base.py
    TcDhl
        7
    TcDhl  
    OP
       2022-06-02 22:52:10 +08:00
    @Kobayashi #6

    谢谢老哥
    julyclyde
        8
    julyclyde  
       2022-06-06 10:34:02 +08:00
    但是我在 sync worker base 里边没有看到这个功能。没明白咋回事
    关于     帮助文档     自助推广系统     博客     API     FAQ     Solana     955 人在线   最高记录 6679       Select Language
    创意工作者们的社区
    World is powered by solitude
    VERSION: 3.9.8.5 39ms UTC 19:22 PVG 03:22 LAX 11:22 JFK 14:22
    Do have faith in what you're doing.
    ubao msn snddm index pchome yahoo rakuten mypaper meadowduck bidyahoo youbao zxmzxm asda bnvcg cvbfg dfscv mmhjk xxddc yybgb zznbn ccubao uaitu acv GXCV ET GDG YH FG BCVB FJFH CBRE CBC GDG ET54 WRWR RWER WREW WRWER RWER SDG EW SF DSFSF fbbs ubao fhd dfg ewr dg df ewwr ewwr et ruyut utut dfg fgd gdfgt etg dfgt dfgd ert4 gd fgg wr 235 wer3 we vsdf sdf gdf ert xcv sdf rwer hfd dfg cvb rwf afb dfh jgh bmn lgh rty gfds cxv xcv xcs vdas fdf fgd cv sdf tert sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf shasha9178 shasha9178 shasha9178 shasha9178 shasha9178 liflif2 liflif2 liflif2 liflif2 liflif2 liblib3 liblib3 liblib3 liblib3 liblib3 zhazha444 zhazha444 zhazha444 zhazha444 zhazha444 dende5 dende denden denden2 denden21 fenfen9 fenf619 fen619 fenfe9 fe619 sdf sdf sdf sdf sdf zhazh90 zhazh0 zhaa50 zha90 zh590 zho zhoz zhozh zhozho zhozho2 lislis lls95 lili95 lils5 liss9 sdf0ty987 sdft876 sdft9876 sdf09876 sd0t9876 sdf0ty98 sdf0976 sdf0ty986 sdf0ty96 sdf0t76 sdf0876 df0ty98 sf0t876 sd0ty76 sdy76 sdf76 sdf0t76 sdf0ty9 sdf0ty98 sdf0ty987 sdf0ty98 sdf6676 sdf876 sd876 sd876 sdf6 sdf6 sdf9876 sdf0t sdf06 sdf0ty9776 sdf0ty9776 sdf0ty76 sdf8876 sdf0t sd6 sdf06 s688876 sd688 sdf86