1

I am using Nginx's proxy cache for our dynamic pages and have recently integrated ssi. The first page load works fine but once the page is cached and another request comes through the page just hangs.

The logs seem to indicate multiple sub-requests being made (there is only one directive, and in the layout) and I'm not really sure why this is happening. The page loads fine on first load, the cached version spins its wheels and breaks down. Here is my config.

proxy_cache_path  /var/cache/nginx levels=1:2 keys_zone=one:8m max_size=500m inactive=60m; #caching
proxy_temp_path /var/tmp; #caching

gzip_comp_level 6;
gzip_vary on;
gzip_min_length  1000;
gzip_proxied any;
gzip_types text/plain text/css application/json application/x-javascript text/xml application/xml application/xml+rss text/javascript;
gzip_buffers 16 8k;

upstream staging {
  server 127.0.0.1:1337;
}

server {
  listen 0.0.0.0:80;
  server_name dev.example.com;
  access_log /var/log/nginx/dev.example.log;
  error_log  /var/log/nginx/dev.example.error.log debug;   log_subrequest on;

  location ~ ^/(images/|scripts/|styles/|robots.txt|humans.txt|favicon.ico) { #caching
    root /home/example/app/website/public;
    access_log off;
    expires modified +1h;
  }

  location / {
    ssi on;

    proxy_redirect off;
    proxy_set_header X-Real-IP $remote_addr;
    proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
    proxy_set_header Host $http_host;
    proxy_set_header X-NginX-Proxy true;

    proxy_cache one; #caching
    proxy_cache_key sfs$request_uri$scheme; #caching

    proxy_http_version 1.1;
    proxy_pass http://staging/; #points to the upstream staging
  }
}

And this is the directive that is in the layout

<!--# include virtual="/ssi/dynamic-content" -->

-- EDIT --

I just noticed that the page layout seems to be rendering multiple times too. The ssi request returns no markup other than a div, I am not sure why the whole layout would be inserted multiple times.

-- EDIT 2 --

I don't know why this works, but I was able to fix this issue by moving the ssi requests outside of the location / {} block and into they're own which skips the caching settings and goes directly to the server. My config now looks like this.

proxy_cache_path  /var/cache/nginx levels=1:2 keys_zone=one:8m max_size=500m inactive=60m; #caching
proxy_temp_path /var/tmp; #caching

gzip_comp_level 6;
gzip_vary on;
gzip_min_length  1000;
gzip_proxied any;
gzip_types text/plain text/css application/json application/x-javascript text/xml application/xml application/xml+rss text/javascript;
gzip_buffers 16 8k;

upstream staging {
  server 127.0.0.1:1337;
}

server {
  listen 0.0.0.0:80;
  server_name dev.example.com;
  access_log /var/log/nginx/dev.example.log;
  error_log  /var/log/nginx/dev.example.error.log debug;   log_subrequest on;

  location ~ ^/(images/|scripts/|styles/|robots.txt|humans.txt|favicon.ico) { #caching
    root /home/example/app/website/public;
    access_log off;
    expires modified +1h;
  }

  #New proxy block specifically for ssi routes
  location /ssi {
    proxy_pass http://staging;
  }

  location / {
    ssi on;

    proxy_redirect off;
    proxy_set_header X-Real-IP $remote_addr;
    proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
    proxy_set_header Host $http_host;
    proxy_set_header X-NginX-Proxy true;

    proxy_cache one; #caching
    proxy_cache_key sfs$request_uri$scheme; #caching

    proxy_http_version 1.1;
    proxy_pass http://staging/; #points to the upstream staging
  }
}

After more investigation the problem seemed to be the page was literally inserting itself repeatedly into the ssi include. Almost as if the include was including the whole page, which had an include as well, and continued to include new markup recursively.

I think that by moving ssi requests outside of the caching block setting this was mitigated but I am not entirely sure why.

George
  • 123
  • 5

1 Answers1

0

I discovered the answer.

In the previous config I had caching set for $request_uri. That means nginx will file and fetch caches based on the incoming request. The server side include makes another request but since caching is based on the incoming uri it ends up fetching the main page itself, thus inserting itself repeatedly.

By using $uri instead of $request_uri nginx will respect rewrites and ssi requests thus caching and fetching via appropriate namespaces (in this case the app's defined ssi routes).

Here is more info on nginx's variables

George
  • 123
  • 5