Python Web开发中,WSGI协议的作用和实现原理详解

首先理解下面三个概念:

WSGI:全称是Web Server Gateway Interface,WSGI不是服务器,python模块,框架,API或者任何软件,只是一种规范,描述web server如何与web application通信的规范。

uwsgi:与WSGI一样是一种协议,是uWSGI服务器的独占协议,用于定义传输信息的类型(type of information),每一个uwsgi packet前4byte为传输信息类型的描述,与WSGI协议是两种东西,据说该协议是fcgi协议的10倍快。

uWSGI:是一个web服务器,实现了WSGI协议、uwsgi协议、http协议等。

WSGI协议主要包括server和application两部分:

其中application部分:

示例代码:

def application(environ, start_response):
    status = ‘200 OK‘
    response_headers = [(‘Content-Type‘, ‘text/html‘)]
    # application内部调用start_response
    start_response(status, response_headers)

    # 解析environ信息,业务逻辑处理后,返回对应的响应信息(下面代码只是模拟业务处理)
    file_name = environ[‘PATH_INFO‘]
    if file_name == "/index.py":
        return index(file_name)
    elif file_name == "/center.py":
        return center(file_name)
    else:
        return ‘Hello world a simple WSGI application!‘

有了WSGI,我们在框架中只关心如何从environ这个dict(wgsi规定传过来一个字典)对象拿到HTTP请求信息,然后构造HTML,通过start_response()发送Header,最后返回Body。

整个application()函数本身没有涉及到任何解析HTTP的部分。 也就是说,底层代码不需要我们自己编写,我们只负责业务逻辑部分即可。

但是我们想一下,这个application()函数怎么调用?如果我们自己调用,两个参数environ和start_response我们没法提供,返回的str也没法发给浏览器。

截取server端部分代码实例如下:

          # 重点关注逻辑
                # 准备一个字典,里面存放需要传递给web框架的数据
                env = dict()
                # ----------更新---------
                env[‘PATH_INFO‘] = file_name  # 例如 index.py(模拟请求信息)

                # 重点关注逻辑
                # 服务器调用框架中实现的application函数,并将包含请求信息的字典和获取响应头的函数传入
                response_body = self.application(env, self.start_response)
?

                # 合并header和body(响应客户端的请求,这个逻辑不用关注)
                response_header = "HTTP/1.1 {status}\r\n".format(status=self.headers[0])
                response_header += "Content-Type: text/html; charset=utf-8\r\n"
                response_header += "Content-Length: %d\r\n" % len(response_body.encode("utf-8"))
                for temp_head in self.headers[1]:
                    response_header += "{0}:{1}\r\n".format(*temp_head)
?
                response = response_header + "\r\n"
                response += response_body
?
                client_socket.send(response.encode(‘utf-8‘))
?
    # 重点关注逻辑
    # server端实现了start_response函数的定义
    def start_response(self, status, headers):
        """这个方法,会在 web框架中被默认调用"""
        response_header_default = [
            ("Data", time.time()),
            ("Server", "ItCast-python mini web server")
        ]
?
        # 将状态码/相应头信息存储起来
        # [字符串, [xxxxx, xxx2]]
        self.headers = [status, response_header_default + headers]

这段代码,是在客户端请求动态资源时启动,即服务器需要向后端框架请求资源。代码解析已在代码中注释。

所以我们基本可以获得如下结论:

要实现WSGI协议,必须同时实现web server端和web application端

当前运行在WSGI协议之上的web框架有Torando,Flask,Django等

比较常用的WSGI协议服务器有:uWSGI,gunicorn等

1、框架需要实现WSGI协议,例如:Flask,Django等

2、environ 和 start_response 由 http server 提供并实现 3、environ 变量是包含了请求信息的字典 4、Application 内部在返回前调用 start_response 5、application()函数必须由WSGI服务器来调用

server要履行的任务:

1、接收HTTP请求

2、解析HTTP请求

3、准备 environ请求参数

4、定义 start_response 函数

5、组装响应头和相应体返回给客户端

application要履行的责任:

1、解析服务器发来的请求信息

2、根据请求信息,进行业务处理

3、返回所需要的数据

至此,您应该对WSGI有了一定的了解吧。

扩展阅读:

目前一些主要的实现了WSGI协议的服务器:

gunicorn

Gunicorn(从Ruby下面的Unicorn发展而来):依赖Nginx的代理行为,同Nginx进行功能上的分离。由于不需要直接处理用户来的请求(都被Nginx先处理),Gunicorn不需要完成相关的功能,其内部逻辑非常简单:接受从Nginx来的动态请求,处理完之后返回给Nginx,由后者返回给用户。

由于功能定位很明确,Gunicorn得以用纯Python开发:大大缩短了开发时间的同时,性能上也不会很掉链子。同时,它也可以配合Nginx的代理之外的别的Proxy模块工作,其配置也相应比较简单。

配置上的简单,大概是它流行的最大的原因。

uwsgi

因为使用C语言开发,会和底层接触的更好,配置也是比较方便,目前和gunicorn两个算是部署时的唯二之选。

以下是通常的配置文件

fcgi

不多说,用的少。

bjoern

Python WSGI界最牛逼性能的Server其中一个是bjoern,纯C,小于1000行代码,就是看不惯uWSGI的冗余自写的。

原文地址:https://www.cnblogs.com/wangcoo/p/10018373.html

时间: 2024-10-10 01:44:19

Python Web开发中,WSGI协议的作用和实现原理详解的相关文章

[Python WEB开发] 使用WSGI开发类Flask框架 (二)

WSGI     Web服务器网关接口 WSGI主要规定了Web服务器如何与Web应用程序进行通信,以及如何将Web应用程序链接在一起来处理一个请求. wsgiref Python中的WSGI参考模块 一.WSGI 应用程序端: 1. 根据WSGI定义,应用程序应该是可调用对象 2.该可调用对象必须有两个固定参数:一个是含有服务器环境变量的字典,另一个是可调用对象,该对象使用HTTP状态码和会返回给客户端的HTTP头来初始化响应 environ 变量包含一些熟悉的环境变量,如HTTP_HOST,

《Python Web开发与接口测试》

为什么学习本书: 是否想学习Python web开发而找不到很好的入门教程. 是否很想知道当你点击一个按钮后,程序到底经过哪些过程把你想要的页面展现在你面前. 是否想告诉别人,不就是开发嘛,我也会. 是否想知道接口到底是什么,它是如何被开发出来的,我们又如何对它进行测试? 为什么是Django? 我们总是很难去决定一件事情.比如,我到底该学Java 呢还是C# 呢? 到底测试的工资高还是开发的高?我学习了Python之后,想学习web开发,是Django 还是Flask 好学.强大和灵活? 搞J

Web开发中的18个关键性错误

前几年,我有机会能参与一些有趣的项目,并且独立完成开发.升级.重构以及新功能的开发等工作. 本文总结了一些PHP程序员在Web开发中经常 忽略的关键错误,尤其是在处理中大型的项目上问题更为突出.典型的错误表现在不能很好区分各种开发环境和没有使用缓存和备份等. 下面以PHP为例,但是其核心思想对每一个Web程序员都是适用的. 应用程序级别的错误 1.在开发阶段关闭了错误报告 我唯一想问的是:为什么?为什么在开发的时候要关闭错误报告? PHP有很多级别的错误报告,在开发阶段我们必须将它们全部开启.

Redis的Python实践,以及四中常用应用场景详解——学习董伟明老师的《Python Web开发实践》

首先,简单介绍:Redis是一个基于内存的键值对存储系统,常用作数据库.缓存和消息代理. 支持:字符串,字典,列表,集合,有序集合,位图(bitmaps),地理位置,HyperLogLog等多种数据结构. 支持事务.分片.主从复之.支持RDB(内存数据保存的文件)和AOF(类似于MySQL的binlog)两种持久化方式.3.0加入订阅分发.Lua脚本.集群等特性. 命令参考:http://doc.redisfans.com 中文官网:http://www.redis.net.cn 安装(都大同小

Web开发中 前端路由 实现的几种方式和适用场景

浅析Web开发中前端路由实现的几种方式 主题 Web开发 故事从名叫Oliver的绿箭虾`说起,这位大虾酷爱社交网站,一天他打开了 Twitter ,从发过的tweets的选项卡一路切到followers选项卡,Oliver发现页面的内容变化了,URL也变化了,但为什么页面没有闪烁刷新呢?于是Oliver打开的网络监控器(没错,Oliver是个程序员),他惊讶地发现在切换选项卡时,只有几个XHR请求发生,但页面的URL却在对应着变化,这让Oliver不得不去思考这一机制的原因- 叙事体故事讲完,

python web 开发学习路线

自己目前学习python web 开发, 经过两个月的摸索,目前对web开发有了浅显的认识,把自己的学习过程贴出来.1.python入门推荐老齐<从零开始学python>,<python简明教程>,这两本书很适合小白入门(像我一样长期徘徊在编程门外的人)2.python进阶推荐<python学习手册>,python学习手册的前半部分与在入门教程中的基础部分相重复,后面部分对python的介绍更细致,比如面向对象的这部分对于小白理解相对容易.还有一本<python

《Python入门》Linux 下 Python Web开发环境搭建笔记

之前写过 Windows 7下Python Web开发环境搭建笔记,今天写一下在Linux系统下搭建Python Web的开发测试环境. 我使用的系统是:ubuntu 14.04 server,根据个人经验,CentOS 6.5 下也适用. 关于Python的版本 进入Python的网站,鼠标移到导航条上的下载,我们会发现提供两下主版本的下载链接! 这两个之间存在什么差别呢? 个人理解,2.7.x的版本为更加稳定的版本,而3.x的版本则是比较前卫的版本,包含了很多新功能新特性之类的: 但如果想要

windows下python web开发环境的搭建

windows下python web开发环境: python2.7,django1.5.1,eclipse4.3.2,pydev3.4.1 一. python环境安装 https://www.python.org/ftp/python/2.7/python-2.7.amd64.msi 不多说,装完后把C:\Python27加入到path环境变量里. 然后就溜溜python,看看version啦.OK,next step. 二. python web开发框架django安装 django是一个采用

WEB开发中的字符集和编码

html,body,div,span,applet,object,iframe,h1,h2,h3,h4,h5,h6,p,blockquote,pre,a,abbr,acronym,address,big,cite,code,del,dfn,em,img,ins,kbd,q,s,samp,small,strike,strong,sub,sup,tt,var,b,u,i,center,dl,dt,dd,ol,ul,li,fieldset,form,label,legend,table,caption