varnishでbackendのapacheにPOSTしているときにたまに(1/1000ぐらい)503 Service Unavailable になる現象はpassをpipeに変えたら出なくなった
これも同じような感じ?
backendの設定とbackendに投げる設定のvclはこんな感じ(抜粋)
- backend
probe healthcheck {
.url = "/index.html";
.interval = 30s;
.timeout = 10s;
.threshold = 3;
.window = 3;
.expected_response = 200;
}
backend apache1 {
.host = "192.168.0.1";
.port = "80";
.probe = healthcheck;
.connect_timeout = 60s;
.first_byte_timeout = 60s;
.between_bytes_timeout = 60s;
}
backend apache2 {
.host = "192.168.0.2";
.port = "80";
.probe = healthcheck;
.connect_timeout = 60s;
.first_byte_timeout = 60s;
.between_bytes_timeout = 60s;
}
director apache fallback {
{ .backend = apache1; }
{ .backend = apache2; }
}
- default.vcl
sub vcl_recv {
(中略)
if (req.url ~ "^/(foo|bar)") {
set req.backend = apache;
return (pass);
}
return (lookup);
}
で、このときに携帯からapacheへPOSTするときに1/1000 ぐらいの頻度で503になってた。そのときのvarnishlog を見ていると以下のようなものが流れている。varnishlog にはbackend write error と出ているが、backendのapacheのログにはerrorらしきものは見当たらない。
66 Hash c varnish.example.com 66 VCL_return c hash 66 VCL_call c pass pass 66 Backend c 25 apache apache1 66 FetchError c Resource temporarily unavailable 66 FetchError c backend write error: 11 (Resource temporarily unavailable) 66 VCL_call c error restart 66 VCL_call c recv pass 66 VCL_call c error deliver 66 VCL_call c deliver deliver 66 TxProtocol c HTTP/1.1 66 TxStatus c 503 66 TxResponse c Service Unavailable 66 TxHeader c Server: Varnish 66 TxHeader c Content-Type: text/html; charset=utf-8 66 TxHeader c Retry-After: 5 66 TxHeader c Content-Length: 366 66 TxHeader c Accept-Ranges: bytes 66 TxHeader c Date: Tue, 28 May 2013 04:38:12 GMT 66 TxHeader c X-Varnish: 1888567253
passとpipeの違い
xcirさんのvarnish cache 入門からの引用
pipe クライアントとバックエンド間のコネクションが閉じられるまで、継続的に スルーします。Varnish は内容に対する操作は行いませんし、キャッシュも 行いません。単純に右から左へ通信を中継するだけです。 pass Varnish はキャッシュしません。しかし、返却時にレスポンスヘッダに追加 で項目を加えるなどの操作は可能です。
curl などで見てみるとたしかにpassの場合はvarnishのヘッダが追加されている。
- pass の場合
$ curl -I http://varnish.example.com/foo/ HTTP/1.1 200 OK Server: Apache Content-Type: text/html Accept-Ranges: bytes Date: Tue, 28 May 2013 14:50:04 GMT X-Varnish: 1889133345 Age: 0 Via: 1.1 varnish Connection: keep-alive
- pipe の場合
$ curl -I http://varnish.example.com/foo/ HTTP/1.1 200 OK Date: Tue, 28 May 2013 14:51:56 GMT Server: Apache Connection: close Content-Type: text/html
追記
pipe を使うと、そのリクエストはvarnishncsa ログに記録されなくなっていることに気づいた。
tcpのコネクションを丸投げしてるだけでvarnishは何もしていないから?
というわけでログを残す必要がある場合はやっぱりpassを使わないといけない。