摘要:在實際創建一個運行的時,一個參數都不需要我們傳,無論是還是回調函數都由服務器,也就是負責。如上所述,兩個參數,回調函數傳入和最后返回一個字符串,也就是服務器返回給客戶端的核心數據。
Python中的WSGI
https://jasonlvhit.github.io/...
簡單來看,wsgi是web組件的接口規范,在wsgi規范里,wsgi把web組件分成三個部分,wsgi server,wsgi middleware,wsgi application
application更多的時候,我們關心的只是wsgi application, wsgi application就是一個Python中的callable對象(函數,或定義了__call__方法的類等), 接受兩個參數,environ和start_response,參數只是一個名字而已,environ指的是環境變量,start_response是一個回調函數。在實際創建一個運行的app時,一個參數都不需要我們傳,無論是environ還是回調函數都由服務器,也就是wsgi server負責。
environenviron 包括 服務器環境變量,客戶端環境變量,和請求中的數據method,path等等。environ是怎么生成的呢?
wsgi server主要分為兩部分,server和handler。server監聽端口,handler處理請求。server接受到一個request,解析客戶端environ,bind一個handler,handler解析請求,將請求信息放入environ,最后服務器端環境變量也放入environ中。這就是environ的全部了。
start_response
在wsgiref中,回調函數start_response的源碼是下面這樣的:
def start_response(self, status, headers,exc_info=None):
""""start_response()" callable as specified by PEP 333""" if exc_info: try: if self.headers_sent: # Re-raise original exception if headers sent raise exc_info[0], exc_info[1], exc_info[2] finally: exc_info = None # avoid dangling circular ref elif self.headers is not None: raise AssertionError("Headers already set!") assert type(status) is StringType,"Status must be a string" assert len(status)>=4,"Status must be at least 4 characters" assert int(status[:3]),"Status message must begin w/3-digit code" assert status[3]==" ", "Status message must have a space after code" if __debug__: for name,val in headers: assert type(name) is StringType,"Header names must be strings" assert type(val) is StringType,"Header values must be strings" assert not is_hop_by_hop(name),"Hop-by-hop headers not allowed" self.status = status self.headers = self.headers_class(headers) return self.write
函數接受兩個參數,status,也就是HTTP狀態碼,和headers,請求頭。函數驗證這兩個信息,并將其塞入服務器。最后調用write方法,write方法的功能是“to buffer data for send to client”,也就是把信息再塞回客戶端。
說到這,我們就可以看看一個在PEP3333中給出的簡單的wsgi app了。
HELLO_WORLD = b"Hello world!n"
def simple_app(environ, start_response): """Simplest possible application object""" status = "200 OK" response_headers = [("Content-type", "text/plain")] start_response(status, response_headers) return [HELLO_WORLD]
如上所述,兩個參數,environ, start_response, 回調函數start_response傳入status和headers,最后返回一個字符串,也就是服務器返回給客戶端的核心數據。
同樣,我們說過,一個wsgi application是一個callable對象,只要他是callable(實現__call__方法)的就可以。在PEP3333中也給出了一個簡單的類形式的app:
class AppClass:
def __call__(self, environ, start_response): status = "200 OK" response_headers = [("Content-type", "text/plain")] start_response(status, response_headers) return [HELLO_WORLD]
到這,其實wsgi的結構很清晰了,最后,還差一個wsgi middleware。
middleware
按照PEP3333的說法,wsgi server是server端的東西,wsgi app是應用端的東西,并不是說middleware是中間的東西,middleware是一個兩頭兼顧的東西。
我們可以把app看成一個蛋糕,middleware則是這塊蛋糕的包裝。web服務中,例如session,route,auth等等,都是用middleware實現的。
例如一個PEP3333中的這個轉換piglatin的wsgi middleware:
from piglatin import piglatin
class LatinIter:
"""Transform iterated output to piglatin, if it"s okay to do so Note that the "okayness" can change until the application yields its first non-empty bytestring, so "transform_ok" has to be a mutable truth value. """ def __init__(self, result, transform_ok): if hasattr(result, "close"): self.close = result.close self._next = iter(result).__next__ self.transform_ok = transform_ok def __iter__(self): return self def __next__(self): if self.transform_ok: return piglatin(self._next()) # call must be byte-safe on Py3 else: return self._next()
class Latinator:
# by default, don"t transform output transform = False def __init__(self, application): self.application = application def __call__(self, environ, start_response): transform_ok = [] def start_latin(status, response_headers, exc_info=None): # Reset ok flag, in case this is a repeat call del transform_ok[:] for name, value in response_headers: if name.lower() == "content-type" and value == "text/plain": transform_ok.append(True) # Strip content-length if present, else it"ll be wrong response_headers = [(name, value) for name, value in response_headers if name.lower() != "content-length" ] break write = start_response(status, response_headers, exc_info) if transform_ok: def write_latin(data): write(piglatin(data)) # call must be byte-safe on Py3 return write_latin else: return write return LatinIter(self.application(environ, start_latin), transform_ok)
middleware與函數裝飾器很像。
最后,一個應用的middleware不止一層,middleware可能像下面一樣工作:
def configure(app): return ErrorHandlerMiddleware( SessionMiddleware( IdentificationMiddleware( AuthenticationMiddleware( UrlParserMiddleware(app))))))webframework
最后我們來看webframework,現在回想一下包括Django,Flask等框架,我們可以察覺出Python的web框架并不是特別的難以搭建。在4年前,第一個版本的Flask,只有短短600行代碼,并且其中充斥著大量的注釋(文檔)。
一般來說,一個python的webframework需要一個wsgi工具集(werkzeug, webob(pylons)),一個模板渲染引擎(mako,jinja2)和一個ORM數據庫工具集(sqlalchemy),還有其他的包括dispatcher,mail,json等支持,這樣我們可以膠合一個自己的框架。
文章版權歸作者所有,未經允許請勿轉載,若此文章存在違規行為,您可以聯系管理員刪除。
轉載請注明本文地址:http://specialneedsforspecialkids.com/yun/40680.html
摘要:系統安裝部署環境教程第一安裝依賴環境在準備安裝框架部署之前,我們需要先安裝依賴環境,因為可能默認的環境沒有完善的最新部署包。檢查最新版本的數據庫,然后部署安裝。到目前為止,我們已經成功的在環境中部署了應用程序,以及。 Django,是一款針對Python環境的WEB開發框架,能夠幫助我們構架快捷、簡單的WEB框架設置,Django框架非常適合開發內容應用環境,所以在本文中,麥子將整理基...
摘要:先在服務器上安裝配置好下載地址將下載好的文件上傳至服務器解壓安裝下載頁面有說明注意看一下滿足沒有有種安裝方式一種是直接安裝到一種是安裝到這里先采用第一種直接安裝到進入下載的文件目錄常規安裝先然后最后因為我是自己搭的服務器而且是版所以很多軟件 先在linux服務器上安裝, 配置好apache 下載wsgi, 地址: https://pypi.python.org/pypi/mod_ws...
摘要:提出這些規范的目的就是為了定義統一的標準,提升程序的可移植性。的對象處理完成后,會調用并且返回結果給,存放在中。比如可以檢查是否有非法內容,檢查是否有非法內容,為加上特定的等,這些都是可以的。的實現和部署要使用,需要分別實現角色和角色。 WSGI是什么 WSGI的全稱是Web Server Gateway Interface,翻譯過來就是Web服務器網關接口。具體的來說,WSGI是一個...
摘要:最新的工作中,有一部分的任務,于是開始折騰先惡補理論吧,關于有篇需要看,和,前者是年的提案,后者在年對前者做了小幅修訂,提案狀態也已經是,所以已經不是提案,已經是協議規范了,是的縮寫,解決的是各種比如與各種框架比如之間互聯互通的兼容性問題如 最新的工作中,有一部分HTTP API的任務,于是開始折騰Python WSGI... WSGI 先惡補理論吧,關于Python WSGI有2...
摘要:一般來說,這一例行程序用于處理請求的每一部分,例如把路徑作為一系列字典鍵值進行處理。,必須是按照中所規定地鍵值元組列表。行為時回車換行。這個包裝器也可能用模塊指明那些有問題的,但不完全違反的行為。 wsgirf-WSGI功能及參考實現 源碼:Lib/wsgiref Web服務器網關接口(Web Server Gateway Interface, WSGI),是用Python寫的一個服務...
閱讀 1518·2023-04-25 17:41
閱讀 3040·2021-11-22 15:08
閱讀 842·2021-09-29 09:35
閱讀 1605·2021-09-27 13:35
閱讀 3323·2021-08-31 09:44
閱讀 2716·2019-08-30 13:20
閱讀 1939·2019-08-30 13:00
閱讀 2557·2019-08-26 12:12