1、WSGI是什么
wsgi:Web Server Gateway Interface,是一种协议。用于定义Server与app之间的交互方式。
wsgi把应用分成了3个组件:
1. web server:
主要实现:
1.socket通讯服务器端,监听端口
2.接收、解析http报文
3.读取服务器端的html文档,把读取的html文档response回浏览器,这是静态服务器,如nginx、Apache
4.调用app,返回app执行结果给浏览器。这是动态服务器,如Tomcat。
2. web app
1.一个函数或类的方法
2.遵循固定格式的入口函数_call_()、入参(environ,start_response)、返回值
3. 中间件
1.server与app中间的程序(所以叫中间件)
2.路由
3.流量控制等
ps:
wsgi对web应用的划分太精辟了,对WebServer的理解、应用、url转应用调用等场景的理解豁然开朗。
以前只知道Tomcat,按这个概念套用,也更清楚了。
2、举个例子加深理解
import socket
import sysclass WSGIServer:def __init__(self):self.listener&#61;socket.socket()self.listener.setsockopt(socket.SOL_SOCKET,socket.SO_REUSEADDR,1)self.listener.bind((&#39;0.0.0.0&#39;,8080))self.listener.listen(1)print(&#39;Serving HTTP 0.0.0.0 port 8080&#39;)self.app&#61;Noneself.headers_set&#61;Nonedef set_app(self,application):self.app&#61;applicationdef start_response(self,status,headers):self.headers_set&#61;[status,headers]def serve_forever(self):while True:listener&#61;self.listenerclient_connection,client_address&#61;listener.accept()request&#61;client_connection.recv(1024)print(f&#39;request we received:{request}&#39;)method,path,_&#61;request.split(b&#39; &#39;,2)environ &#61; {&#39;wsgi.version&#39;: (1, 0),&#39;wsgi.url_scheme&#39;: &#39;http&#39;,&#39;wsgi.input&#39;: request,&#39;wsgi.errors&#39;: sys.stderr,&#39;wsgi.multithread&#39;: False,&#39;wsgi.multiprocess&#39;: False,&#39;wsgi.run_once&#39;: False,&#39;REQUEST_METHOD&#39;: method.decode(&#39;utf-8&#39;),&#39;PATH_INFO&#39;: path.decode(&#39;utf-8&#39;),&#39;SERVER_NAME&#39;: &#39;127.0.0.1&#39;,&#39;SERVER_PORT&#39;: &#39;8080&#39;,}app_result&#61;self.app(environ,self.start_response)response_status,response_headers&#61;self.headers_setresponse&#61;f&#39;HTTP/1.1 {response_status}\r\n&#39;for header in response_headers:response&#43;&#61;f&#39;{header[0]}:{header[1]}\r\n&#39;response&#43;&#61;&#39;\r\n&#39;response&#61;response.encode(&#39;utf-8&#39;)for data in app_result:response&#43;&#61;dataclient_connection.sendall(response)client_connection.close()print(&#39;!!!!!!!!one request responsed!!!!!!!!&#39;)if __name__&#61;&#61;&#39;__main__&#39;:if len(sys.argv)<2:sys.exit(&#39;argv error&#39;)app_path&#61;sys.argv[1]module,app&#61;app_path.split(&#39;:&#39;)module&#61;__import__(module)app&#61;getattr(module,app)server&#61;WSGIServer()server.set_app(app)server.serve_forever()
在上边的程序了里&#xff1a;
- init(self)&#xff1a;定义socket通讯的服务器端&#xff0c;用来监听端口、接收数据、返回数据。
- serve_forever(self)&#xff1a;调用app&#xff0c;生成相应的http报文&#xff0c;在通过socket返回。
- 浏览器&#xff1a;接收服务器返回的http报文&#xff0c;然后渲染展示。
3、看看http请求和相应报文
对程序的部分内容加深理解。
3.1 请求报文
包括&#xff1a;请求的方法、url、客户端程序类型等。
浏览器自动生成并发送的。
GET / HTTP/1.1
Host: localhost:8080
User-Agent: Mozilla/5.0 (Windows NT 6.3; Win64; x64; rv:73.0) Gecko/20100101 Firefox/73.0
Accept: text/html,application/xhtml&#43;xml,application/xml;q&#61;0.9,image/webp,*
3.2 响应报文
注意遵守固定格式&#xff0c;响应头包括协议版本、响应编号、响应结果&#xff0c;
然后&#xff0c;与实际内容中间间隔一个空行。
HTTP/1.1 200 OKHello, World!