Nginx 与 wordpress 拒绝 varnish 静态内容请求

Nginx 与 wordpress 拒绝 varnish 静态内容请求

我刚刚向我的 ubuntu 服务器添加了另一个 wordpress 站点。2 个 wordpress 站点,不是多站点。

它们使用 2 个不同的 fpm 池,配置相同。它们的 Nginx 配置文件基本相同,只是 fpm 套接字名称和监听的 ip 端口不同。

网站 A 一切正常。网站 B(新安装的网站,全新安装)的所有静态文件(例如 js、css、png 等)均出现 503 错误

Php 和 Nginx 错误日志显示此问题没有错误。

确认 varnish 和 nginx 已相互连接(至少对于 php 而言)。事实上,站点 B 可以显示 wordpress hello world 博客文章。确认 varnish 确实向正确的 nginx 后端发出了请求。

停止 varnish 并单独使用 nginx。站点 B 在加载所有静态内容后运行正常!但是,在重新打开 varnish 后,静态文件仍然会出现 503 错误。

请帮忙。

$curl 127.0.0.1:80/robots.txt
// return correct files from site A


$curl 127.0.0.2:80/robots.txt
// return 503

$ sudo netstat -anp | grep varnish
[sudo] password for tangrufus:
tcp        0      0 127.0.0.1:6082          0.0.0.0:*               LISTEN      1765/varnishd
tcp        0      0 0.0.0.0:80              0.0.0.0:*               LISTEN      1766/varnishd
tcp        0      0 127.0.0.1:46727         127.0.0.2:8080          ESTABLISHED 1766/varnishd
tcp        0      0 127.0.0.1:33175         127.0.0.1:8080          ESTABLISHED 1766/varnishd
tcp6       0      0 :::80                   :::*                    LISTEN      1766/varnishd
unix  2      [ ]         DGRAM                    11594    1765/varnishd

$ sudo netstat -anp | grep nginx
tcp        0      0 127.0.0.2:8080          0.0.0.0:*               LISTEN      1960/nginx
tcp        0      0 127.0.0.1:8080          0.0.0.0:*               LISTEN      1960/nginx
tcp        0      0 127.0.0.1:8080          127.0.0.1:33240         ESTABLISHED 1963/nginx: worker
unix  3      [ ]         STREAM     CONNECTED     12812    1960/nginx
unix  3      [ ]         STREAM     CONNECTED     12811    1960/nginx



    server { 
    // Default server block blacklisting all unconfigured access
    listen 127.0.0.2:8080 default_server;
    server_name _;
    return 444;
    }

    server {
    // Configure the domain that will run WordPress
    server_name siteB.com image.siteB.com 127.0.0.2;
    listen 127.0.0.2:8080 deferred;

    error_log   /var/log/nginx/siteB.com.error.log;
    access_log /var/log/nginx/siteB.com.access.log;


    // WordPress needs to be in the webroot of /var/www/ in this case
    root        /var/www/siteB.com/htdocs;

    // pass PHP scripts to Fastcgi listening on Unix socket
    // Do not process them if inside WP uploads directory
    // If using Multisite or a custom uploads directory,
    // please set the */uploads/* directory in the regex below
    location ~* (^(?!(?:(?!(php|inc)).)*/uploads/).*?(php)) {
        try_files $uri = 404;
        fastcgi_split_path_info ^(.+.php)(.*)$;
        fastcgi_pass unix:/var/run/siteB.php5-fpm.sock;
        fastcgi_index index.php;
        fastcgi_param SCRIPT_FILENAME $document_root$fastcgi_script_name;
        include fastcgi_params;
        fastcgi_intercept_errors on;
        fastcgi_ignore_client_abort off;
        fastcgi_connect_timeout 60;
        fastcgi_send_timeout 180;
        fastcgi_read_timeout 180;
        fastcgi_buffer_size 128k;
        fastcgi_buffers 4 256k;
        fastcgi_busy_buffers_size 256k;
        fastcgi_temp_file_write_size 256k;
    }

    location ^~ /nocache/ {
        fastcgi_pass unix:/var/run/tangr.php5-fpm.sock;
        fastcgi_index index.php;
        fastcgi_param  SCRIPT_FILENAME $document_root$fastcgi_script_name;
        include fastcgi_params;
        access_log   off;
        allow 127.0.0.1;
    allow 127.0.0.2;
        deny all;
    }

    location ^~ /nocache/fpm_status {
     access_log off;
     include fastcgi_params;
     fastcgi_pass unix:/var/run/siteB.php5-fpm.sock;
    }


    include sites-available/global/common.conf;
    }

// Redirect all www. queries to non-www
// Change in case your site is to be available at "www.yourdomain.tld"
server {
    listen 127.0.0.2:8080;
    server_name www.siteB.com;
    rewrite ^ $scheme://siteB.com$request_uri? permanent;
}

Varnish 配置

import std;

include "lib/xforward.vcl";
include "lib/cloudflare.vcl";
include "lib/purge.vcl";
include "lib/bigfiles.vcl";        // Varnish 3.0.3+
//include "lib/bigfiles_pipe.vcl";  // Varnish 3.0.2
include "lib/static.vcl";

backend siteA {
    .host = "127.0.0.1";
    .port = "8080";
    .max_connections = 250;
    .connect_timeout = 4.0s;
    .first_byte_timeout = 600s;
    .between_bytes_timeout = 600s;
}

backend siteB {
    .host = "127.0.0.2";
    .port = "8080";
    .max_connections = 250;
    .connect_timeout = 4.0s;
    .first_byte_timeout = 600s;
    .between_bytes_timeout = 600s;
}

acl cloudflare {
    // set this ip to your Railgun IP (if applicable)
    // "1.2.3.4";
    "108.162.196.62";
    "108.162.197.62";
}

// Only allow purging from specific IPs
acl purge {
    "localhost";
    "127.0.0.1";
    "127.0.0.2";
}

// Pick just one of the following:
// (or don't use either of these if your application is "adaptive")
// include "lib/mobile_cache.vcl";
// include "lib/mobile_pass.vcl";

////// WordPress-specific config //////
// This config was initially derived from the work of Donncha Ó Caoimh:
// http://ocaoimh.ie/2011/08/09/speed-up-wordpress-with-apache-and-varnish/
sub vcl_recv {
    if (! req.http.Host) {
        error 404 "Need a host header";
    }

    // Let Nginx deal with 301 www to non-www redirect
    // set req.http.Host = regsub(req.http.Host, "^www\.", "");

    set req.http.Host = regsub(req.http.Host, ":80$", "");

    if ( req.http.host ~ "^(www\.)?siteA\.com$" ) {
        set req.backend = siteA;
    }
        else if ( req.http.host ~ "127\.0\.0\.1$" ) {
                set req.backend = siteA;
        }
    else if ( req.http.host ~ "^(www\.)?siteB\.com$" ) {
        set req.backend = siteB;
    }
        else if ( req.http.host ~ "127\.0\.0\.2$" ) {
                set req.backend = siteB;
        }
    else {
        error 503 "Service Unavailable";
    }

    // pipe on weird http methods
    if (req.request !~ "^GET|HEAD|PUT|POST|TRACE|OPTIONS|DELETE$") {
        return(pipe);
    }

    // Handle compression correctly. Different browsers send different
    // "Accept-Encoding" headers, even though they mostly support the same
    // compression mechanisms. By consolidating compression headers into
    // a consistent format, we reduce the cache size and get more hits.
    // @see: http:// varnish.projects.linpro.no/wiki/FAQ/Compression

    if (req.http.Accept-Encoding) {
        if (req.http.Accept-Encoding ~ "gzip") {
            // If the browser supports it, we'll use gzip.
            set req.http.Accept-Encoding = "gzip";
        }
        else if (req.http.Accept-Encoding ~ "deflate") {
            // Next, try deflate if it is supported.
            set req.http.Accept-Encoding = "deflate";
        }
        else {
            // Unknown algorithm. Remove it and send unencoded.
            unset req.http.Accept-Encoding;
        }
    }

    ////// Check for reasons to bypass the cache!
    // never cache anything except GET/HEAD
    if (req.request != "GET" && req.request != "HEAD") {
        return(pass);
    }
    // don't cache logged-in users or authors
    if (req.http.Cookie ~ "wp-postpass_|wordpress_logged_in_|comment_author|PHPSESSID") {
        return(pass);
    }
    // don't cache ajax requests
    if (req.http.X-Requested-With == "XMLHttpRequest") {
        return(pass);
    }
    // don't cache these special pages
    if (req.url ~ "nocache|wp-admin|wp-(comments-post|login|activate|mail)\.php|bb-admin|server-status|control\.php|bb-login\.php|bb-reset-password\.php|register\.php") {
        return(pass);
    }

    // Do not cache these paths
    if (req.url ~ "^/wp-cron\.php$" ||
        req.url ~ "^/xmlrpc\.php$" ||
        req.url ~ "^/wp-admin/.*$" ||
        req.url ~ "^/wp-includes/.*$" ||
        req.url ~ "\?s=") {
        return (pass);
    }

    ////// looks like we might actually cache it!
    // fix up the request
    // Define the default grace period to serve cached content
    if (req.backend.healthy) {
        set req.grace = 30s;
        } else {
            set req.grace = 1h;
        }

        set req.url = regsub(req.url, "\?replytocom=.*$", "");

        // Remove has_js, Google Analytics __*, and wooTracker cookies.
        set req.http.Cookie = regsuball(req.http.Cookie, "(^|;\s*)(__[a-z]+|has_js|wooTracker)=[^;]*", "");
        set req.http.Cookie = regsub(req.http.Cookie, "^;\s*", "");
        if (req.http.Cookie ~ "^\s*$") {
            unset req.http.Cookie;
        }

        return(lookup);
    }

    sub vcl_hash {
        // Add the browser cookie only if a WordPress cookie found.
        if (req.http.Cookie ~ "wp-postpass_|wordpress_logged_in_|comment_author|PHPSESSID") {
            hash_data(req.http.Cookie);
        }
    }

    sub vcl_fetch {
        // remove some headers we never want to see
        unset beresp.http.Server;
        unset beresp.http.X-Powered-By;

        // Drop any cookies WordPress tries to send back to the client.
        if (!(req.url ~ "wp-(login|admin)")) {
            unset beresp.http.set-cookie;
        }

        // make sure grace is at least 2 minutes
        if (req.backend.healthy) {
            set req.grace = 30s;
            } else {
                set req.grace = 1h;
            }

            // catch obvious reasons we can't cache
            if (beresp.http.Set-Cookie) {
                set beresp.ttl = 0s;
            }

            // only allow cookies to be set if we're in admin area
            if( beresp.http.Set-Cookie && req.url !~ "^/wp-(login|admin)" ){
                set beresp.ttl = 0s;
                unset beresp.http.Set-Cookie;
            }

            // Varnish determined the object was not cacheable
            if (beresp.ttl <= 0s) {
                set beresp.http.X-Cacheable = "NO:Not Cacheable";
                return(hit_for_pass);

                // You don't wish to cache content for logged in users
                } else if (req.http.Cookie ~ "wp-postpass_|wordpress_logged_in_|comment_author|PHPSESSID") {
                    set beresp.http.X-Cacheable = "NO:Got Session";
                    return(hit_for_pass);

                     You are respecting the Cache-Control=private header from the backend
                    } else if (beresp.http.Cache-Control ~ "private") {
                        set beresp.http.X-Cacheable = "NO:Cache-Control=private";
                        return(hit_for_pass);

                        // don't cache response to posted requests or those with basic auth
                        } else if ( req.request == "POST" || req.http.Authorization ) {
                            return (hit_for_pass);

                            // don't cache search results
                            } else if( req.url ~ "\?s=" ){
                                return (hit_for_pass);

                                // You are extending the lifetime of the object artificially
                                } else if (beresp.ttl < 300s) {
                                    set beresp.ttl   = 300s;
                                    set beresp.grace = 300s;
                                    set beresp.http.X-Cacheable = "YES:Forced";

                                    // Varnish determined the object was cacheable
                                    } else {
                                        set beresp.http.X-Cacheable = "YES";
                                    }

                                    // Avoid caching error responses
                                    if (beresp.status == 404 || beresp.status >= 500) {
                                        set beresp.ttl   = 0s;
                                        set beresp.grace = 15s;
                                    }

                                    // GZip the cached content if possible
                                    if (beresp.http.content-type ~ "text") {
                                        set beresp.do_gzip = true;
                                    }

                                    // if nothing abovce matched it is now ok to cache the response
                                    // Deliver the content
                                    return (deliver);

                                }

相关内容