概述Python Web服务器网关接口有三种标准分别针对异步、实时同步和传统同步Web应用场景设计即ASGI、RSGI、WSGI。标准全称中文含义发布时间WSGIWeb Server Gateway InterfaceWeb服务器网关接口2003年ASGIAsynchronous Server Gateway Interface异步服务器网关接口2016年RSGIReal-time Server Gateway Interface实时服务器网关接口2023年WSGI示例代码defapplication(environ,start_response):status200 OKheaders[(Content-Type,text/plain)]start_response(status,headers)return[bHello World]特点同步阻塞一个请求处理完才能处理下一个单线程模型不适合高并发简单稳定成熟稳定生态完善Web框架举例Django、Flask、Pyramid、Bottle优势成熟稳定近20年发展bug极少生态丰富几乎所有Python Web框架支持简单易学同步编程模型直观部署简单Gunicorn、uWSGI等成熟方案劣势性能瓶颈同步阻塞高并发需多进程协议落后不支持WebSocket、HTTP/2资源消耗每个请求一个进程/线程实时性差不适合实时应用工作原理核心思想是将Web应用程序与Web服务器解耦规定应用程序需要实现的接口以便能够与任何兼容WSGI的Web服务器通信。使得开发者可专注于应用程序的逻辑而无需关心与特定Web服务器的交互。两个主要组件应用程序ApplicationWSGI应用程序是一个可调用对象通常是一个函数或一个类的实例。接受两个参数environ和start_response并返回一个迭代器用于生成HTTP响应。服务器网关Server Gateway服务器网关是一个中间件组件负责处理HTTP请求并将请求传递给WSGI应用程序。服务器网关还负责调用应用程序生成的响应并将响应返回给客户端。中间件WSGI中间件一种用于在WSGI应用程序和Web服务器之间执行预/后处理操作的机制可用于添加额外的功能如请求/响应处理、身份验证、缓存等是构建复杂Web应用程序的重要组成部分。作用包括请求处理可在请求到达应用程序之前执行一些处理逻辑如身份验证、请求重定向等。响应处理可在应用程序生成响应后对响应进行处理如添加HTTP头、压缩响应内容等。异常处理可捕获应用程序抛出的异常并根据需要执行特定的操作如记录错误日志、返回自定义错误页面等。uWSGI一个应用服务器实现WSGI协议并提供高性能的Web应用程序托管环境。支持多种协议包括HTTP、FastCGI、SCGI等使得Python应用程序可与不同类型的Web服务器通信。相比开发环境中的简易服务器如Django的runserver或Flask的Werkzeug在生产环境中具备更强的并发处理能力和更多高级特性如负载均衡、缓存。实战安装pip install uwsgi指定脚本启动uwsgi --http :9090 --wsgi-file myapp.py --master --processes 4 --threads 2生成4个进程每个进程有2个线程。适合开发阶段。生产环境一般需要创建uWSGI配置文件myapp_uwsgi.ini指定WSGI应用程序[uwsgi] ; 虚拟环境绝对路径Docker部署时不需要 home/opt/python_venv/test_project ; 项目的绝对路径 chdir /opt/project/test_project ; 项目名 projectflask_demo ; 启动路由指定启动协议当和nginx结合进行反向代理就用unix-socket协议无法直接访问只能通过nginx进行反代 socket0.0.0.0:8000 ; 项目启动入口文件默认入口函数是application wsgi-filemain.py ; 入口文件中的函数如flask文件中的app callableapp ; 启用process manager管理worker进程worker进程都是master进程的子进程 masterTrue ; 指定开启的工作进程数量一般指定为cpu的核数即可(填cpu的4倍数量) processes1 ; 设置每个工作进程的线程数 threads2 ; 设置用于uwsgi包解析的内部缓存区大小为64k默认是4k buffer-size 32768 ; 使进程在后台运行并将日志打到指定的日志文件或者udp服务器 daemonize /var/log/test_project/uwsgi.log ; 设置最大日志文件大小 ; log-maxsize 5000000 ; 指定pid文件的位置记录主进程的pid号 pidfileuwsgi.pid ; 当服务器退出的时候自动删除unix socket文件和pid文件 vacuum true ; 格式化日志打印 logformat-strftimetrue log-date%%Y-%%m-%%d %%H:%%M:%%S log-format[%(ftime)] pid: %(pid) %(addr) host: %(host)%(uri)(%(method)) in %(secs)s %(status) total-size: %(size) bytes备注CSDN编辑器太垃圾不支持ini脚本语言;表示注释。启动uWSGI服务器并托管Python应用uwsgi --ini myapp_uwsgi.ini。其他命令# 重启uWSGI服务器$ uwsgi--reloaduwsgi.pid# 查看所有uWSGI进程$psaux|grepuwsgi# 停止uWSGI服务器$ uwsgi--stopuwsgi.pid# 启动时会生成uwsgi.pid文件uwsgi一个通信协议定义应用服务器和Web服务器之间的通信方式。uWSGI是uwsgi的一种实现。ASGI示例代码asyncdefapplication(scope,receive,send):awaitsend({type:http.response.start,status:200,headers:[[bcontent-type,btext/plain]]body:bHello World})特点异步非阻塞一个请求等待时处理其他请求支持WebSocket原生支持实时通信高性能适合高并发场景Web框架举例FastAPI、Starlette、Django Channels、BlackSheep优势高性能单进程处理数千并发现代协议原生支持WebSocket、HTTP/2资源高效低内存占用高CPU利用率实时性强适合实时通信应用劣势学习曲线需要理解异步编程概念调试困难异步代码调试更复杂生态迁移部分WSGI库需重写阻塞风险同步代码可能阻塞事件循环RSGI示例代码defapplication(scope,receive,send):# 同步接口但支持流式响应send({type:http.response.start,status:200,headers:[[bcontent-type,btext/plain]]})# 支持分块传输send({type:http.response.body,body:bHello ,more_body:True})send({type:http.response.body,body:bWorld})特点同步但支持流式保持同步编程模型实时响应支持服务器推送兼容WSGI迁移成本低诞生于2023年背景部分开发者不适应异步编程模型问题ASGI学习曲线陡峭WSGI功能有限解决方案RSGI保持同步模型但支持现代特性定位WSGI和ASGI之间的折中方案优势平衡折中同步编程现代特性迁移简单WSGI应用易迁移实时支持支持流式响应学习友好无需掌握异步编程劣势新生标准生态不成熟性能折中不如ASGI高性能定位模糊可能被ASGI和WSGI挤压社区认可需要时间验证对比核心差异矩阵维度WSGIASGIRSGI编程模型同步阻塞异步非阻塞同步流式并发能力低依赖多进程高单线程异步中多线程/进程实时支持不支持原生支持支持流式学习曲线简单较陡需理解async/await中等生态成熟度⭐⭐⭐⭐⭐⭐⭐⭐⭐⭐⭐性能表现⭐⭐⭐⭐⭐⭐⭐⭐⭐⭐内存占用高多进程低单进程中适用场景传统Web应用高并发实时应用实时同步应用协议支持对比协议WSGIASGIRSGIHTTP/1.1✅✅✅HTTP/2❌✅✅WebSocket❌✅✅受限Server-SentEvents❌✅✅长轮询有限✅✅分块传输❌✅✅性能基准测试估算​场景WSGIASGIRSGI1000并发请求500-800ms50-100ms200-300msWebSocket连接不支持10000连接5000连接内存占用100并发500MB100MB-300MBCPU利用率高上下文切换高事件循环中Gunicorn官网Green Unicorn缩写开源GitHub10.5K Star1.8K Fork高性能的 Python WSGI UNIX HTTP服务器移植自Ruby的独角兽Unicorn项目。特性原生支持WSGI、Django和Paster自动工作进程管理简单的Python配置多Worker配置多种可扩展性服务器挂钩兼容Python 3.5Gunicorn从5个地方依次读取配置环境变量框架配置gunicorn.conf.py配置文件环境变量中的GUNICORN_CMD_ARGS命令行常见配置项--config配置文件--reload代码更改时重新启动--access-logfile要写入的访问日志文件--error-logfile要写入的错误日志文件--log-level错误输出级别--certfileSSL证书文件--bind绑定socket--workers处理请求的工作进程数--threads用于处理请求的工作线程数服务器钩子on_starting在主进程初始化之前调用on_reload重新加载期间调用when_ready在服务器启动后立即调用pre_fork在fork之前调用post_fork在fork之后调用post_worker_init在work初始化之后调用worker_int在worker退出SIGINT或SIGQUIT后立即调用worker_abort在worker收到SIGABRT信号时调用pre_exec新的主进程之前调用pre_request处理请求之前调用post_request处理请求后调用child_exit在主进程中退出工作程序后立即调用worker_exitworker退出后调用nworkers_changed在num_workers更改后立即调用on_exit在退出Gunicorn之前调用实战安装基于pippip install gunicorn基于源码pip install githttps://github.com/benoitc/gunicorn.git若需要使用异步workers还需要安装pipinstallgreenlet# Required for bothpipinstalleventlet# For eventlet workerspipinstallgunicorn[eventlet]# Or, using extrapipinstallgevent# For gevent workerspipinstallgunicorn[gevent]# Or, using extra命令行示例gunicorn--workers2test:app# 工厂模式指定方法gunicorn--workers2test:create_app()Uvicorn官网开源GitHub10.6K Star932 Fork基于asyncio、高性能ASGI服务器用于构建异步Web服务支持HTTP和WebSocket协议。应用场景异步API服务处理大量并发请求提高系统的性能和吞吐量Websocket服务可用于构建实时通信的Web应用程序实战提供多种安装方式pippip install uvicornuvuv install uvicorn命令行uvicorn main:app--reloaduvicorn main:app --ssl-keyfile key.pem --ssl-certfile cert.pem解读支持通过SSL加密来提供安全的通信。可使用--ssl-keyfile和--ssl-certfile参数来指定SSL密钥文件和证书文件常用配置选项--host指定主机地址默认为127.0.0.1--port指定端口号默认为8000--workers指定工作进程数量默认为CPU核心数的1倍--log-level指定日志级别默认为info--reload在代码修改时自动重新加载应用程序支持处理WebSocket连接用于实时通信应用程序# websocket_app.pyfromfastapiimportFastAPI,WebSocket appFastAPI()app.websocket(/ws)asyncdefwebsocket_endpoint(websocket:WebSocket):awaitwebsocket.accept()whileTrue:dataawaitwebsocket.receive_text()awaitwebsocket.send_text(fMessage text was:{data})支持使用中间件来修改请求和响应以及执行其他自定义操作。可通过--middleware参数来指定中间件。# middleware.pyfromuvicorn.middleware.proxy_headersimportProxyHeadersMiddlewarefromuvicorn.middleware.debugimportDebugMiddlewarefromfastapiimportFastAPI appFastAPI()app.add_middleware(ProxyHeadersMiddleware,trusted_hosts[10.0.0.1])app.add_middleware(DebugMiddleware)app.get(/)asyncdefread_root():return{message:Hello, World!}支持在异步Web服务中执行异步任务不会阻塞主事件循环# async_task.pyfromfastapiimportFastAPIimportasyncio appFastAPI()asyncdefbackground_task():whileTrue:print(Background task is running...)awaitasyncio.sleep(5)app.on_event(startup)asyncdefstartup_event():asyncio.create_task(background_task())app.get(/)asyncdefread_root():return{message:Hello, World!}可通过自定义异常处理器来处理异常情况如未找到页面、服务器错误等。# error_handling.pyfromfastapiimportFastAPI,HTTPException appFastAPI()app.get(/items/{item_id})asyncdefread_item(item_id:int):ifitem_id42:raiseHTTPException(status_code404,detailItem not found)return{item_id:item_id}