我有一个 mod_ext_filter 来替换静态图像 url,并使用 mod_deflate 来压缩网页。
如果我分别使用这两个模块,一切都能正常工作。
(1. 替换内容成功,不压缩 2. 压缩内容但不替换网址)
但是如果我同时使用这两个模块,那么我就会得到垃圾,并且响应头没有 gzip 但是有 Transfer-Encoding: chunked。
有人能帮我解决这个问题吗?我应该尝试哪种方法来解决?谢谢。
答案1
我自己也遇到过这种情况。INFLATE、DEFLATE 和我的自定义过滤器的组合都不起作用。它似乎总是在交给我的客户过滤器之前执行 gzip DEFLATE。
我使用的是 Apache 2.2.2。因此,本质上,当收到 gzip 编码的响应(反向代理模式)并将其传递给我的自定义过滤器时phpFilter
:
ExtFilterDefine phpFilter mode=output \
cmd="/path/my_php_filter.php"
这工作得很好(无论内容类型如何,我都会收到很好的解压缩的东西):
SetOutputFilter INFLATE;DEFLATE
这也有效(我看到了很好的压缩内容,或者很好的未压缩内容,用于非 gzip 响应,如 JSON 或 HTML):
SetOutputFilter phpFilter
但这不起作用!当 Content-Type 为 gzip 时,我的 php 脚本的 STDIN 总是会出现乱码。
SetOutputFilter INFLATE;phpFilter;DEFLATE
经过大量的谷歌搜索,再加上一点运气,这个方法终于奏效了。我不知道为什么有必要这么做,但将 proxy-html 添加到过滤器链中似乎会强制执行我的自定义过滤器前放气。
SetOutputFilter INFLATE;phpFilter;proxy-html;DEFLATE
我知道我回答这个问题晚了两年,但希望这可以为下一个人节省一两天的头痛。
答案2
我也刚刚遇到了这个:
所以也许添加 ftype=N>21 也会有效
# Trace the data read and written by mod_deflate
# for a particular client (IP 192.168.1.31)
# experiencing compression problems.
# This filter will trace what goes into mod_deflate.
ExtFilterDefine tracebefore \
cmd="/bin/tracefilter.pl /tmp/tracebefore" \
EnableEnv=trace_this_client
# This filter will trace what goes after mod_deflate.
# Note that without the ftype parameter, the default
# filter type of AP_FTYPE_RESOURCE would cause the
# filter to be placed *before* mod_deflate in the filter
# chain. Giving it a numeric value slightly higher than
# AP_FTYPE_CONTENT_SET will ensure that it is placed
# after mod_deflate.
ExtFilterDefine traceafter \
cmd="/bin/tracefilter.pl /tmp/traceafter" \
EnableEnv=trace_this_client ftype=21
<Directory /usr/local/docs>
SetEnvIf Remote_Addr 192.168.1.31 trace_this_client
SetOutputFilter tracebefore;deflate;traceafter
</Directory>