带有memcache,gunzip和ssi的Nginx不能一起工作

dem*_*101 5 memcached nginx ssi

我正在尝试在Memcached中保存packed(gzip)html并在nginx中使用:

  1. memcached模块加载来自memcached的html
  2. 如果打包,请通过nginx gunzip模块解压缩
  3. ssi模块处理ssi插入
  4. 将结果返回给用户

大多数情况下,配置工作,除了ssi步骤:

  location / {
    ssi on;
    set $memcached_key "$uri?$args";
    memcached_pass memcached.up;
    memcached_gzip_flag 2; #  net.spy.memcached use second byte for compression flag
    default_type text/html;
    charset utf-8;
    gunzip on;
    proxy_set_header Accept-Encoding "gzip";
    error_page  404 405 400 500 502 503 504 = @fallback;
  } 
Run Code Online (Sandbox Code Playgroud)

看起来,nginx在通过gunzip模块解压之前进行ssi处理.

在结果HTML中,我看到未解决的ssi指令:

<!--# include virtual="/remote/body?argument=value" -->
Run Code Online (Sandbox Code Playgroud)

nginx日志中没有错误.

尝试过ssi_types* - 没效果

知道怎么解决吗?

nginx 1.10.3(Ubuntu)

UPDATE

已经尝试了一个上游.相同的结果=(

在日志中,我看到,ssi过滤器在上游请求后应用,但没有检测到包含.

upstream memcached {
  server localhost:11211;
  keepalive 100;
}

upstream unmemcached {
  server localhost:21211;
  keepalive 100;
}

server {
  server_name dev.me;
  ssi_silent_errors off;
  error_log   /var/log/nginx/error1.log debug;    log_subrequest  on;
  location / {
    ssi on;
    ssi_types *;
    proxy_pass http://unmemcached;
    proxy_max_temp_file_size 0;
    proxy_http_version 1.1;
    proxy_set_header Connection "";
  }

  location @fallback {
    ssi on;
    proxy_pass http://proxy.site;
    proxy_max_temp_file_size 0;
    proxy_http_version 1.1;
    proxy_set_header Connection "";
    error_page 400 500 502 503 504  /offline.html;
  }
}

server {
  access_log  on;
  listen 21211;
  server_name unmemcached;
  error_log   /var/log/nginx/error2.log debug;    log_subrequest  on;

  location / {
    set $memcached_key "$uri?$args";
    memcached_pass memcached;
    memcached_gzip_flag 2;
    default_type text/html;
    charset utf-8;
    gunzip on;
    proxy_set_header Accept-Encoding "gzip";
    error_page  404 405 400 500 502 503 504 = @fallback;
  }

  location @fallback {
    #ssi on;
    proxy_pass http://proxy.site;
    proxy_max_temp_file_size 0;
    proxy_http_version 1.1;
    proxy_set_header Connection "";
    error_page 400 500 502 503 504  /offline.html;
  }

}
Run Code Online (Sandbox Code Playgroud)

如果可能的话,我想避免使用动态nginx模块的解决方案

cns*_*nst 0

基本上有两个问题需要考虑 \xe2\x80\x94 过滤器模块的顺序是否合适,以及gunzip 是否适合您的情况。

\n\n

0.gunzip/ssi/gzip的顺序。

\n\n

简单搜索“nginx order of filter module”就会发现,顺序是在编译时根据auto/modulesshell 脚本的内容确定的:

\n\n\n\n

快速浏览一下就会auto/modules发现ssi介于gzip和 之间gunzip,但是,并不能立即清楚模块的执行方式(从上到下或从下到上),因此,默认值可能是合理的,或者,您可能需要切换两者(恕我直言,这不一定受支持)。

\n\n

这里的一个提示是过滤器的位置,它作为上面 EMiller 指南中http_not_modified的处理示例给出;If-Modified-Since我想它必须放在最后,在所有其他的之后,如果是这样,那么,确实,gunzip/ssi/gzip 的顺序似乎与您需要的完全相反。

\n\n

1.gunzip 有用吗?

\n\n

根据http://nginx.org/r/gunzip,过滤器的文档中存在以下文本:

\n\n
\n

为缺乏 gzip 支持的客户端启用或禁用 gzip 响应的解压缩。

\n
\n\n

尚不完全清楚上述语句是否应被解释为模块的描述(例如,缺少 gzip 支持的客户端是您可能想要使用此模块的原因),或者它是否是行为的描述(例如,模块是否自行确定客户端是否支持gzip)。src/http/modules/ngx_http_gunzip_filter_module.c的源代码似乎暗示它只是检查Content-Encoding回复的 是否为gzip,如果是则继续。然而,文档中的下一句话(在上面引用的句子之后)似乎表明它与模块有更多的交互gzip,因此,也许还涉及其他内容。

\n\n

我的猜测是,如果您使用浏览器进行测试,那么浏览器确实支持 gzip,因此,不gunzip参与是合理的,因此,SSI 模块永远不会有任何有效的处理。这就是为什么我建议您确定 Gunzip 是否正常工作和/或通过执行简单的纯文本请求curl与浏览器使用Accept-Encoding包含gzip.

\n\n

解决方案。

\n\n

根据上述调查的结果,我会尝试确定模块的顺序,如果不正确,则可以选择重新编译或双重代理作为解决方案。

\n\n

随后,如果问题仍然没有解决,我将确保gunzip过滤器无条件地对来自 ; 的数据进行解压memcached。我想您可能必须忽略或重置Accept-Encoding标题或类似内容。

\n