当前位置: 首页 > news >正文

python WSGI和ASGI的区别

用户到我们web应用中间经过的相关协议,具体介绍和pyhton相关的WSGI和ASGI,我先把结论列出来,详细描述请看下面介绍!

请大家先记住这张图,带着问题和整个框架去看比较易于了解

CGI,WSGI,ASGI、框架以及Web服务器的关系:比如flask,这是一个同步框架,同时也是一个Web应用,一个请求需要经过Web服务器和WSGI服务器才能和框架“交流”数据。下面请看一张图来澄清整个链路

对这张图有一段话解释这里借鉴一下,参考[1]

 

首先nginx 是对外的服务接口,外部浏览器通过url访问nginx,

nginx 接收到浏览器发送过来的http请求,将包进行解析,分析url,如果是静态文件请求就直接访问用户给nginx配置的静态文件目录,直接返回用户请求的静态文件, 如果不是静态文件,而是一个动态的请求,那么nginx就将请求转发给uwsgi,uwsgi 接收到请求之后将包进行处理,处理成wsgi可以接受的格式,并发给wsgi,wsgi 根据请求调用应用程序的某个文件,某个文件的某个函数,最后处理完将返回值再次交给wsgi,wsgi将返回值进行打包,打包成uwsgi能够接收的格式,uwsgi接收wsgi 发送的请求,并转发给nginx,nginx最终将返回值返回给浏览器。

要知道第一级的nginx并不是必须的,uwsgi完全可以完成整个的和浏览器交互的流程,但是要考虑到某些情况

​ a. 安全问题,程序不能直接被浏览器访问到,而是通过nginx,nginx只开放某个接口,uwsgi本身是内网接口,这样运维人员在nginx上加上安全性的限制,可以达到保护程序的作用。

​ b. 负载均衡问题,一个uwsgi很可能不够用,即使开了多个work也是不行,毕竟一台机器的cpu和内存都是有限的,有了nginx做代理,一个nginx可以代理多台uwsgi完成uwsgi的负载均衡。

​ c. 静态文件问题,用django或是uwsgi这种东西来负责静态文件的处理是很浪费的行为,而且他们本身对文件的处理也不如nginx好,所以整个静态文件的处理都直接由nginx完成,静态文件的访问完全不去经过uwsgi以及其后面的东西。

通用型网关接口:CGI、FastCGI

网关接口是一种协议,为了实现加载动态脚本。CGI程序则是实现了CGI协议的一种程序

Web服务器网关接口协议:WSGI、ASGI、uwsgi

网关接口是用于Web应用与Web服务器进行通讯。其中WSGI、ASGI是专为python设计的网关接口。uwsgi是uWSGI服务器自有的传输协议

实现了Web服务器网关接口的软件有:uWSGI(注意大小写)、uvicorn、gunicorn

同步异步:同步是指执行是串行的,需要处理完当前任务在处理一下;异步指并行的,现有的任务不影响下一个任务的执行。类比到请求上面就是假如同时有两个请求进来,在同步处理的框架下第二个请求需要等第一个结束之后才能响应,而异步就可以并行处理

Web框架:

诸如Flask、Django这类pyhton Web框架,可以被启动当成服务器的原因,都是因为其自带启动了WSGI服务器,才允许Web服务器与Web框架之间进行连接。(效率极其低下,一般生产可以使用gunicorn、gevent等WSGI服务器)

这里请参考flask启动的案例,Flask.run()

def run(self, host=None, port=None, debug=None, load_dotenv=True, **options):
    """Runs the application on a local development server.

    Do not use ``run()`` in a production setting. It is not intended to
    meet security and performance requirements for a production server.
    Instead, see :ref:`deployment` for WSGI server recommendations.
    ****"""
    *     # 省略了部分代码
    *     # 省略了部分代码
    *     # 省略了部分代码
    from werkzeug.serving import run_simple

    try:
        run_simple(host, port, self, **options)
    *     # 省略了部分代码
    *     # 省略了部分代码
    *     # 省略了部分代码
    
这里注意到run_simple,我们继续跟踪进去看其代码,如下:

def run_simple(
    hostname,
    port,
    application,
    use_reloader=False,
    use_debugger=False,
    use_evalex=True,
    extra_files=None,
    reloader_interval=1,
    reloader_type="auto",
    threaded=False,
    processes=1,
    request_handler=None,
    static_files=None,
    passthrough_errors=False,
    ssl_context=None,
):
    """Start a WSGI application. Optional features include a reloader,
    multithreading and fork support."""

可以看到这里就是做启动WSGI服务的简单准备工作,具体代码就不分析,感兴趣的小伙伴可以去跟踪看下生成的过程

而FastAPI这类高性能、纯Web框架,是没有带WSGI或者ASGI协议的服务器启动功能的,所以我们在启动的时候需要用uvicorn等命令

总结:框架是为了让我们专注于逻辑代码和业务的实现,我们可以无需将时间和精力花在数据如何传输,如何编码,请求和响应是如何执行的。不过这中间可能会涉及到服务器之间的层层关系,所以我们有必要了解一下整个链路来龙去脉

协议,规范    支持的请求协议(常见,未列全)    同步/异步    支持的框架
CGI    HTTP        CGI程序
WSGI    HTTP    同步    Flup,Flask
ASGI    HTTP,HTTP2,WebSocket等    同步/异步    FastAPI,Quart,Sanic,Vibora,Tornado
CGI
CGI(Common Gateway Interface),通用网关接口,它是一种协议,是Web服务器和独立进程之间的协议,它会把HTTP请求的Request的Header设置成进程环境变量,HTTP请求的Body正文设置成进程的标准输入,进程的标准输出设置为HTTP响应的Response。

早期的Web服务器,只能响应浏览器发来的HTTP静态资源的请求,随着技术的发展,需要用到动态技术。由于Web服务器不能直接运行动态脚本,为了解决Web服务器与应用程序之间数据互通,出现了CGI。由于效率低下,不安全等原因,目前在生产环境基本被抛弃。

CGI程序
CGI(Common Gateway Interface)是一个接口规范或协议,实现其规范的程序叫做CGI程序。Web客户端发送HTTP请求到Web服务端,之后服务端通过CGI程序进行处理数据,处理完的结果在逐层返回,请看下图

我们常说的Web服务器一般是用于加载静态文件的请求,有一些动态脚本的请求,就会需要Web服务器创建一个新的进程来启动CGI程序,也就是CGI程序进行加载动态脚本,之后由Web服务器返回给客户端。

CGI程序可以是任何有标准输入和输出的脚本语言或者编程语言实现的,但由于其漏洞大,安全性低,每次有动态页面请求都会启动一个CGI程序,因此服务器压力特别大。逐渐出现了mod_perl、FastCGI等增强版本

WSGI
Web服务器网关接口(Python Web Server Gateway Interface),缩写为WSGI,它是一种专为python定义的接口规范,用于web服务端和web应用(框架)之间的连接,如此web应用可以一起处理一个请求,同时也是基于CGI进行设计的

通俗的理解,WSGI也是一种规范协议,主要是建立一个适用于服务器与Web框架之间的接口。那么跟CGI类似的,你可以通过自己的编程语言实现符合WSGI的应用程序,下面看一下WIKI上面的例子

def app(environ, start_response):
    start_response('200 OK', [('Content-Type', 'text/plain')])
    yield "Hello world!\n"
1
2
3
其中

第一行定义了一个名为 app 的 callable服务器网关接口#cite_note-2),接受两个参数,environ 和 start_response,environ 是一个字典包含了 CGI 中的环境变量。
第二行调用了start_response,状态指定为“200 OK”,消息头指定为内容类型是“text/plain”。start_response 也是一个 callable,接受两个必须的参数,status(HTTP 状态)和 response_headers(响应消息的头)。
第三行将响应消息的消息体返回。
这里的流程请注意:

Web客户端(浏览器)发送请求

HTTP服务器接收请求

实现了WSGI的服务器接收请求(可以和2合并)

a. 把环境变量和请求参数以及一个callback回调函数传递给Web应用程序

b. Web应用程序处理完之后通过回调函数返回给HTTP服务器

WSGI 协议包含两个部分,一个是 WSGI 服务器端(server),另一个则是应用程序端(application)。即 WSGI 对上文中的 Web 应用程序也有比较严格协议规定。固编写 Web 应用程序通常需要使用支持 WSGI 协议的应用框架,如 Django、Flask 等。

ASGI
异步网关接口(Asynchronous Server Gateway Interface),是WSGI的扩展版本,旨在为Python Web服务、框架和应用之间提供一个标准的异步接口。其本身可以提供同步和异步应用,并且可以并行处理。还能处理多种通用协议,包括HTTP,HTTP2和WebSocket。同WSGI一样,需要有独立的服务器实现这种异步的网关接口,比如Daphne、Uvicorn、Hypercorn等

相关文章:

python WSGI和ASGI的区别

用户到我们web应用中间经过的相关协议,具体介绍和pyhton相关的WSGI和ASGI,我先把结论列出来,详细描述请看下面介绍! 请大家先记住这张图,带着问题和整个框架去看比较易于了解 CGI,WSGI,ASGI、…...

【Golang】什么是内存逃逸?

文章目录 要从C/C谈起Golang的内存逃逸 要从C/C谈起 在C/C中,局部变量被分配到栈区,一旦当前函数执行完毕,局部变量占用的内存也将被释放,因此以下代码无法将数组的内容传递出去。 int *getArray() {int array[7] {1, 2, 3, 4,…...

MVC OR DDD

MVC OR DDD 说明:这篇是标题党,不包含相关概念说明 前段时间跟随师兄学习了解了DDD领域驱动模型,觉得这个思想更好,进行下面解析和学习方面的思考和实践,觉得很好,耐心读下去。希望对您有所帮助。 首先&am…...

前端面试:【TypeScript】静态类型检查与编译时类型检查

TypeScript是一种由Microsoft开发的编程语言,它在JavaScript的基础上添加了强大的静态类型系统。在本文中,我们将深入探讨TypeScript的静态类型检查和编译时类型检查,以及它们如何提高代码的可靠性和可维护性。 1. 静态类型检查(S…...

Qt中设置QListWidget滑动条滚动速度

QListWidget继承QListView控件,Qt帮助文档中说 QAbstractItemView::ScrollPerPixel 和QAbstractItemView::ScrollPerItem分别可以实现按item滚动和像数点滚动,但是好像都没效果。还有就是说通过创建QScrollBar有用,但是也没效果。 亲测还是这…...

STM32的lorawan协议栈

LoRa 是LPWAN通信技术中的一种,是美国Semtech公司采用和推广的一种基于扩频技术的超远距离无线传输方案。这一方案改变了以往关于传输距离与功耗的折衷考虑方式为用户提供一种简单的能实现远距离、长电池寿命、大容量的系统,进而扩展传感网络。目前&…...

IC芯片 trustzone学习

搭建Airplay TA环境需要在IC的TrustZone中进行。TrustZone是一种安全技术,用于隔离安全和非安全环境,并保护敏感文件。在TrustZone中,我们需要编写一个叫做TA(Trusted Application)的应用程序来控制这些私密文档。 &am…...

Day19-异步请求-axios文件上传

Day19-异步请求 什么是同步请求当前浏览器刷新或者改变浏览器地址栏地址才能发送请求,这种请求称为同步请求 什么是异步请求当我们发送请求时,浏览器不会刷新,浏览器地址栏也不会变化,这种请求称为异步请求异步请求用到的前端技术: ajax 或 axios一 封装Ajax /*** 编写ajax函…...

从零学算法79

79.给定一个 m x n 二维字符网格 board 和一个字符串单词 word 。如果 word 存在于网格中,返回 true ;否则,返回 false 。 单词必须按照字母顺序,通过相邻的单元格内的字母构成,其中“相邻”单元格是那些水平相邻或垂直…...

ctfshow-web-红包题第六弹

0x00 前言 CTF 加解密合集CTF Web合集 0x01 题目 0x02 Write Up 首先跑一下字典,这里用的dirmap,可以看到有一个web.zip 下载下来之后发现是一个网站备份,备份的是check.php.bak 然后接着看,可以看到这里不太可能是sql注入,有…...

蓝蓝设计UI设计公司-界面设计与开发案例

天津航天中为项目 中国南方电网十二个软件交互优化和界面设计 图标设计 | 交互设计 | 界面设计 天津航天中为数据系统科技有限公司是航天503所控股的专业化公司,坐落于天津滨海新区航天技术产业园,是航天五院家入住天津未来科技城的军民融合型企业&…...

IDEA 配置注释模板

目录 一、配置类模板注释 二、配置方法注释 一、配置类模板注释 打开IDEA,打开settings(快捷键:Ctrl Alt s),选择Editor,找到File and Code Templates,设置需要配置注释的文件类型,如下图所示&#xf…...

Kuka机器人设计通用码垛程序

假设需要一个码垛程序, 从输送线抓到托盘, 托盘每层4个, 需要码5层, 可以用以下程序架构设计: 1, 再config中定义层数cengshu , 每层码垛的个数(码垛的次数)cishu , 每层的高度levelHeight , 码垛放置点的集合putPoint[,] ,预放点1集合prePut1[,], 预放点2集合prePut2[,] DEC…...

pandas由入门到精通-数据清洗-扩展数据类型

pandas-02-数据清洗&预处理 扩展数据类型1. 传统数据类型缺点2. 扩展的数据类型3. 如何转换类型文中用S代指Series,用Df代指DataFrame 数据清洗是处理大型复杂情况数据必不可少的步骤,这里总结一些数据清洗的常用方法:包括缺失值、重复值、异常值处理,数据类型统计,分…...

深入理解 Vue Router:构建可靠的前端路由系统

目录 01-什么是前端路由以及路由两种模式实现原理02-路由的基本搭建与嵌套路由模式03-动态路由模式与编程式路由模式04-命名路由与命名视图与路由元信息05-路由传递参数的多种方式及应用场景06-详解route对象与router对象07-路由守卫详解及应用场景 01-什么是前端路由以及路由两…...

Mysql B+数索引结构

一、B树和B树区别 二、 B 树形成过程 三、页分裂过程 3.1 页分裂过程实例 3.1.1 原有数据1、3、5形成如下数据页 3.1.2 先新插入数据4,因为 页10 最多只能放3条记录所以我们不得不再分配一个新页: 新分配的数据页编号可能并不是连续的,也…...

在window上配置NASM

NASM是支持x86、x64架构CPU的汇编器(汇编软件);NASM也支持大量的文件格式,包括Linux,*BSD,a.out,ELF,COFF,Mach−O,Microsoft 16−bit OBJ,Win32以及Win64,同…...

用QT实现MVP模式

近些天用qt 作项目,遇到参数界面.偷闲写个mvp模式示例. mvp模式重要的有两点 1 低耦合: 界面与后端数据类,不直接引用,可方便替换. 2 形成界面驱动-界面更新的闭环.:通过函数指针类技术,让数据自动回流. MVP (Model-View-Presenter) 视图(View): 接…...

(2023)Linux安装pytorch并使用pycharm远程编译运行

(2023)Linux安装pytorch并使用pycharm远程编译运行 安装miniconda 这部分参考我这篇博客的前半部分Linux服务器上通过miniconda安装R(2022)_miniconda 安装r_Dream of Grass的博客-CSDN博客 创建环境 创建一个叫pytorch的环境…...

poi带表头多sheet导出

导出工具类 package com.hieasy.comm.core.excel;import com.hieasy.comm.core.excel.fragment.ExcelFragment; import com.hieasy.comm.core.utils.mine.MineDateUtil; import org.apache.poi.hssf.usermodel.*; import org.apache.poi.ss.usermodel.*; import org.apache.po…...

java调用dll出现unsatisfiedLinkError以及JNA和JNI的区别

UnsatisfiedLinkError 在对接硬件设备中,我们会遇到使用 java 调用 dll文件 的情况,此时大概率出现UnsatisfiedLinkError链接错误,原因可能有如下几种 类名错误包名错误方法名参数错误使用 JNI 协议调用,结果 dll 未实现 JNI 协…...

PL0语法,分析器实现!

简介 PL/0 是一种简单的编程语言,通常用于教学编译原理。它的语法结构清晰,功能包括常量定义、变量声明、过程(子程序)定义以及基本的控制结构(如条件语句和循环语句)。 PL/0 语法规范 PL/0 是一种教学用的小型编程语言,由 Niklaus Wirth 设计,用于展示编译原理的核…...

NFT模式:数字资产确权与链游经济系统构建

NFT模式:数字资产确权与链游经济系统构建 ——从技术架构到可持续生态的范式革命 一、确权技术革新:构建可信数字资产基石 1. 区块链底层架构的进化 跨链互操作协议:基于LayerZero协议实现以太坊、Solana等公链资产互通,通过零知…...

OpenLayers 分屏对比(地图联动)

注:当前使用的是 ol 5.3.0 版本,天地图使用的key请到天地图官网申请,并替换为自己的key 地图分屏对比在WebGIS开发中是很常见的功能,和卷帘图层不一样的是,分屏对比是在各个地图中添加相同或者不同的图层进行对比查看。…...

【学习笔记】深入理解Java虚拟机学习笔记——第4章 虚拟机性能监控,故障处理工具

第2章 虚拟机性能监控,故障处理工具 4.1 概述 略 4.2 基础故障处理工具 4.2.1 jps:虚拟机进程状况工具 命令:jps [options] [hostid] 功能:本地虚拟机进程显示进程ID(与ps相同),可同时显示主类&#x…...

ubuntu系统文件误删(/lib/x86_64-linux-gnu/libc.so.6)修复方案 [成功解决]

报错信息:libc.so.6: cannot open shared object file: No such file or directory: #ls, ln, sudo...命令都不能用 error while loading shared libraries: libc.so.6: cannot open shared object file: No such file or directory重启后报错信息&…...

ZYNQ学习记录FPGA(一)ZYNQ简介

一、知识准备 1.一些术语,缩写和概念: 1)ZYNQ全称:ZYNQ7000 All Pgrammable SoC 2)SoC:system on chips(片上系统),对比集成电路的SoB(system on board) 3)ARM:处理器…...

LangChain 中的文档加载器(Loader)与文本切分器(Splitter)详解《二》

🧠 LangChain 中 TextSplitter 的使用详解:从基础到进阶(附代码) 一、前言 在处理大规模文本数据时,特别是在构建知识库或进行大模型训练与推理时,文本切分(Text Splitting) 是一个…...

python读取SQLite表个并生成pdf文件

代码用于创建含50列的SQLite数据库并插入500行随机浮点数据,随后读取数据,通过ReportLab生成横向PDF表格,包含格式化(两位小数)及表头、网格线等美观样式。 # 导入所需库 import sqlite3 # 用于操作…...

初探用uniapp写微信小程序遇到的问题及解决(vue3+ts)

零、关于开发思路 (一)拿到工作任务,先理清楚需求 1.逻辑部分 不放过原型里说的每一句话,有疑惑的部分该问产品/测试/之前的开发就问 2.页面部分(含国际化) 整体看过需要开发页面的原型后,分类一下哪些组件/样式可以复用,直接提取出来使用 (时间充分的前提下,不…...