diff --git a/docs/httpbin.1.md b/docs/httpbin.1.md index ceb9145..5f5090e 100644 --- a/docs/httpbin.1.md +++ b/docs/httpbin.1.md @@ -11,6 +11,7 @@ httpbin(1): HTTP Client Testing Service `/post` Returns POST data. `/put` Returns PUT data. `/delete` Returns DELETE data. +`/gzip` Returns GZip-encoded data. ## DESCRIPTION diff --git a/httpbin/core.py b/httpbin/core.py index 7140bca..3e6b71c 100644 --- a/httpbin/core.py +++ b/httpbin/core.py @@ -7,16 +7,17 @@ httpbin.core This module provides the core HttpBin experience. """ -import os + import json +import gzip +import os +from cStringIO import StringIO from time import time as now from decimal import Decimal import redi - from decorator import decorator -from flask import Flask, request, render_template, g - +from flask import Flask, Response, request, render_template, g from .db import redis_connect from .helpers import get_files, get_headers @@ -75,6 +76,40 @@ def json_resource(f, runtime=True, *args, **kwargs): +@decorator +def gzip_response(f, *args, **kwargs): + + data = f(*args, **kwargs) + + if isinstance(data, Response): + content = data.data + else: + content = data + + gzip_buffer = StringIO() + gzip_file = gzip.GzipFile( + mode='wb', + compresslevel=4, + fileobj=gzip_buffer + ) + gzip_file.write(content) + gzip_file.close() + + gzip_data = gzip_buffer.getvalue() + + if isinstance(data, Response): + data.data = gzip_data + data.headers['Content-Encoding'] = 'gzip' + data.headers['Content-Length'] = str(len(data.data)) + + return data + + return gzip_data + + + + + def log_request(key): """Logging Decorator.""" @@ -200,6 +235,21 @@ def view_post(): files=get_files() ) +@app.route('/gzip') +@gzip_response +@json_resource +@log_request(key='httpbin:gzip') +def view_gzip_encoded_content(): + """Returns GZip-Encoded Data.""" + + return dict( + origin=request.remote_addr, + headers=get_headers(), + method=request.method, + gzipped=True + ) + + if __name__ == '__main__':