首页   注册   登录
 ytymf 最近的时间轴更新

ytymf

V2EX 第 285474 号会员,加入于 2018-01-22 19:07:59 +08:00
今日活跃度排名 6403
ytymf 最近回复了
@gmywq0392 大部分的基础数据类型,比如 list,dict 都可以 pickle,类似于 socket,DB connection 不可以
@fub2020 这个怎么说? Django 自带 JsonResponse 可以很方便搭建接口啊。
@lolizeppelin “搞清楚了原理,自然知道如何避免 celery 有可能带来的负面影响”, 这一点具体要怎么做呢,读 celery 的源代码么
@lolizeppelin 现实中是麻烦的,如果父进程不是 fork safe 的,就是很难处理,不是任何父进程都可以很安全地被 fork 的(与 python 无关),参考
https://stackoverflow.com/questions/6078712/is-it-safe-to-fork-from-within-a-thread

不知道是不是这个原因,python3.8 中 macos 下的 multiprocessing 的默认启动方式也被改成了 spwan,之前是 fork。
@lolizeppelin 楼主给的题目是有限定的,是个命题作文,那就是如何在 celery worker 下启动子进程,这个问题要怎么解决?即使通晓了你给的所有知识,遇到这个具体的问题不还是得看 celery 具体的实现,找出冲突的共享资源?如果父进程是楼主自己写的,我一定会推荐他搞明白。可面对的是一个庞杂的第三方库,又是具体的命题作文,那要怎么回答呢?
@hanssx billiard 我没用过,可能跟原生的 multiprocessing 有区别了,最终可以尝试下 forkserver。其实楼上说的有道理,你的用法有点点奇特了,即使用 spwan 或者 forkserver 能够启动,也不是最优雅的办法,还是重构成正经的方法比较好
@lolizeppelin 只是给楼主一个快速尝试看能不能解决问题的方法,确实是不推荐直接 spawn 的。你说的没错,是要看好基础,可是也得解决具体的问题才行。
@hanssx 很难说 celery worker 本身的实现里面没有线程,而且大概率是有线程的。你可以简单试试改下进程启动方法为 spawn,如果问题解决那就是这个问题。
@hanssx 看 fork 的介绍,Note that safely forking a multithreaded process is problematic. 我的经验是,后果就是 fork 出的子进程会成为僵尸进程
@hanssx 不,就是确保父进程是单线程的,也就是说你要 fork 的那个进程里不能有多个线程。可以了解一下 fork safe 这个概念,fork 出来的子进程并不会继承父进程的所有线程,会造成一些问题。
为了解决这个问题,multiprocessing 给出了 spwan 跟 forkserver 两个启动子进程的方式,这里摘抄一点官方文档:

Depending on the platform, multiprocessing supports three ways to start a process. These start methods are

spawn
The parent process starts a fresh python interpreter process. The child process will only inherit those resources necessary to run the process objects run() method. In particular, unnecessary file descriptors and handles from the parent process will not be inherited. Starting a process using this method is rather slow compared to using fork or forkserver.

Available on Unix and Windows. The default on Windows and macOS.

fork
The parent process uses os.fork() to fork the Python interpreter. The child process, when it begins, is effectively identical to the parent process. All resources of the parent are inherited by the child process. Note that safely forking a multithreaded process is problematic.

Available on Unix only. The default on Unix.

forkserver
When the program starts and selects the forkserver start method, a server process is started. From then on, whenever a new process is needed, the parent process connects to the server and requests that it fork a new process. The fork server process is single threaded so it is safe for it to use os.fork(). No unnecessary resources are inherited.
关于   ·   FAQ   ·   API   ·   我们的愿景   ·   广告投放   ·   感谢   ·   实用小工具   ·   4283 人在线   最高记录 5043   ·     Select Language
创意工作者们的社区
World is powered by solitude
VERSION: 3.9.8.3 · 13ms · UTC 02:48 · PVG 10:48 · LAX 18:48 · JFK 21:48
♥ Do have faith in what you're doing.