HTTPエグレス トラフィックの監視とアクセスポリシー
HTTPエグレス トラフィックの監視とアクセスポリシーのために Istio を設定する方法について説明します。
Istio の主な焦点は、サービスメッシュ内のマイクロサービス間のトラフィック管理ですが、Istio はイングレス (外部からメッシュへのトラフィック) およびエグレス (メッシュから外部へのトラフィック) のトラフィックも管理できます。Istio は、メッシュ内部、イングレス、およびエグレス トラフィックに対して、アクセスポリシーを一貫して適用し、テレメトリーデータを集約できます。
このブログ記事では、Istio を使用して HTTP エグレス トラフィックに監視とアクセスポリシーを適用する方法を示します。
ユースケース
cnn.com からのコンテンツを処理するアプリケーションを実行している組織を考えてみましょう。アプリケーションは、Istio サービスメッシュにデプロイされたマイクロサービスに分解されています。アプリケーションは、cnn.com からさまざまなトピックのページにアクセスします: edition.cnn.com/politics、edition.cnn.com/sport、および edition.cnn.com/health。この組織は、Istio を設定して edition.cnn.com へのアクセスを許可しており、すべて正常に機能しています。しかし、ある時点で、組織は政治関連のコンテンツを禁止することにしました。実際には、edition.cnn.com/politics へのアクセスをブロックし、edition.cnn.com/sport および edition.cnn.com/health へのアクセスのみを許可することを意味します。組織は、edition.cnn.com/politics へのアクセスを、個々のアプリケーションおよび特定のユーザーにケースバイケースで許可します。
その目標を達成するために、組織の運用担当者は、外部サービスへのアクセスを監視し、Istio のログを分析して、承認されていないリクエストが edition.cnn.com/politics に送信されていないことを確認します。また、edition.cnn.com/politics へのアクセスを自動的に防ぐように Istio を設定します。
組織は、新しいポリシーの改ざんを防止することを決意しています。悪意のあるアプリケーションが禁止されたトピックにアクセスする可能性を排除するためのメカニズムを導入することにしました。
関連タスクと例
- エグレス トラフィックの制御タスクでは、メッシュ内のアプリケーションが外部 (Kubernetes クラスターの外部) の HTTP および HTTPS サービスにアクセスする方法を示しています。
- エグレス ゲートウェイの構成の例では、エグレス ゲートウェイと呼ばれる専用のゲートウェイサービスを介してエグレス トラフィックをルーティングするように Istio を構成する方法について説明しています。
- TLSオリジネーション付きエグレスゲートウェイの例では、エグレスゲートウェイを介してトラフィックをルーティングしながら、アプリケーションがHTTPSを必要とする外部サーバーにHTTPリクエストを送信できるようにする方法を示しています。
- Grafanaを使用したメトリクスの可視化では、メッシュトラフィックを監視するためのIstioダッシュボードについて説明しています。
- 基本的なアクセス制御タスクは、メッシュ内サービスへのアクセスを制御する方法を示しています。
- 拒否とホワイト/ブラックリストタスクでは、ブラックリストまたはホワイトリストチェッカーを使用してアクセスポリシーを構成する方法を示しています。
上記の可観測性とセキュリティに関するタスクとは対照的に、このブログ記事では、エグレス トラフィックにのみ適用される Istio の監視およびアクセスポリシーについて説明します。
始める前に
TLS オリジネーション付きのエグレス ゲートウェイの例の手順を、相互 TLS 認証を有効にして、クリーンアップの手順なしで実行します。その例を完了すると、curl
がインストールされたメッシュ内のコンテナから edition.cnn.com/politics にアクセスできます。このブログ記事では、SOURCE_POD
環境変数にはソースポッドの名前が含まれており、コンテナの名前は sleep
であることを前提としています。
監視とアクセスポリシーの構成
タスクを安全な方法で完了したいので、TLS オリジネーション付きエグレス ゲートウェイタスクの説明に従って、エグレス トラフィックをエグレス ゲートウェイを介してルーティングする必要があります。ここで言う安全な方法とは、悪意のあるアプリケーションが Istio の監視とポリシー適用をバイパスするのを防ぎたいということです。
私たちのシナリオによると、組織は始める前にセクションの手順を実行し、edition.cnn.comへのHTTPトラフィックを有効にし、そのトラフィックがエグレスゲートウェイを通過するように設定しました。エグレスゲートウェイは、edition.cnn.comへのTLSオリジネーションを実行するため、トラフィックは暗号化された状態でメッシュを離れます。この時点で、組織はIstioを設定して、edition.cnn.comへのトラフィックを監視し、アクセスポリシーを適用する準備が整いました。
ロギング
*.cnn.comへのアクセスをログに記録するようにIstioを設定します。logentry
と2つのstdio handlers
を作成します。1つは禁止されたアクセス(errorログレベル)をログに記録し、もう1つは*.cnn.comへのすべてのアクセス(infoログレベル)をログに記録します。次に、logentry
インスタンスをhandlers
にルーティングするためのrules
を作成します。1つのルールは、*.cnn.com/politicsへのアクセスを禁止されたアクセスをログに記録するためのハンドラーにルーティングし、別のルールは、*.cnn.comへの各アクセスをinfoログエントリとして出力するハンドラーにログエントリをルーティングします。Istioのlogentries
、rules
、およびhandlers
を理解するには、Istioアダプターモデルを参照してください。関係するエンティティとそれらの間の依存関係を示す図を以下に示します。
logentry
、rules
、およびhandlers
を作成します。ルールでcontext.reporter.uid
をkubernetes://istio-egressgateway
として指定して、エグレスゲートウェイからのみログを取得するように注意してください。$ cat <<EOF | kubectl apply -f - # Log entry for egress access apiVersion: "config.istio.io/v1alpha2" kind: logentry metadata: name: egress-access namespace: istio-system spec: severity: '"info"' timestamp: request.time variables: destination: request.host | "unknown" path: request.path | "unknown" responseCode: response.code | 0 responseSize: response.size | 0 reporterUID: context.reporter.uid | "unknown" sourcePrincipal: source.principal | "unknown" monitored_resource_type: '"UNSPECIFIED"' --- # Handler for error egress access entries apiVersion: "config.istio.io/v1alpha2" kind: stdio metadata: name: egress-error-logger namespace: istio-system spec: severity_levels: info: 2 # output log level as error outputAsJson: true --- # Rule to handle access to *.cnn.com/politics apiVersion: "config.istio.io/v1alpha2" kind: rule metadata: name: handle-politics namespace: istio-system spec: match: request.host.endsWith("cnn.com") && request.path.startsWith("/politics") && context.reporter.uid.startsWith("kubernetes://istio-egressgateway") actions: - handler: egress-error-logger.stdio instances: - egress-access.logentry --- # Handler for info egress access entries apiVersion: "config.istio.io/v1alpha2" kind: stdio metadata: name: egress-access-logger namespace: istio-system spec: severity_levels: info: 0 # output log level as info outputAsJson: true --- # Rule to handle access to *.cnn.com apiVersion: "config.istio.io/v1alpha2" kind: rule metadata: name: handle-cnn-access namespace: istio-system spec: match: request.host.endsWith(".cnn.com") && context.reporter.uid.startsWith("kubernetes://istio-egressgateway") actions: - handler: egress-access-logger.stdio instances: - egress-access.logentry EOF
cnn.com、edition.cnn.com/politics、edition.cnn.com/sport、およびedition.cnn.com/healthに3つのHTTPリクエストを送信します。3つすべてが200 OKを返すはずです。
$ kubectl exec -it $SOURCE_POD -c sleep -- sh -c 'curl -sL -o /dev/null -w "%{http_code}\n" http://edition.cnn.com/politics; curl -sL -o /dev/null -w "%{http_code}\n" http://edition.cnn.com/sport; curl -sL -o /dev/null -w "%{http_code}\n" http://edition.cnn.com/health' 200 200 200
Mixerログをクエリして、リクエストに関する情報がログに表示されることを確認します
$ kubectl -n istio-system logs -l istio-mixer-type=telemetry -c mixer | grep egress-access | grep cnn | tail -4 {"level":"info","time":"2019-01-29T07:43:24.611462Z","instance":"egress-access.logentry.istio-system","destination":"edition.cnn.com","path":"/politics","reporterUID":"kubernetes://istio-egressgateway-747b6764b8-44rrh.istio-system","responseCode":200,"responseSize":1883355,"sourcePrincipal":"cluster.local/ns/default/sa/sleep"} {"level":"info","time":"2019-01-29T07:43:24.886316Z","instance":"egress-access.logentry.istio-system","destination":"edition.cnn.com","path":"/sport","reporterUID":"kubernetes://istio-egressgateway-747b6764b8-44rrh.istio-system","responseCode":200,"responseSize":2094561,"sourcePrincipal":"cluster.local/ns/default/sa/sleep"} {"level":"info","time":"2019-01-29T07:43:25.369663Z","instance":"egress-access.logentry.istio-system","destination":"edition.cnn.com","path":"/health","reporterUID":"kubernetes://istio-egressgateway-747b6764b8-44rrh.istio-system","responseCode":200,"responseSize":2157009,"sourcePrincipal":"cluster.local/ns/default/sa/sleep"} {"level":"error","time":"2019-01-29T07:43:24.611462Z","instance":"egress-access.logentry.istio-system","destination":"edition.cnn.com","path":"/politics","reporterUID":"kubernetes://istio-egressgateway-747b6764b8-44rrh.istio-system","responseCode":200,"responseSize":1883355,"sourcePrincipal":"cluster.local/ns/default/sa/sleep"}
3つのリクエストに関連する4つのログエントリが表示されます。edition.cnn.comへのアクセスに関する3つのinfoエントリと、edition.cnn.com/politicsへのアクセスに関する1つのerrorエントリです。サービスメッシュのオペレーターは、すべてのアクセスインスタンスを確認でき、禁止されているアクセスを表すerrorログエントリをログで検索することもできます。これは、禁止されているアクセスを自動的にブロックする前に、組織が適用できる最初のセキュリティ対策です。つまり、禁止されているすべてのアクセスインスタンスをエラーとしてログに記録します。一部の設定では、これで十分なセキュリティ対策となる場合があります。
属性に注意してください
destination
、path
、responseCode
、responseSize
は、リクエストのHTTPパラメーターに関連付けられていますsourcePrincipal
:cluster.local/ns/default/sa/sleep
-default
名前空間のsleep
サービスアカウントを表す文字列reporterUID
:kubernetes://istio-egressgateway-747b6764b8-44rrh.istio-system
- レポートポッドのUID。この場合、istio-system
名前空間のistio-egressgateway-747b6764b8-44rrh
です
ルーティングによるアクセス制御
edition.cnn.comへのアクセスのロギングを有効にしたら、アクセスポリシーを自動的に適用します。つまり、/healthおよび/sportのURLパスのみへのアクセスを許可します。このような単純なポリシー制御は、Istioルーティングで実装できます。
edition.cnn.comの
VirtualService
を再定義します$ cat <<EOF | kubectl apply -f - apiVersion: networking.istio.io/v1alpha3 kind: VirtualService metadata: name: direct-cnn-through-egress-gateway spec: hosts: - edition.cnn.com gateways: - istio-egressgateway - mesh http: - match: - gateways: - mesh port: 80 route: - destination: host: istio-egressgateway.istio-system.svc.cluster.local subset: cnn port: number: 443 weight: 100 - match: - gateways: - istio-egressgateway port: 443 uri: regex: "/health|/sport" route: - destination: host: edition.cnn.com port: number: 443 weight: 100 EOF
URLパスが/healthまたは/sportのいずれかであることを確認する
uri
条件によるmatch
を追加したことに注意してください。また、この条件はVirtualService
のistio-egressgateway
セクションに追加されていることに注意してください。これは、エグレスゲートウェイがセキュリティの面で強化されたコンポーネントであるためです(エグレスゲートウェイのセキュリティに関する考慮事項 (/docs/tasks/traffic-management/egress/egress-gateway/#additional-security-considerations)を参照)。ポリシーの改ざんを防止する必要があります。以前の3つのHTTPリクエストをcnn.comに送信します
$ kubectl exec -it $SOURCE_POD -c sleep -- sh -c 'curl -sL -o /dev/null -w "%{http_code}\n" http://edition.cnn.com/politics; curl -sL -o /dev/null -w "%{http_code}\n" http://edition.cnn.com/sport; curl -sL -o /dev/null -w "%{http_code}\n" http://edition.cnn.com/health' 404 200 200
edition.cnn.com/politicsへのリクエストは404 Not Foundを返しましたが、edition.cnn.com/sportおよびedition.cnn.com/healthへのリクエストは、予想どおり200 OKを返しました。
Mixerログをクエリして、リクエストに関する情報が再びログに表示されることを確認します
$ kubectl -n istio-system logs -l istio-mixer-type=telemetry -c mixer | grep egress-access | grep cnn | tail -4 {"level":"info","time":"2019-01-29T07:55:59.686082Z","instance":"egress-access.logentry.istio-system","destination":"edition.cnn.com","path":"/politics","reporterUID":"kubernetes://istio-egressgateway-747b6764b8-44rrh.istio-system","responseCode":404,"responseSize":0,"sourcePrincipal":"cluster.local/ns/default/sa/sleep"} {"level":"info","time":"2019-01-29T07:55:59.697565Z","instance":"egress-access.logentry.istio-system","destination":"edition.cnn.com","path":"/sport","reporterUID":"kubernetes://istio-egressgateway-747b6764b8-44rrh.istio-system","responseCode":200,"responseSize":2094561,"sourcePrincipal":"cluster.local/ns/default/sa/sleep"} {"level":"info","time":"2019-01-29T07:56:00.264498Z","instance":"egress-access.logentry.istio-system","destination":"edition.cnn.com","path":"/health","reporterUID":"kubernetes://istio-egressgateway-747b6764b8-44rrh.istio-system","responseCode":200,"responseSize":2157009,"sourcePrincipal":"cluster.local/ns/default/sa/sleep"} {"level":"error","time":"2019-01-29T07:55:59.686082Z","instance":"egress-access.logentry.istio-system","destination":"edition.cnn.com","path":"/politics","reporterUID":"kubernetes://istio-egressgateway-747b6764b8-44rrh.istio-system","responseCode":404,"responseSize":0,"sourcePrincipal":"cluster.local/ns/default/sa/sleep"}
まだedition.cnn.com/politicsへのアクセスに関する情報およびエラーメッセージが表示されますが、今回は
responseCode
が予想どおり404
になっています。
この単純なケースでは、Istioルーティングを使用したアクセス制御の実装がうまくいきましたが、より複雑なケースには十分ではありません。例えば、組織が特定の条件下でedition.cnn.com/politicsへのアクセスを許可したい場合、URLパスによるフィルタリングだけでは不十分で、より複雑なポリシーロジックが必要になります。例えば、Istio Mixerアダプター、具体的には許可/禁止されたURLパスのホワイトリストまたはブラックリストを適用することができます。ポリシー規則では、豊富な式言語で指定された複雑な条件を指定できます。これには、ANDやORなどの論理演算子が含まれます。ルールは、ロギングとポリシーチェックの両方に再利用できます。より高度なユーザーは、Istioロールベースアクセス制御を適用したい場合があります。
さらに考慮すべき点は、リモートアクセス制御システムとの統合です。もし、ユースケースの組織が何らかのIDおよびアクセス管理システムを運用している場合、そのようなシステムからのアクセス制御情報をIstioで使用するように構成したい場合があります。この統合は、Istio Mixerアダプターを適用することで実現できます。
このセクションで使用したルーティングによるアクセス制御をキャンセルし、次のセクションではMixerポリシーチェックによるアクセス制御を実装してください。
edition.cnn.comの
VirtualService
を、エグレスゲートウェイの構成の例の以前のバージョンに置き換えてください。$ cat <<EOF | kubectl apply -f - apiVersion: networking.istio.io/v1alpha3 kind: VirtualService metadata: name: direct-cnn-through-egress-gateway spec: hosts: - edition.cnn.com gateways: - istio-egressgateway - mesh http: - match: - gateways: - mesh port: 80 route: - destination: host: istio-egressgateway.istio-system.svc.cluster.local subset: cnn port: number: 443 weight: 100 - match: - gateways: - istio-egressgateway port: 443 route: - destination: host: edition.cnn.com port: number: 443 weight: 100 EOF
以前と同じように、3つのHTTPリクエストをcnn.comに送信すると、3つの200 OKレスポンスが返ってくるはずです。
$ kubectl exec -it $SOURCE_POD -c sleep -- sh -c 'curl -sL -o /dev/null -w "%{http_code}\n" http://edition.cnn.com/politics; curl -sL -o /dev/null -w "%{http_code}\n" http://edition.cnn.com/sport; curl -sL -o /dev/null -w "%{http_code}\n" http://edition.cnn.com/health' 200 200 200
Mixerポリシーチェックによるアクセス制御
このステップでは、MixerのListchecker
アダプター、そのホワイトリスト版を使用します。リクエストのURLパスを持つlistentry
と、overrides
フィールドで指定された許可されたURLパスの静的なリストを使用してlistentry
をチェックするlistchecker
を定義します。外部のIDおよびアクセス管理システムの場合は、代わりにproviderurl
フィールドを使用します。インスタンス、ルール、およびハンドラーの更新された図を以下に示します。同じポリシー規則handle-cnn-access
が、ロギングとアクセス制御の両方に再利用されていることに注意してください。
path-checker
とrequest-path
を定義します。$ cat <<EOF | kubectl create -f - apiVersion: "config.istio.io/v1alpha2" kind: listchecker metadata: name: path-checker namespace: istio-system spec: overrides: ["/health", "/sport"] # overrides provide a static list blacklist: false --- apiVersion: "config.istio.io/v1alpha2" kind: listentry metadata: name: request-path namespace: istio-system spec: value: request.path EOF
handle-cnn-access
ポリシー規則を、request-path
インスタンスをpath-checker
に送信するように変更します。$ cat <<EOF | kubectl apply -f - # Rule handle egress access to cnn.com apiVersion: "config.istio.io/v1alpha2" kind: rule metadata: name: handle-cnn-access namespace: istio-system spec: match: request.host.endsWith(".cnn.com") && context.reporter.uid.startsWith("kubernetes://istio-egressgateway") actions: - handler: egress-access-logger.stdio instances: - egress-access.logentry - handler: path-checker.listchecker instances: - request-path.listentry EOF
edition.cnn.com/politics、edition.cnn.com/sport、およびedition.cnn.com/healthにHTTPリクエストを送信して、通常どおりのテストを実行します。予想どおり、edition.cnn.com/politicsへのリクエストは*403*(Forbidden)を返します。
$ kubectl exec -it $SOURCE_POD -c sleep -- sh -c 'curl -sL -o /dev/null -w "%{http_code}\n" http://edition.cnn.com/politics; curl -sL -o /dev/null -w "%{http_code}\n" http://edition.cnn.com/sport; curl -sL -o /dev/null -w "%{http_code}\n" http://edition.cnn.com/health' 403 200 200
Mixerポリシーチェックによるアクセス制御、パート2
このユースケースの組織は、ロギングとアクセス制御の設定に成功した後、特別なサービスアカウントを持つアプリケーションが、監視なしでcnn.comのすべてのトピックにアクセスできるようにすることで、アクセス制御ポリシーを拡張することにしました。この要件をIstioでどのように構成できるかを見ていきましょう。
politics
サービスアカウントを持つsleepサンプルを開始します。$ sed 's/: sleep/: politics/g' @samples/sleep/sleep.yaml@ | kubectl create -f - serviceaccount "politics" created service "politics" created deployment "politics" created
外部サービスにリクエストを送信するために、
politics
サービスアカウントを持つソースポッドの名前を保持するSOURCE_POD_POLITICS
シェル変数を定義します。$ export SOURCE_POD_POLITICS=$(kubectl get pod -l app=politics -o jsonpath={.items..metadata.name})
今回は
SOURCE_POD_POLITICS
から3つのHTTPリクエストを送信する通常のテストを実行します。edition.cnn.com/politicsへのリクエストは、politics名前空間の例外を構成していないため、*403*を返します。$ kubectl exec -it $SOURCE_POD_POLITICS -c politics -- sh -c 'curl -sL -o /dev/null -w "%{http_code}\n" http://edition.cnn.com/politics; curl -sL -o /dev/null -w "%{http_code}\n" http://edition.cnn.com/sport; curl -sL -o /dev/null -w "%{http_code}\n" http://edition.cnn.com/health' 403 200 200
Mixerログをクエリして、politics名前空間からのリクエストに関する情報がログに表示されることを確認します。
$ kubectl -n istio-system logs -l istio-mixer-type=telemetry -c mixer | grep egress-access | grep cnn | tail -4 {"level":"info","time":"2019-01-29T08:04:42.559812Z","instance":"egress-access.logentry.istio-system","destination":"edition.cnn.com","path":"/politics","reporterUID":"kubernetes://istio-egressgateway-747b6764b8-44rrh.istio-system","responseCode":403,"responseSize":84,"sourcePrincipal":"cluster.local/ns/default/sa/politics"} {"level":"info","time":"2019-01-29T08:04:42.568424Z","instance":"egress-access.logentry.istio-system","destination":"edition.cnn.com","path":"/sport","reporterUID":"kubernetes://istio-egressgateway-747b6764b8-44rrh.istio-system","responseCode":200,"responseSize":2094561,"sourcePrincipal":"cluster.local/ns/default/sa/politics"} {"level":"error","time":"2019-01-29T08:04:42.559812Z","instance":"egress-access.logentry.istio-system","destination":"edition.cnn.com","path":"/politics","reporterUID":"kubernetes://istio-egressgateway-747b6764b8-44rrh.istio-system","responseCode":403,"responseSize":84,"sourcePrincipal":"cluster.local/ns/default/sa/politics"} {"level":"info","time":"2019-01-29T08:04:42.615641Z","instance":"egress-access.logentry.istio-system","destination":"edition.cnn.com","path":"/health","reporterUID":"kubernetes://istio-egressgateway-747b6764b8-44rrh.istio-system","responseCode":200,"responseSize":2157009,"sourcePrincipal":"cluster.local/ns/default/sa/politics"}
sourcePrincipal
がcluster.local/ns/default/sa/politics
であり、default
名前空間のpolitics
サービスアカウントを表していることに注意してください。handle-cnn-access
およびhandle-politics
ポリシー規則を再定義して、politics名前空間のアプリケーションが監視とポリシー適用から除外されるようにします。$ cat <<EOF | kubectl apply -f - # Rule to handle access to *.cnn.com/politics apiVersion: "config.istio.io/v1alpha2" kind: rule metadata: name: handle-politics namespace: istio-system spec: match: request.host.endsWith("cnn.com") && context.reporter.uid.startsWith("kubernetes://istio-egressgateway") && request.path.startsWith("/politics") && source.principal != "cluster.local/ns/default/sa/politics" actions: - handler: egress-error-logger.stdio instances: - egress-access.logentry --- # Rule handle egress access to cnn.com apiVersion: "config.istio.io/v1alpha2" kind: rule metadata: name: handle-cnn-access namespace: istio-system spec: match: request.host.endsWith(".cnn.com") && context.reporter.uid.startsWith("kubernetes://istio-egressgateway") && source.principal != "cluster.local/ns/default/sa/politics" actions: - handler: egress-access-logger.stdio instances: - egress-access.logentry - handler: path-checker.listchecker instances: - request-path.listentry EOF
SOURCE_POD
から通常のテストを実行します。$ kubectl exec -it $SOURCE_POD -c sleep -- sh -c 'curl -sL -o /dev/null -w "%{http_code}\n" http://edition.cnn.com/politics; curl -sL -o /dev/null -w "%{http_code}\n" http://edition.cnn.com/sport; curl -sL -o /dev/null -w "%{http_code}\n" http://edition.cnn.com/health' 403 200 200
SOURCE_POD
にはpolitics
サービスアカウントがないため、edition.cnn.com/politicsへのアクセスは以前と同様に禁止されています。SOURCE_POD_POLITICS
から前のテストを実行します。$ kubectl exec -it $SOURCE_POD_POLITICS -c politics -- sh -c 'curl -sL -o /dev/null -w "%{http_code}\n" http://edition.cnn.com/politics; curl -sL -o /dev/null -w "%{http_code}\n" http://edition.cnn.com/sport; curl -sL -o /dev/null -w "%{http_code}\n" http://edition.cnn.com/health' 200 200 200
edition.cnn.comのすべてのトピックへのアクセスが許可されます。
Mixerログを調べると、
sourcePrincipal
がcluster.local/ns/default/sa/politics
と等しいリクエストがログに表示されなくなっていることがわかります。$ kubectl -n istio-system logs -l istio-mixer-type=telemetry -c mixer | grep egress-access | grep cnn | tail -4
HTTPSエグレストラフィック制御との比較
このユースケースでは、アプリケーションはHTTPを使用し、Istio Egress GatewayがTLSオリジネーションを実行します。または、アプリケーションがedition.cnn.comにHTTPSリクエストを発行して、自身でTLSを生成することもできます。このセクションでは、両方のアプローチとその長所と短所について説明します。
HTTPアプローチでは、リクエストはローカルホスト上で暗号化されずに送信され、Istioサイドカープロキシによってインターセプトされ、エグレスゲートウェイに転送されます。サイドカープロキシとエグレスゲートウェイの間で相互TLSを使用するようにIstioを構成しているため、トラフィックは暗号化された状態でポッドから送信されます。エグレスゲートウェイはトラフィックを復号化し、URLパス、HTTPメソッド、およびヘッダーを検査し、テレメトリを報告してポリシーチェックを実行します。リクエストがポリシーチェックによってブロックされない場合、エグレスゲートウェイは外部宛先(この場合はcnn.com)へのTLSオリジネーションを実行するため、リクエストは再度暗号化され、暗号化された状態で外部宛先に送信されます。以下の図は、このアプローチのネットワークフローを示しています。ゲートウェイ内のHTTPプロトコルは、復号化後にゲートウェイから見たプロトコルを示しています。
このアプローチの欠点は、リクエストがポッド内で暗号化されずに送信されることです。これは、一部の組織のセキュリティポリシーに反する可能性があります。また、一部のSDKにはプロトコルを含む外部サービスURLがハードコードされているため、HTTPリクエストの送信が不可能な場合があります。このアプローチの利点は、HTTPメソッド、ヘッダー、およびURLパスを検査し、それらに基づいてポリシーを適用できることです。
HTTPSアプローチでは、リクエストはアプリケーションから外部宛先までエンドツーエンドで暗号化されます。以下の図は、このアプローチのネットワークフローを示しています。ゲートウェイ内のHTTPSプロトコルは、ゲートウェイから見たプロトコルを示しています。
エンドツーエンドのHTTPSは、セキュリティの観点からより良いアプローチと考えられています。ただし、トラフィックは暗号化されているため、Istioプロキシとエグレスゲートウェイは、送信元と宛先のIP、および宛先のSNIしか確認できません。サイドカープロキシとエグレスゲートウェイの間で相互TLSを使用するようにIstioを構成しているため、送信元のIDも認識されます。ゲートウェイは、リクエストのURLパス、HTTPメソッド、およびヘッダーを検査できないため、HTTP情報に基づく監視とポリシーはできません。このユースケースでは、組織はedition.cnn.comへのアクセスを許可し、どのアプリケーションがedition.cnn.comにアクセスできるかを指定できます。ただし、edition.cnn.comの特定のURLパスへのアクセスを許可またはブロックすることはできません。edition.cnn.com/politicsへのアクセスをブロックしたり、そのようなアクセスを監視したりすることは、HTTPSアプローチでは不可能です。
各組織が2つのアプローチの長所と短所を検討し、ニーズに最適なものを選択すると考えられます。
まとめ
このブログ記事では、Istioのさまざまな監視およびポリシーメカニズムをHTTPエグレストラフィックに適用する方法を示しました。監視は、ロギングアダプターを構成することで実装できます。アクセス制御ポリシーは、VirtualServices
を構成するか、さまざまなポリシーチェックアダプターを構成することで実装できます。特定のURLパスのみを許可する単純なポリシーを実証しました。また、特定のサービスアカウントを持つアプリケーションを例外とするシンプルなポリシーを拡張する、より複雑なポリシーも示しました。最後に、HTTP-with-TLS-originationエグレストラフィックとHTTPSエグレストラフィックを、Istioによる制御可能性の観点から比較しました。
クリーンアップ
エグレスゲートウェイの構成の例のクリーンアップセクションの手順を実行します。
ロギングとポリシーチェックの設定を削除します。
$ kubectl delete logentry egress-access -n istio-system $ kubectl delete stdio egress-error-logger -n istio-system $ kubectl delete stdio egress-access-logger -n istio-system $ kubectl delete rule handle-politics -n istio-system $ kubectl delete rule handle-cnn-access -n istio-system $ kubectl delete -n istio-system listchecker path-checker $ kubectl delete -n istio-system listentry request-path
politicsソースポッドを削除します。
$ sed 's/: sleep/: politics/g' @samples/sleep/sleep.yaml@ | kubectl delete -f - serviceaccount "politics" deleted service "politics" deleted deployment "politics" deleted