ワニスの ESI は、指定した URL に接続しないという点で、ブラウザーの iframe やリンク タグのようには機能しません。ESI は varnish 内で新しいリクエストを開始し、ワークフロー (vcl_recv など) を通過します。
varnish が http クライアントのように動作し、URL を解析し、認証ヘッダーを設定し、ホスト ヘッダーを api.dev:8081 に設定し、新しい http 接続/要求を開始することを期待していますが、そうではありません。この場合、req.url を /app.php/next に設定して新しい req を開始し、親リソース (esi タグを含む) の要求からヘッダーを継承するか、esi タグを完全に無視する可能性があると思います。
あなたがやりたいことを達成する方法は(vcl_recvで)です:
if (req.esi_level > 0 && req.url == "/app.php/next") {
set req.http.Authorization = "BASIC [base64 encoded admin:adminpass]"
return (pass);
}
esiタグは次のようになります<esi:include src="/app.php/next" />
ESI リクエストを別のバックエンド サーバーにヒットさせる必要がある場合は、そのサーバーを別の名前のバックエンドとして追加する必要があります。
backend authorization_needed {
.host = "api.dev";
.port = "8081";
}
vcl_recv で、esi リクエストに使用するように varnish に指示します。
if (req.esi_level > 0 && req.url == "/app.php/next") {
set req.http.Authorization = "BASIC [base64 encoded admin:adminpass]"
set req.backend = authorization_needed;
return (pass);
}
バックエンドが「api.dev」とは異なる仮想ホストに応答する場合は、if ブロックに req.http.Host を設定する必要がある場合もあります。
アップデート:
基本認証はクライアントから送信され、req.http.Authorization が存在するときに return (pass) を呼び出しているため、varnish はこれらのページを ESI 処理しません。渡すときに呼び出されない vcl_fetch() で esi を明示的に有効にする必要があります。
したがって、親ページではなく ESI フラグメントの認証を渡すには、vcl_rev を次のように変更します。
if (req.http.Authorization && req.esi_level == 0) {
set req.http.X-Esi-Authorization = req.http.Authorization;
unset req.http.Authorization;
}
else if (req.http.X-Esi-Authorization && req.esi_level > 0 ) {
set req.http.Authorization = req.http.X-Esi-Authorization;
return (pass);
}
そして vcl_fetch に追加します:
if (req.http.X-Esi-Authorization) {
set beresp.do_esi = true;
}
最終的な効果は、親の応答がキャッシュ可能であり、esi を処理することです。esi フラグメント自体は常にクライアントの認証ヘッダーと共にバックエンドに渡されます。