すべてのプロダクト
Search
ドキュメントセンター

Alibaba Cloud Service Mesh:OPA エンジンとイングレスゲートウェイの統合

最終更新日:Mar 12, 2026

イングレスゲートウェイが外部トラフィックを受信すると、きめ細かなアクセス制御には単純な許可/拒否ルールだけでは不十分な場合が多くあります。Open Policy Agent (OPA) を使用すると、Rego 言語でカスタムの権限付与ポリシーを作成し、アプリケーションコードを変更することなく、ゲートウェイレベルでそのポリシーを適用できます。

本トピックでは、Service Mesh (ASM) のイングレスゲートウェイと並列して OPA エンジンをデプロイし、Envoy の外部権限付与メカニズムを介して両者を接続したうえで、HTTPBin アプリケーションを用いて設定を検証する手順について説明します。

仕組み

ASM イングレスゲートウェイは、データプレーンプロキシとして Envoy を使用します。Envoy は、外部権限付与フィルター (ext_authz) をサポートしており、このフィルターにより、権限付与の判断を外部サービスに委譲できます。

OPA が外部権限付与サービスとして統合される場合:

  1. リクエストがイングレスゲートウェイに到着します。

  2. Envoy が、リクエストのメタデータ(HTTP メソッド、パス、ヘッダー)を gRPC 経由で OPA エンジンに送信します。

  3. OPA が、ロード済みの Rego ポリシーに基づいてリクエストを評価します。

  4. OPA が「許可」または「拒否」の判定結果を返します。Envoy は、許可された場合はリクエストをアップストリームに転送し、拒否された場合は 403 Forbidden 応答を返します。

OPA はクラスター内に独立した Pod として実行されるため、ポリシー評価はローカルで行われ、外部ネットワークホップを必要としません。また、OPA の HTTP API を使用することで、ワークロードの再デプロイを伴わず、ランタイム中にポリシーを更新できます。

前提条件

開始する前に、以下の条件を満たしていることを確認してください。

ステップ 1:OPA エンジンのデプロイ

以下の内容で asm-opa.yaml というファイルを作成します。このマニフェストでは、3 つの Kubernetes リソースが定義されています。

リソース目的
サービス9191 ポート(gRPC)および 8181 ポート(HTTP)で OPA エンジンを公開します
デプロイメントEnvoy 外部権限付与 gRPC プラグインを有効化した状態で OPA コンテナを実行します
シークレットOPA が起動時に読み込むデフォルトの Rego ポリシーを格納します
説明

コンテナイメージのパスに含まれるリージョン ID cn-hangzhou を、ご利用のクラスターがデプロイされているリージョンに置き換えてください。たとえば、クラスターが中国 (上海) リージョンにある場合は、registry-vpc.cn-shanghai.aliyuncs.com/acs/opa:0.46.1-istio-3-static を使用します。

asm-opa.yaml の内容を表示

apiVersion: v1
kind: Service
metadata:
  name: asm-opa
  labels:
    app: opa
spec:
  ports:
    - name: grpc
      port: 9191
      targetPort: 9191
      protocol: TCP
    - name: http
      port: 8181
      targetPort: 8181
      protocol: TCP
  selector:
    app: opa
---
kind: Deployment
apiVersion: apps/v1
metadata:
  name: opa
  labels:
    app: opa
spec:
  replicas: 1
  selector:
    matchLabels:
      app: opa
  template:
    metadata:
      labels:
        app: opa
      annotations:
        sidecar.istio.io/inject: "false"
    spec:
      containers:
        - name: opa
          image: registry-vpc.cn-hangzhou.aliyuncs.com/acs/opa:0.46.1-istio-3-static
          securityContext:
            runAsUser: 1111
          volumeMounts:
            - readOnly: true
              mountPath: /policy
              name: opa-policy
          args:
            - "run"
            - "--server"
            - "--addr=0.0.0.0:8181"
            - "--diagnostic-addr=0.0.0.0:8282"
            - "--set=plugins.envoy_ext_authz_grpc.addr=:9191"
            - "--set=plugins.envoy_ext_authz_grpc.path=asm/authz/allow"
            - "--set=decision_logs.console=true"
            - "--ignore=.*"
            - "/policy/policy.rego"
          ports:
            - containerPort: 9191
              protocol: TCP
          resources:
            limits:
              cpu: "0"
              memory: "0"
      volumes:
        - name: opa-policy
          secret:
            secretName: opa-policy
---
apiVersion: v1
kind: Secret
metadata:
  name: opa-policy
type: Opaque
stringData:
  policy.rego: |
    package asm.authz

    import future.keywords

    import input.attributes.request.http as http_request
    import input.parsed_path

    default allow := false

    allow if {
      parsed_path[0] == "health"
    }

    allow if {
      http_request.method == "HEAD"
    }

    allow if {
      user_name == "alice"
    }

    user_name := parsed if {
      [_, encoded] := split(http_request.headers.authorization, " ")
      [parsed, _] := split(base64url.decode(encoded), ":")
    }

主な構成フィールド

デプロイメントの args は、OPA エンジンの動作を制御するパラメーターを指定します。

フィールド説明
--addr0.0.0.0:8181ポリシー管理およびヘルスチェック用の HTTP API リスニングアドレスです。
--diagnostic-addr0.0.0.0:8282readiness プローブおよび liveness プローブ用の診断エンドポイントです。
plugins.envoy_ext_authz_grpc.addr:9191Envoy 外部権限付与プラグインの gRPC リスニングアドレスです。サービスのポートと一致させる必要があります。
plugins.envoy_ext_authz_grpc.pathasm/authz/allowRego ポリシーの判定パスです。OPA は各リクエストに対して data.asm.authz.allow を評価します。
decision_logs.consoletrueデバッグ用に、判定ログを stdout に出力します。

デフォルトのポリシールール

シークレットに格納された Rego ポリシーでは、3 つの権限付与ルールが定義されています。リクエストは、**いずれかのルール**が true と評価された場合に許可されます。

ルール条件
ヘルスチェックのバイパスリクエストパスが healthGET /health
HEAD メソッドのバイパスHTTP メソッドが HEADHEAD /any-path
ユーザーの権限付与Authorization ヘッダー内のユーザー名が aliceAuthorization: Basic YWxpY2U6dGVzdHBhc3N3b3Jk(alice:testpassword、Base64 エンコード)

上記以外のすべてのリクエストは拒否されます(default allow := false)。

デプロイ

以下のコマンドを実行して、OPA を Container Service for Kubernetes (ACK) クラスターにデプロイします。

kubectl apply -f asm-opa.yaml

ステップ 2:イングレスゲートウェイから OPA を利用するよう構成

ASM コンソールを使用して、OPA エンジンをカスタム権限付与サービスとしてイングレスゲートウェイに接続します。

  1. ASM コンソールにログインします。左側のナビゲーションウィンドウで、Service Mesh > Mesh Management を選択します。

  2. Mesh Management ページで、対象の ASM インスタンスの名前をクリックします。左側のナビゲーションウィンドウで、ASM Gateways > Ingress Gateway を選択します。

  3. Ingress Gateway ページで、構成対象のイングレスゲートウェイの横にある Gateway security をクリックします。

  4. 左側のナビゲーションウィンドウで、Gateway Security > Custom Authorization Service を選択します。

  5. Custom Authorization Service Configuration ステップで、イングレスゲートウェイのカスタム権限付与サービスとして OPA エンジンを構成し、Next をクリックします。

    Custom Authorization Service Configuration

  6. Matching Rules ステップで、OPA 権限付与を適用するリクエストを指定し、Submit をクリックします。

    Matching Rules

構成が保存されると、カスタム権限付与サービスがページ上に表示されます。

Custom Authorization Service Created

ステップ 3:OPA 権限付与の検証

HTTPBin アプリケーションをイングレスゲートウェイ経由で呼び出し、3 つの権限付与ルールをテストします。

以下のコマンドで使用する <gateway-ip> は、ご利用の ASM イングレスゲートウェイの IP アドレスに置き換えてください。

テスト 1:マッチングルールの対象外パスへのアクセス

ルートパス (/) に対して GET リクエストを送信します。ステップ 2 で構成したマッチングルールがこのパスをカバーしていない場合、リクエストは OPA をバイパスし、直接アップストリームサービスに到達します。

curl <gateway-ip>/ -I -X GET

期待される出力:

HTTP/1.1 200 OK
server: istio-envoy
date: Tue, 25 Jul 2023 08:30:58 GMT
content-type: text/html; charset=utf-8
content-length: 9593
access-control-allow-origin: *
access-control-allow-credentials: true
x-envoy-upstream-service-time: 2

200 OK 応答は、このパスに対するリクエストが OPA によってインターセプトされていないことを確認します。

テスト 2:認証情報なしでの保護パスへのアクセス

GET リクエストを、/status/201 に対して、Authorization ヘッダーを含めずに送信します。

curl <gateway-ip>/status/201 -I -X GET

期待される出力:

HTTP/1.1 403 Forbidden
date: Tue, 25 Jul 2023 08:31:18 GMT
server: istio-envoy
content-length: 0
x-envoy-upstream-service-time: 1

403 Forbidden 応答は、許可ルールに一致しないリクエストが OPA によって拒否されることを確認します。

テスト 3:有効な認証情報を用いた保護パスへのアクセス

許可されたユーザー名 alice を用いて、GET リクエストを /status/201 に対して送信します。

curl <gateway-ip>/status/201 -I -X GET --user alice:testpassword

期待される出力:

HTTP/1.1 201 Created
server: istio-envoy
date: Tue, 25 Jul 2023 08:31:38 GMT
content-type: text/html; charset=utf-8
access-control-allow-origin: *
access-control-allow-credentials: true
content-length: 0
x-envoy-upstream-service-time: 3

201 Created 応答は、ユーザー alice からのリクエストが OPA によって許可されることを確認します。

ステップ 4:ランタイムでの OPA ポリシーの更新

OPA は、ポリシー管理用の HTTP API を提供しています。この API を使用すると、OPA Pod の再デプロイを伴わずにポリシーを更新できます。

以下の例では、許可されるユーザーを alice から bob に変更します。

kubectl exec deployment/httpbin -c istio-proxy -- curl asm-opa:8181/v1/policies/policy/policy.rego -XPUT --data-binary 'package asm.authz

import future.keywords
import input.attributes.request.http as http_request
import input.parsed_path

default allow := false

allow if {
  parsed_path[0] == "health"
}

allow if {
  http_request.method == "HEAD"
}

allow if {
  user_name == "bob"
}

user_name := parsed if {
  [_, encoded] := split(http_request.headers.authorization, " ")
  [parsed, _] := split(base64url.decode(encoded), ":")
}'
説明

このコマンドは、OPA サービス (asm-opa:8181) がクラスター内からのみアクセス可能であるため、httpbin Pod の istio-proxy コンテナから curl を実行します。HTTP PUT メソッドは、指定されたパスにある既存のポリシーを置き換えます。

更新されたポリシーの検証

  1. bob としてリクエストを送信します。201 Created 応答が期待されます。期待される出力:

       curl <gateway-ip>/status/201 -I -X GET --user bob:testpassword
       HTTP/1.1 201 Created
       server: istio-envoy
       date: Tue, 25 Jul 2023 08:32:16 GMT
       content-type: text/html; charset=utf-8
       access-control-allow-origin: *
       access-control-allow-credentials: true
       content-length: 0
       x-envoy-upstream-service-time: 3
  2. alice としてリクエストを送信します。403 Forbidden 応答が期待されます。期待される出力:

       curl <gateway-ip>/status/201 -I -X GET --user alice:testpassword
       HTTP/1.1 403 Forbidden
       date: Tue, 25 Jul 2023 08:32:49 GMT
       server: istio-envoy
       content-length: 0
       x-envoy-upstream-service-time: 1

これらの結果より、更新されたポリシーが即座に有効化されたことが確認できます:bob は許可され、alice は拒否されるようになりました。