tornado總結9-自動對gzip的請求進行解壓

說明

            server.py寫了一個tornado服務,監聽了8956端口,client.py組裝請求併發送到這個端口,須要先啓動server.py,而後再啓動client.py才能看到測試效果。python

server.py

#server.py

import json
from sys import getsizeof

import tornado
import tornado.httpserver
import tornado.ioloop
import tornado.web

class TestHandler(tornado.web.RequestHandler):

    def post(self):

        # 獲取請求頭部的大小
        print("請求報文頭部: {0}".format(self.request.headers.__dict__))
        print("請求報文內容大小: {0}".format(self.request.headers["Content-Length"]))

        print("請求報文內容解壓後的大小: {0}".format(getsizeof(self.request.body)))

        return self.finish(self.request.body)


class Application(tornado.web.Application):
    def __init__(self):
        handlers = [
            (r'/test',TestHandler)
        ]
        settings = dict(
        )
        tornado.web.Application.__init__(self, handlers, **settings)

if __name__ == '__main__':
    app_port = 8965
    app = Application()
    http_server = tornado.httpserver.HTTPServer(app, decompress_request=True)
    http_server.listen(app_port)

    print("http://localhost:8965")
    tornado.ioloop.IOLoop.instance().start()

與沒有特殊設置的tornado配置相比只是在初始化時對httpserver增長了一個配置項web

decompress_request=True

在有這個配置項的時候,若是post請求的報文頭部有說明編碼方式是 gzip時,tornado將會對這個請求進行解壓操做。json

 

若是不設置這個操做,當收到gzip類型的請求時會出現一句告警日誌bash

WARNING:tornado.general:Unsupported Content-Encoding: gzip併發

而且不會對請求進行解壓操做。app

 

client.py

import gzip
import json
from io import BytesIO
from sys import getsizeof

#client.py
from tornado.escape import utf8
from tornado.httpclient import HTTPRequest, HTTPClient

if __name__ == '__main__':
    url = 'http://localhost:8965/test'


    try:
        #請求內容
        requ_data =  "111111111111111111111111111111111111111111111"*6000

        #對請求內容進行gzip壓縮操做
        bytesio = BytesIO()
        gzip_file = gzip.GzipFile(mode='w', fileobj=bytesio)
        gzip_file.write(utf8(requ_data))
        gzip_file.close()
        compressed_requ_data = bytesio.getvalue()

        print("請求內容壓縮前的大小: {0}".format(getsizeof(requ_data)))
        print("請求內容壓縮後的大小: {0}".format(getsizeof(compressed_requ_data)))

        # 發送未壓縮的請求
        # request = HTTPRequest(url=url, method='POST',  body=requ_data)  
        
        # 發送壓縮後的請求
        request = HTTPRequest(url=url, method='POST', headers={'Content-Encoding': 'gzip'}, body=compressed_requ_data)

        http_client = HTTPClient()
        response = http_client.fetch(request)

        #因爲回覆的內容太大了,所以註釋掉了輸出
        #print("回覆內容: {0}".format(response.body.decode()))

        print("請求報文頭部: {0}".format(request.headers.__dict__))
        print("請求報文內容大小: {0}".format(request.headers["Content-Length"]))

        print("回覆頭部: {0}".format(request.response.__dict__))
        print("回覆報文內容大小: {0}".format(response.headers["Content-Length"]))
        print("回覆報文內容解壓後大小: {0}".format(getsizeof(response.body)))

    except Exception as e:
        print('異常', e)

在發送壓縮請求時須要設置報文的頭部 tornado

headers={'Content-Encoding': 'gzip'}

上面的server.py收到這種類型的請求時就會進行解壓操做oop

 

測試輸出:

client

請求內容壓縮前的大小: 270049
請求內容壓縮後的大小: 331
請求報文頭部: {'_as_list': {'Connection': ['close'], 'Content-Encoding': ['gzip'], 'Accept-Encoding': ['gzip'], 'Content-Length': ['298'], 'Host': ['localhost:8965'], 'Content-Type': ['application/x-www-form-urlencoded']}, '_last_key': None, '_dict': {'Connection': 'close', 'Content-Encoding': 'gzip', 'Accept-Encoding': 'gzip', 'Content-Length': '298', 'Host': 'localhost:8965', 'Content-Type': 'application/x-www-form-urlencoded'}}
請求報文內容大小: 298
回覆頭部: {'_as_list': {'Connection': ['close'], 'Content-Encoding': ['gzip'], 'Accept-Encoding': ['gzip'], 'Content-Length': ['298'], 'Host': ['localhost:8965'], 'Content-Type': ['application/x-www-form-urlencoded']}, '_last_key': None, '_dict': {'Connection': 'close', 'Content-Encoding': 'gzip', 'Accept-Encoding': 'gzip', 'Content-Length': '298', 'Host': 'localhost:8965', 'Content-Type': 'application/x-www-form-urlencoded'}}
回覆報文內容大小: 298

server

請求報文頭部: {'_as_list': {'Accept-Encoding': ['gzip'], 'Content-Length': ['298'], 'X-Consumed-Content-Encoding': ['gzip'], 'Connection': ['close'], 'Content-Type': ['application/x-www-form-urlencoded'], 'Host': ['localhost:8965']}, '_dict': {'Accept-Encoding': 'gzip', 'Content-Length': '298', 'X-Consumed-Content-Encoding': 'gzip', 'Connection': 'close', 'Content-Type': 'application/x-www-form-urlencoded', 'Host': 'localhost:8965'}, '_last_key': 'X-Consumed-Content-Encoding'}
請求報文內容大小: 298
請求報文內容解壓後的大小: 270033

 

對回覆進行壓縮

tornado初始話時增長一個 post

compress_response=True

以下測試

class Application(tornado.web.Application):
    def __init__(self):
        handlers = [
            (r'/test',TestHandler)
        ]
        settings = dict(
            compress_response=True
        )
        tornado.web.Application.__init__(self, handlers, **settings)

若是請求的報文頭部裏面有要求  'Accept-Encoding': 'gzip', 那麼tornado會對回覆的報文進行壓縮操做, 請求方收到回覆時須要本身手動對這個進行解壓操做。

 

若是使用tornado的HTTPClient話只須要添加以下設置便可

decompress_response=True

以下

request = HTTPRequest(url=url, method='POST', headers={'Content-Encoding': 'gzip', 'Accept-Encoding': 'gzip'}, body=compressed_requ_data, decompress_response=True)
相關文章
相關標籤/搜索