Pass アクションの動作について

Pass 設定をリクエスト設定で行う場合とキャッシュ設定で行う場合では、Varnish の動作が大きく異なります。リクエスト設定で Pass を設定すると、VCL では vcl_recvreturn(pass) することになります。キャッシュ設定で Pass を設定すると、vcl_fetchreturn(pass) されます。 キャッシュ設定で Pass を行うのは、Varnish 3+ での return(hit_for_pass) と同じ動作となります。

リクエスト設定を使用する

リクエスト設定で Pass を設定すると、生成された VCL の vcl_recv 内で return(pass) に出力されます。Varnish は、オブジェクトがキャッシュにあるかどうかのルックアップを実行せず、オリジンからのレスポンスもキャッシュされません。

キャッシュ設定

この方法で Pass を行うと、リクエスト共有が無効になります。通常、同じオブジェクトへの同時リクエストでキャッシュミスが発生した場合、これらのリクエストはオリジンへの1つのリクエストとして束ねられます。最初のリクエストがオリジンに送信される間、そのオブジェクトに対する他のリクエストは、レスポンスを受信するまでキューに入れられます。リクエストが vcl_recv で Pass されると、それらのリクエストはすべて共有されることなく別々にオリジンに送信されます。

キャッシュ設定を使用する

キャッシュ設定で Pass を設定すると、生成された VCL の vcl_fetch 内で return(pass) に出力されます。リクエストフローのこの時点で Varnish はルックアップを実行し、オブジェクトがキャッシュにないと判断します。その後、オリジンへリクエストが送信されますが、vcl_fetch でレスポンスがキャッシュできないと判断されます。この動作は、Fastly のデフォルトの VCL では、オリジンからのレスポンスに Set-Cookie ヘッダーが存在する場合などに発生します。

キャッシュ設定

vcl_fetch での Pass は、リクエスト共有が無効にならないため、望ましくない場合がよくあります。これは、Varnish が vcl_recv の段階ではオブジェクトがキャッシュできないことを認識しないためです。後に vcl_fetch で Pass されるオブジェクトへの最初のリクエストでは、他のすべての同時キャッシュミスがキューに入れられます。オリジンからのレスポンスが受信され、リクエストが Pass されるべきであると Varnish が認識すると、キューに入れられたリクエストがオリジンに送信されます。

この場合、2人のユーザーが同時にオブジェクトをリクエストすると、1人のユーザーのリクエストが処理されるまで、もう一方のユーザーが待機する必要があります。これに対して、これらのリクエストが vcl_recv で Pass された場合、どちらのユーザーにも待ち時間は発生しません。

このデメリットを回避するために、リクエストが vcl_fetch で Pass されると、Varnish は hit-for-pass オブジェクトと呼ばれるものを作成します。これらのオブジェクトは独自の TTL を持ち、TTL が有効な間、Varnish はこれらに対するリクエストを vcl_recv で Pass されたかのように処理します。そのため、vcl_fetch で Pass を行う際には用途にあった TTL を設定することが重要です。そのオブジェクトに対する今後のすべてのリクエストは、hit-for-pass オブジェクトの TTL が期限切れになるまで Pass されます。Hit-for-pass オブジェクトも他のオブジェクトと同様にパージすることができます。

ただしこの機能があっても、同時に発生したリクエストがキューに入れられ、待ち時間が発生する場合があります。キャッシュ内に hit-for-pass オブジェクトがない場合、常にこれらのリクエストは通常のキャッシュミスのように扱われ、リクエスト共有が有効になります。できるだけ vcl_fetch で Pass するのを避けるようにしてください。

req.hash_always_miss と req.hash_ignore_busy の使用について

req.hash_always_miss を設定すると、キャッシュにあるかどうかに関わらず、リクエストが強制的にミスとなります。これはレスポンスがキャッシュされ、リクエストの共有が無効にならないという点で vcl_recv で Pass する場合と異なります。必要に応じて後でリクエストを vcl_fetch で Pass することもできます。

2つ目の関連する変数に があります。これを true に設定するとリクエスト共有が無効になり、各リクエストが個別にオリジンに送信されます。 が有効な場合、すべてのレスポンスがキャッシュされ、オリジンから受信した各レスポンスによって最後のレスポンスが上書きされます。キャッシュにあるオブジェクトに対する今後のリクエストは、その前のキャッシュミスで取得したオブジェクトのコピーを受け取ります。req.hash_ignore_busy は主に、複数の Varnish を利用した複雑な環境においてデッドロックを避ける目的で使用されます。

これらの両方の変数を利用することで、レスポンスをキャッシュしながら強制的にリクエストを個別にオリジンにオリジンに送信することが可能となります。

Back to Top