【问题标题】:Apache lags when responding to gzipped requests响应 gzip 压缩请求时 Apache 滞后
【发布时间】:2009-10-13 10:36:34
【问题描述】:

对于我正在开发的应用程序,用户提交带有多部分表单数据(内容类型:multipart/form-data)的 gzip 压缩 HTTP POST 请求(内容编码:GZIP)。我使用 mod_deflate 作为输入过滤器进行解压,并通过 mod_wsgi 在 Django 中处理 Web 请求。

一般来说,一切都很好。但是对于某些请求(确定性),从请求到响应几乎有一分钟的延迟。调查显示 django 中的处理是立即完成的,但服务器的响应却停滞不前。如果请求未经过 GZIP 压缩,则一切正常。

请注意,为了处理 mod_wsgi 中的故障,我将 content-length 设置为未压缩的消息大小。

有人遇到过这个问题吗?有没有办法在处理响应时轻松调试 apache?

【问题讨论】:

    标签: django apache gzip mod-wsgi mod-deflate


    【解决方案1】:

    您认为 mod_wsgi 中存在什么故障?

    简单的事实是 WSGI 1.0 不支持改变请求内容的内容长度的可变输入过滤器。因此,在使用 WSGI 1.0 时,从技术上讲,您不能在 Apache 中使用 mod_deflate 来请求内容。您将内容长度设置为实际大小以外的值很可能会填满 mod_deflate 的操作。

    如果您希望能够处理压缩的请求内容,您需要跳出 WSGI 1.0 规范并使用非标准代码。

    我建议您阅读:

    http://blog.dscpl.com.au/2009/10/details-on-wsgi-10-amendmentsclarificat.html

    这解释了这个问题和有关它的建议。

    我非常建议您将此问题提交给官方mod_wsgi mailing list,以讨论您需要如何编写代码。但是,如果您使用的是 Python 框架之一,您可能会受到限制,因为它们将实现 WSGI 1.0,而您无法做到这一点。


    更新 1

    根据 mod_wsgi 列表的讨论,原始的 WSGI 应用程序应该被包装在以下 WSGI 中间件中。这仅适用于实际提供空字符串作为输入的结束标记的 WSGI 适配器,这是 WSGI 1.0 不需要的。这可能只用于小型上传,因为所有内容都被读入内存。如果需要大量压缩上传,则应将累积的数据写入文件。

    class Wrapper(object):
    
        def __init__(self, application):
            self.__application = application
    
        def __call__(self, environ, start_response):
            if environ.get('HTTP_CONTENT_ENCODING', '') == 'gzip':
                buffer = cStringIO.StringIO()
                input = environ['wsgi.input']
                blksize = 8192
                length = 0
    
                data = input.read(blksize)
                buffer.write(data)
                length += len(data)
    
                while data:
                    data = input.read(blksize)
                    buffer.write(data)
                    length += len(data)
    
                buffer = cStringIO.StringIO(buffer.getvalue())
    
                environ['wsgi.input'] = buffer
                environ['CONTENT_LENGTH'] = length
    
            return self.__application(environ, start_response)
    
    
    application = Wrapper(original_wsgi_application_callable)
    

    【讨论】:

    猜你喜欢
    • 2010-12-17
    • 2012-08-21
    • 1970-01-01
    • 2012-08-22
    • 2019-05-07
    • 1970-01-01
    • 2012-02-12
    • 2014-02-20
    • 1970-01-01
    相关资源
    最近更新 更多