Fastlyのrequest conditionは最後にマッチしたconditionが適用される
Fastly で条件に応じて origin(backend) を切り替えたいときは request condition を設定することで実現できます。Request condition の挙動を勘違いしてハマったので、何を勘違いしてどう対応したのか紹介します。
Request condition⌗
Request condition には priority があり、default は 10 で、値が低いほど最初に評価されます。このとき、priority に関係なく、最終的にはすべての request condition が評価されます。以下のような request condition があるとします。
- Request condition 1
- priority: 10
- condition:
req.http.host == "foo.example.com" && req.url.path ~ "^/v2"
- backend:
bar.example.com
- Request condition 2
- priority: 20
- condition:
req.http.host == "foo.example.com"
- backend:
foo.example.com
この設定にすると foo.example.com/v2/ping
というリクエストのときは backend を bar.example.com
、foo.example.com/v1/ping
へのリクエストは backend を foo.example.com
にできると思っていたのですが、foo.example.com/v2/ping
の backend は foo.example.com
になっていました。これは、request condition は priority が低い順に評価されますが、条件にマッチしたら評価されなくなるわけではないためです。VCL としては以下のようになります。
# Request Condition: api_v2 Prio: 10
if( req.http.host == "foo.example.com" && req.url.path ~ "^/v2/" ) {
set req.backend = F_bar_example_com;
}
#end condition
# Request Condition: api_v1 Prio: 20
if( req.http.host == "foo.example.com") {
set req.backend = F_foo_example_com;
}
#end condition
このように if 文が request condition の数だけ生成されるので、priority の値が大きい condition にもマッチすれば backend はそれになります。 そのため、request condition を設定する際は、以下のいずれかの対応が必要です。
- 複数の request condition にマッチしないような条件を設定する
- priority を適切に設定し、複数の request condition にマッチしても意図した挙動になるようにする
Read other posts