1.單線程
tornado.web:基礎web框架模塊
tornado.ioloop:核心IO循環模塊,高效的基礎。封裝了:
1.asyncio 協程,異步處理
2. epoll模型:水平觸發(狀態改變就詢問,select(),poll()), 邊緣觸發(一直詢問,epoll())
3.poll 模型:I/O多路復用技術
4.BSD(UNIX操作系統中的一個分支的總稱)的kqueue(kueue是在UNIX上比較高效的IO復用技術)
epoll和kqueue的區別如下:
'epoll'僅適用於文件描述符,在Unix中,一切都是文件”。
這大多是正確的,但並非總是如此。例如,計時器不是文件。
信號不是文件。信號量不是文件。進程不是文件。
(在Linux中)網絡設備不是文件。類UNIX操作系統中有許多不是文件的東西
。您不能使用select()/ poll()/ epoll來復制那些“事物”。
Linux支持許多補充系統調用,signalfd(),eventfd()和timerfd_create()
它們將非文件資源轉換為文件描述符,以便您可以將它們與epoll()復用。
epoll甚至不支持所有類型的文件描述符;
select()/ poll()/ epoll不適用於常規(磁盤)文件。
因為epoll 對准備模型有很強的假設; 監視套接字的准備情況,
以便套接字上的后續IO調用不會阻塞。但是,磁盤文件不適合此模型,因為它們總是准備就緒。
kqueue 中,通用的(struct kevent)系統結構支持各種非文件事件
import tornado.web #tornado.web:基礎web框架模塊
import tornado.ioloop #tornado.ioloop:核心IO循環模塊,高效的基礎。
class IndexHandler(tornado.web.RequestHandler):
#類比Django中的視圖,相當於業務邏輯處理的類
def get(self): #處理get請求的,並不能處理post請求
self.write("good boy") #響應http的請求
if __name__=="__main__":
"""
實例化一個app對象
Application:他是tornado.web框架的核心應用類,是與服務器對應的一個接口
里面保存了路由映射表,還有一個listen方法,可以認為用來創建一個http的實例
並綁定了端口
"""
app = tornado.web.Application([
(r"/" ,IndexHandler),
])
app.listen(8888) #綁定監聽端口,但此時的服務器並沒有開啟監聽
tornado.ioloop.IOLoop.current().start()
#Application([(r"/" ,IndexHandler),])傳入的第一個參數是
#路由路由映射列表,但是在此同時Application還能定義更多參數
#IOLoop.current():返回當前線程的IOLoop實例
#例如實例化對象 ss=run() ,ss.start()
#start():啟動了IOloop實例的循環,連接客服端后,同時開啟了監聽
原理如下:
linux-epoll進行管理多個客服端socket
tornado-IoLoop不斷進行詢問epoll:小老弟,有沒有我需要做的事嗎?
當epoll返回說:老哥,有活了
tornado-IoLoop將活上傳給tornado.web.Application
tornado.web.Application中有 路由映射表
就會將socket進行一個路由匹配
把socket匹配給相對應的Handler(處理者)
Handler(處理者)處理后將數據返回給對應的socket,
(這里因為可能會延時響應,所以這里進行異步處理)
socket然后再傳給了客服端瀏覽器。