Azure Application Gateway for Containers の URL のリダイレクト - Gateway API
Application Gateway for Containers を使用すると、URL の 3 つの側面 (プロトコル、ホスト名、パス) に基づいてリダイレクト応答をクライアントに返すことができます。 リダイレクトごとに定義済みの HTTP 状態コードをクライアントに返して、リダイレクトの性質を定義することがあります。
Usage details
URL のリダイレクトでは、Kubernetes Gateway API で定義される RequestRedirect ルール フィルターを利用します。
リダイレクト
リダイレクトにより、リダイレクトの目的を理解するためにクライアントに返される応答の状態コードが設定されます。 次の種類のリダイレクトがサポートされています。
- 301 (永続的に移動): ターゲット リソースに新しい永続的な URI が割り当てられていることを示します。 このリソースへの今後の参照では、囲まれた URI のいずれかが使用されます。 状態コード 301 は HTTP から HTTPS へのリダイレクトに使用します。
- 302 (検出) :ターゲット リソースが一時的に別の URI に存在することを示します。 リダイレクトは場合によっては変更される可能性があるため、クライアントは今後の要求のために有効な要求 URI を引き続き使用する必要があります。
リダイレクト機能
プロトコル リダイレクトは、暗号化されていないトラフィック スキームからトラフィックに移動する (HTTP から HTTPS へのリダイレクトなど) ようにクライアントに指示するためによく使用されます。
ホスト名のリダイレクトが要求の完全修飾ドメイン名 (FQDN) と一致します。 これは、古いドメイン名を新しいドメイン名に リダイレクトする (
contoso.com
からfabrikam.com
など) 際によく見られます。パスのリダイレクトには、
prefix
とfull
という 2 種類のバリアントがあります。- リダイレクトの種類の
Prefix
は、定義された値で始まるすべての要求をリダイレクトします。 たとえば、/shop のプレフィックスは、/shop とその後に続く任意のテキストと一致します。 たとえば、/shop、/shop/checkout、/shop/item-a はすべて /shop にもリダイレクトします。 - リダイレクトの種類の
Full
は正確な値と一致します。 たとえば、/shop は /store にリダイレクトできますが、/shop/checkout は /store にリダイレクトしません。
- リダイレクトの種類の
次の図は、contoso.com/summer-promotion 向けの要求が contoso.com/shop/category/5 にリダイレクトされる例を示しています。 さらに、http プロトコルを介して contoso.com 向けに開始された 2 つ目の要求は、その https バリアントへの新しい接続を開始するためにリダイレクトを返します。
前提条件
BYO デプロイ戦略に従う場合は、Application Gateway for Containers リソースと ALB コントローラーを設定していることを確認します。
ALB マネージド デプロイ戦略に従う場合は、ALB コントローラーのプロビジョニングと、ApplicationLoadBalancer カスタム リソースを介した Application Gateway for Containers リソースのプロビジョニングが完了していることを確認します。
サンプル HTTP アプリケーションをデプロイする:
クラスターに次の deployment.yaml ファイルを適用して、リダイレクト機能を示すサンプル TLS 証明書をデプロイします。
kubectl apply -f https://trafficcontrollerdocs.blob.core.windows.net/examples/https-scenario/ssl-termination/deployment.yaml
このコマンドによって、クラスターに次のものが作成されます。
test-infra
と呼ばれる名前空間test-infra
名前空間内のecho
という 1 つのサービスtest-infra
名前空間にecho
と呼ばれる 1 つのデプロイtest-infra
名前空間にlistener-tls-secret
と呼ばれる 1 つのシークレット
必要な Gateway API リソースをデプロイする
ゲートウェイを作成する
kubectl apply -f - <<EOF apiVersion: gateway.networking.k8s.io/v1 kind: Gateway metadata: name: gateway-01 namespace: test-infra annotations: alb.networking.azure.io/alb-namespace: alb-test-infra alb.networking.azure.io/alb-name: alb-test spec: gatewayClassName: azure-alb-external listeners: - name: http-listener port: 80 protocol: HTTP allowedRoutes: namespaces: from: Same - name: https-listener port: 443 protocol: HTTPS allowedRoutes: namespaces: from: Same tls: mode: Terminate certificateRefs: - kind : Secret group: "" name: listener-tls-secret EOF
Note
ALB コントローラーは、ARM で Application Gateway for Containers リソースを作成するときに、フロントエンド リソースに対して次の名前付け規則を使用します。fe-<ランダムに生成された 8 文字>
Azure で作成されたフロントエンドの名前を変更したい場合は、BYO デプロイ戦略に従うことを検討してください。
ゲートウェイ リソースが作成されたら、状態が有効であること、リスナーが [プログラム済み] であること、ゲートウェイにアドレスが割り当てられていることを確認します。
kubectl get gateway gateway-01 -n test-infra -o yaml
ゲートウェイの作成に成功した出力例。
status:
addresses:
- type: Hostname
value: xxxx.yyyy.alb.azure.com
conditions:
- lastTransitionTime: "2023-06-19T21:04:55Z"
message: Valid Gateway
observedGeneration: 1
reason: Accepted
status: "True"
type: Accepted
- lastTransitionTime: "2023-06-19T21:04:55Z"
message: Application Gateway For Containers resource has been successfully updated.
observedGeneration: 1
reason: Programmed
status: "True"
type: Programmed
listeners:
- attachedRoutes: 0
conditions:
- lastTransitionTime: "2023-06-19T21:04:55Z"
message: ""
observedGeneration: 1
reason: ResolvedRefs
status: "True"
type: ResolvedRefs
- lastTransitionTime: "2023-06-19T21:04:55Z"
message: Listener is accepted
observedGeneration: 1
reason: Accepted
status: "True"
type: Accepted
- lastTransitionTime: "2023-06-19T21:04:55Z"
message: Application Gateway For Containers resource has been successfully updated.
observedGeneration: 1
reason: Programmed
status: "True"
type: Programmed
name: https-listener
supportedKinds:
- group: gateway.networking.k8s.io
kind: HTTPRoute
https 経由で受信したトラフィックを処理する contoso.com
用の HTTPRoute リソースを作成します。
kubectl apply -f - <<EOF
apiVersion: gateway.networking.k8s.io/v1
kind: HTTPRoute
metadata:
name: https-contoso
namespace: test-infra
spec:
parentRefs:
- name: gateway-01
sectionName: https-listener
hostnames:
- "contoso.com"
rules:
- backendRefs:
- name: echo
port: 80
EOF
HTTPRoute リソースが作成されたら、HTTPRoute リソースに [承認済み] と表示され、Application Gateway for Containers リソースが [プログラム済み] になっていることを確認します。
kubectl get httproute rewrite-example -n test-infra -o yaml
各 HTTPRoute で Application Gateway for Containers リソースが正常に更新されたことを確認します。
status:
parents:
- conditions:
- lastTransitionTime: "2023-06-19T22:18:23Z"
message: ""
observedGeneration: 1
reason: ResolvedRefs
status: "True"
type: ResolvedRefs
- lastTransitionTime: "2023-06-19T22:18:23Z"
message: Route is Accepted
observedGeneration: 1
reason: Accepted
status: "True"
type: Accepted
- lastTransitionTime: "2023-06-19T22:18:23Z"
message: Application Gateway For Containers resource has been successfully updated.
observedGeneration: 1
reason: Programmed
status: "True"
type: Programmed
controllerName: alb.networking.azure.io/alb-controller
parentRef:
group: gateway.networking.k8s.io
kind: Gateway
name: gateway-01
namespace: test-infra
ゲートウェイが作成されたら、http トラフィックを https にリダイレクトする RequestRedirect フィルターを使用して、contoso.com
用の HTTPRoute リソースを作成します。
kubectl apply -f - <<EOF
apiVersion: gateway.networking.k8s.io/v1
kind: HTTPRoute
metadata:
name: http-to-https-contoso-redirect
namespace: test-infra
spec:
parentRefs:
- name: gateway-01
sectionName: http-listener
hostnames:
- "contoso.com"
rules:
- matches:
filters:
- type: RequestRedirect
requestRedirect:
scheme: https
statusCode: 301
EOF
HTTPRoute リソースが作成されたら、HTTPRoute リソースに [承認済み] と表示され、Application Gateway for Containers リソースが [プログラム済み] になっていることを確認します。
kubectl get httproute rewrite-example -n test-infra -o yaml
各 HTTPRoute で Application Gateway for Containers リソースが正常に更新されたことを確認します。
status:
parents:
- conditions:
- lastTransitionTime: "2023-06-19T22:18:23Z"
message: ""
observedGeneration: 1
reason: ResolvedRefs
status: "True"
type: ResolvedRefs
- lastTransitionTime: "2023-06-19T22:18:23Z"
message: Route is Accepted
observedGeneration: 1
reason: Accepted
status: "True"
type: Accepted
- lastTransitionTime: "2023-06-19T22:18:23Z"
message: Application Gateway For Containers resource has been successfully updated.
observedGeneration: 1
reason: Programmed
status: "True"
type: Programmed
controllerName: alb.networking.azure.io/alb-controller
parentRef:
group: gateway.networking.k8s.io
kind: Gateway
name: gateway-01
namespace: test-infra
/summer-promotion のパスの特定の URL へのリダイレクトを処理する contoso.com
用の HTTPRoute リソースを作成します。 http から https への HTTPRoute リソースに示されている sectionName を削除することで、このリダイレクト規則は HTTP 要求と HTTPS 要求の両方に適用されます。
kubectl apply -f - <<EOF
apiVersion: gateway.networking.k8s.io/v1
kind: HTTPRoute
metadata:
name: summer-promotion-redirect
namespace: test-infra
spec:
parentRefs:
- name: gateway-01
sectionName: https-listener
hostnames:
- "contoso.com"
rules:
- matches:
- path:
type: PathPrefix
value: /summer-promotion
filters:
- type: RequestRedirect
requestRedirect:
path:
type: ReplaceFullPath
replaceFullPath: /shop/category/5
statusCode: 302
- backendRefs:
- name: echo
port: 80
EOF
HTTPRoute リソースが作成されたら、HTTPRoute リソースに [承認済み] と表示され、Application Gateway for Containers リソースが [プログラム済み] になっていることを確認します。
kubectl get httproute rewrite-example -n test-infra -o yaml
各 HTTPRoute で Application Gateway for Containers リソースが正常に更新されたことを確認します。
status:
parents:
- conditions:
- lastTransitionTime: "2023-06-19T22:18:23Z"
message: ""
observedGeneration: 1
reason: ResolvedRefs
status: "True"
type: ResolvedRefs
- lastTransitionTime: "2023-06-19T22:18:23Z"
message: Route is Accepted
observedGeneration: 1
reason: Accepted
status: "True"
type: Accepted
- lastTransitionTime: "2023-06-19T22:18:23Z"
message: Application Gateway For Containers resource has been successfully updated.
observedGeneration: 1
reason: Programmed
status: "True"
type: Programmed
controllerName: alb.networking.azure.io/alb-controller
parentRef:
group: gateway.networking.k8s.io
kind: Gateway
name: gateway-01
namespace: test-infra
アプリケーションへのアクセスをテストする
これで、フロントエンドに割り当てられた FQDN を使用して、サンプル アプリケーションにトラフィックを送信する準備ができました。 次のコマンドを実行して、FQDN を取得します。
fqdn=$(kubectl get gateway gateway-01 -n test-infra -o jsonpath='{.status.addresses[0].value}')
curl コマンドを使用してサーバー名インジケーターを指定すると、http://contoso.com
は location
ヘッダーが https://contoso.com
への 301 リダイレクトを定義する Application Gateway for Containers からの応答を返す必要があります。
fqdnIp=$(dig +short $fqdn)
curl -k --resolve contoso.com:80:$fqdnIp http://contoso.com/ -v
応答を介して、次の内容が表示されます。
* Added contoso.com:80:xxx.xxx.xxx.xxx to DNS cache
* Hostname contoso.com was found in DNS cache
* Trying xxx.xxx.xxx.xxx:80...
* Connected to contoso.com (xxx.xxx.xxx.xxx) port 80 (#0)
> GET / HTTP/1.1
> Host: contoso.com
> User-Agent: curl/7.81.0
> Accept: */*
>
* Mark bundle as not supporting multiuse
< HTTP/1.1 301 Moved Permanently
< location: https://contoso.com/
< date: Mon, 26 Feb 2024 22:56:23 GMT
< server: Microsoft-Azure-Application-LB/AGC
< content-length: 0
<
* Connection #0 to host contoso.com left intact
curl コマンドを使用してサーバー名インジケーターを指定すると、https://contoso.com/summer-promotion
Application Gateway for Containers は https://contoso.com/shop/category/5
への 302 リダイレクトを返す必要があります。
fqdnIp=$(dig +short $fqdn)
curl -k --resolve contoso.com:443:$fqdnIp https://contoso.com/summer-promotion -v
応答を介して、次の内容が表示されます。
> GET /summer-promotion HTTP/2
> Host: contoso.com
> user-agent: curl/7.81.0
> accept: */*
>
* TLSv1.2 (IN), TLS header, Supplemental data (23):
* TLSv1.3 (IN), TLS handshake, Newsession Ticket (4):
* TLSv1.3 (IN), TLS handshake, Newsession Ticket (4):
* old SSL session ID is stale, removing
* TLSv1.2 (IN), TLS header, Supplemental data (23):
* TLSv1.2 (OUT), TLS header, Supplemental data (23):
* TLSv1.2 (IN), TLS header, Supplemental data (23):
< HTTP/2 302
< location: https://contoso.com/shop/category/5
< date: Mon, 26 Feb 2024 22:58:43 GMT
< server: Microsoft-Azure-Application-LB/AGC
<
* Connection #0 to host contoso.com left intact
これで、ALB コントローラーをインストールし、バックエンド アプリケーションをデプロイし、Gateway API を使用して、HTTP から HTTPS へのリダイレクトと特定のクライアント要求へのパス ベースのリダイレクトの両方を構成しました。