python tornado开启多进程的几种方法
作者:终成一个大象 发布时间:2021-09-18 22:28:17
以下各种方式仅供参考,本人亲测只有官方提供的方式比较靠谱。
1. 使用多个进程启动多个Tornado实例
import tornado.httpserver
import tornado.ioloop
import tornado.web
class MainHandler(tornado.web.RequestHandler):
def get(self):
self.write("Hello, world")
if __name__ == "__main__":
app = tornado.web.Application([(r"/", MainHandler)])
server = tornado.httpserver.HTTPServer(app)
server.bind(8888)
server.start(0) # 0 表示启动与CPU数量相同的进程
tornado.ioloop.IOLoop.current().start()
2. 使用tornado.process.fork_processes()方法启动多个进程
import tornado.httpserver
import tornado.ioloop
import tornado.web
import tornado.process
class MainHandler(tornado.web.RequestHandler):
def get(self):
self.write("Hello, world")
if __name__ == "__main__":
app = tornado.web.Application([(r"/", MainHandler)])
server = tornado.httpserver.HTTPServer(app)
server.bind(8888)
tornado.process.fork_processes(2) #
tornado.process.fork_processes(2) 表示启动2个进程,每个进程都会调用 server.start(0) 来启动Tornado实例。注意:在使用 tornado.process.fork_processes() 启动多进程时,需要在 if __name__ == "__main__": 中调用该方法,否则会出现错误。
完整代码如下:
import tornado.httpserver
import tornado.ioloop
import tornado.web
import tornado.process
class MainHandler(tornado.web.RequestHandler):
def get(self):
self.write("Hello, world")
if __name__ == "__main__":
app = tornado.web.Application([(r"/", MainHandler)])
server = tornado.httpserver.HTTPServer(app)
server.bind(8888)
tornado.process.fork_processes(2)
server.start(0)
tornado.ioloop.IOLoop.current().start()
3.使用标准库中的multiprocessing
除了以上提到的方式,还可以使用Python标准库中的multiprocessing模块来启动多个Tornado进程,具体实现可以参考以下示例代码:
import tornado.httpserver
import tornado.ioloop
import tornado.web
from multiprocessing import Process
class MainHandler(tornado.web.RequestHandler):
def get(self):
self.write("Hello, world")
def start_tornado():
app = tornado.web.Application([(r"/", MainHandler)])
server = tornado.httpserver.HTTPServer(app)
server.listen(8888)
tornado.ioloop.IOLoop.current().start()
if __name__ == "__main__":
processes = []
for i in range(2):
p = Process(target=start_tornado)
p.start()
processes.append(p)
for p in processes:
p.join()
这段代码会启动两个Tornado进程,每个进程都会监听8888端口,并使用单独的进程处理请求。
4.使用第三方模块gevent
还有一个方式是使用第三方模块gevent来实现协程并发,配合Tornado使用可以达到类似多进程的效果,但是只使用一个进程。示例代码如下:
import gevent.monkey
gevent.monkey.patch_all()
import tornado.httpserver
import tornado.ioloop
import tornado.web
class MainHandler(tornado.web.RequestHandler):
def get(self):
self.write("Hello, world")
if __name__ == "__main__":
app = tornado.web.Application([(r"/", MainHandler)])
server = tornado.httpserver.HTTPServer(app)
server.bind(8888)
server.start(0) # 0 表示启动与CPU数量相同的进程
tornado.ioloop.IOLoop.current().start()
在上面的代码中,我们引入了gevent.monkey模块,使用patch_all()方法将所有的阻塞式IO替换为非阻塞式IO,然后在启动Tornado时,使用server.start(0)方法启动与CPU数量
5.使用官方提供方式
listen:单进程:
async def main():
server = HTTPServer()
server.listen(8888)
await asyncio.Event.wait()
asyncio.run(main())
在许多情况下,tornado.web.Application.listen可用于避免明确创建HTTPServer的需要。
虽然此示例不会单独创建多个进程,但当thereusereuse_port=True参数传递给listen()时,您可以多次运行程序以创建多进程服务。
add_sockets:多过程:
sockets = bind_sockets(8888)
tornado.process.fork_processes(0)
async def post_fork_main():
server = HTTPServer()
server.add_sockets(sockets)
await asyncio.Event().wait()
asyncio.run(post_fork_main())
add_sockets接口更复杂,但它可以与tornado.process.fork_processes一起使用,以运行从单父分支的所有工作进程的多进程服务。如果您想以bind_sockets以外的某种方式创建监听套接字,add_sockets也可以在单进程服务器中使用。
请注意,使用此模式时,触及事件循环的任何东西都不能在fork_processes之前运行。
bind/start:简单不建议使用的多进程:
server = HTTPServer()
server.bind(8888)
server.start(0) # Forks multiple sub-processes
IOLoop.current().start()
此模式被弃用,因为它需要自Python 3.10以来被弃用的asyncio模块中的接口。在start方法中创建多个进程的支持将在的未来版本中删除。
此模式就是文中所说的第一种模式,单从官方文档来看,这种方式已经被抛弃,本人在实测中也发现存在问题:无法完全关闭fork的子进程。
6.使用supervisor
使用supervisor等进程管理工具来管理多个Tornado进程,这种方式可以更加方便地监控和管理多个进程,不过需要额外的配置和安装进程管理工具。
来源:https://blog.csdn.net/Martin_chen2/article/details/130095961


猜你喜欢
- select * from (select t.*, row_number() over(order by 列 desc) r from 表
- Python 作为当前最热门的编程语言之一,不仅仅是因为它的学习成本低、入门容易,还因为它具有丰富的生态环境,包括内置的模块以及第三方的库,
- 本文实例讲述了python获取文件版本信息、公司名和产品名的方法,分享给大家供大家参考。具体如下:该python代码可得到文件版本信息、公司
- 一、前言 JDK(Java Development Kit )是一切java应用程序的基础,可以说,所有的java应用程序是构建
- 在使用Django自带的admin后台的时候,他提供了一些默认的指令可以对数据进行操作, 比如批量删除,修改等 同样的我们也可以添加自己的指
- 前言ThinkPHP,是为了简化企业级应用开发和敏捷WEB应用开发而诞生的开源轻量级PHP框架。随着框架代码量的增加,一些潜在的威胁也逐渐暴
- 目的:在百度贴吧输入关键字和要查找的起始结束页,获取帖子里面楼主所发的图片思路:获取分页里面的帖子链接列表获取帖子里面楼主所发的图片链接列表
- 本文实例为大家分享了opencv+python实现图像矫正的具体代码,供大家参考,具体内容如下需求:将斜着拍摄的文本图像进行矫正python
- 本文实例讲述了python实现的config文件读写功能。分享给大家供大家参考,具体如下:1、设置配置文件[mysql]host = 123
- 一、需求分析我们首先有一个成绩表单,但是学生的成绩是按照学号进行排序的,现在,我们希望清晰明了的知道每一个学生的名次,并且需要将学生按照成绩
- 前言本文实现一个 Python 脚本,用来批量卸载模拟器或者实体机上面的 App 以及清除 LogCat 缓存。开发 Android 的朋友
- 平常的开发过程中不免遇到需要把model转成字典的需求,尤其是现在流行前后端分离架构,Json格式几乎成了前后端之间数据交换的标准,这种mo
- 首先,运行 Python 解释器,导入 re 模块并编译一个 RE:#!python Python 2.2.2 (#1, Feb 10 20
- vue-loader和webpack项目配置及npm错误学习vue的同学都知道,想要生成一个vue项目,使用vue-cli脚手架工具直接生成
- asp如何获知页面上的图象的实际尺寸大小?见下面的两个asp文件:<!--#include virtual="/i
- 环境python3.6合并前第一个文件和第二个文件代码file1 = open("my.txt","r&quo
- 出现invalid syntax报错的几种原因这篇文章旨为刚接触python不久的朋友,提供一点帮助,请在检查代码没有主要问题时再看是否存在
- 代码如下:declare @Q_ID uniqueidentifier set @Q_ID = dbo.uf_GetParamValueBy
- 1.data参数data是可选的,需要使用bytes()方法将参数转化为字节编码格式的内容。如果传递了这个参数,请求方式就不是GET方式,而
- 前言本文提供获取视频时长的python代码,精确到毫秒,一如既往的实用主义。环境依赖 ffmpeg环境安装,可以参考:window