SSOを利用してArgo Serverにログインする
概要
Argo Workflowsに対して、Googleアカウントを使ったssoを使用してみました。
今回はGKE上にArgo Serverを構築したいと思います。
GitHub: https://github.com/hosimesi/code-for-techblogs/tree/main/argo_server_sso
Argo Serverの認証方法
Argo Serverの認証方法にはいくつか方法があります。
- server
- client
- sso
開発時等はserver認証でも問題ないですが、実運用上ではclientかssoの認証を入れる必要があると思います。
今回はより柔軟な権限管理ができるssoでArgo Serverにログインできるように設定したいと思います。
もしArgo CDを使っている場合、Dexとの連携も可能ですが、それについては別記事にまとめたいと思います。
Google Cloudの設定
まずはGKEのクラスター作成やサービスアカウントの作成をします。今回は検証用なので、1ノードで小さいインスタンスを動かしてみます。DNS ZoneをGoogle Cloud上で管理している前提で作成していますが、自身の状況に合わせて修正してください。
provider "google" {
project = var.project
region = var.region
}
# GKEのservice account
resource "google_service_account" "gke_sa" {
account_id = "gke-sa"
display_name = "gke用のservice account"
}
# GKE Cluster
resource "google_container_cluster" "gke_cluster" {
name = "gke-cluster"
location = "asia-northeast1-a"
project = var.project
deletion_protection = false
remove_default_node_pool = true
initial_node_count = 1
}
# GKE Node Pool
resource "google_container_node_pool" "argo_nodes" {
name = "argo-node-pool"
location = "asia-northeast1-a"
cluster = google_container_cluster.gke_cluster.name
project = var.project
node_count = 1
autoscaling {
max_node_count = 1
min_node_count = 1
}
node_config {
preemptible = true
machine_type = "e2-medium"
service_account = google_service_account.gke_sa.email
metadata = {
disable-legacy-endpoints = "true"
}
oauth_scopes = [
"https://www.googleapis.com/auth/logging.write",
"https://www.googleapis.com/auth/monitoring",
]
labels = {
preemptible = "true"
}
tags = ["argo-node-pool"]
}
}
# Argo Workflows用の外部IP
resource "google_compute_global_address" "argo_workflows_external_ip" {
name = "argo-workflows-server-ip"
address_type = "EXTERNAL"
ip_version = "IPV4"
project = var.project
}
# DNSゾーン
data "google_dns_managed_zone" "dns_zone" {
name = "your-dns-zone"
project = var.project
}
# Argo Workflows用のDNSレコード
resource "google_dns_record_set" "argo_workflows" {
project = var.project
name = "argo-workflows.${data.google_dns_managed_zone.dns_zone.dns_name}"
type = "A"
ttl = 300
managed_zone = data.google_dns_managed_zone.dns_zone.name
rrdatas = [google_compute_global_address.argo_workflows_external_ip.address]
lifecycle {
ignore_changes = [rrdatas]
}
}
# Argo Workflowsのservice account
resource "google_service_account" "argo_workflows_sa" {
account_id = "argo-workflows-sa"
display_name = "argo workflows用のservice account"
}
上記作成後、をterraform applyしてリソースを作成します。
ssoの設定
次にssoに必要なID Providerや認証情報の設定をしていきます。
認証情報の作成
認証情報を作成します。OAuthクライアントIDの作成を選択します。
アプリケーションの種類をウェブアプリケーション、名前をargo ssoとして作成します。
この時、承認済みのJavaScript生成元や承認済みのリダイレクトURIには自身のドメインを設定します。
承認済みのJavaScript生成元: https://<your-domain>
承認済みのリダイレクトURI: https://<your-domain>/oauth2/callback
ここで得られたクライアントIDとクライアントシークレットを保存しておきます。
OAuth 同意画面の設定
先ほど認証情報の作成によって自動で以下のようにargo ssoが作成されています。
これを編集していきます。
スコープとしてemailとprofileを選択して保存します。
また、テストユーザとしてGoogleのメールアドレスを2つ用意しておきます。この2つはこの後、Admin権限をもつユーザとRead Only権限をもつユーザとしてログインする用途で使用します。
これで設定は完了です。
ID Providerの作成
次にID Providerを作成していきます。
先ほど得られたクライアントIDとクライアントシークレットを入力し、保存します。
Argo Workflowsの構築
今回はargo-workflowsというnamespaceにリソースを作成するため、まず必要なnamespaceを作成していきます。
apiVersion: v1
kind: Namespace
metadata:
name: argo-workflows
labels:
name: argo-workflows
$ kubectl apply -f argoworkflows/base/namespace.yaml
namespace/argo-workflows created
その後、他のすべてのリソースを作成します。重要な部分をピックアップします。
- Secretを作成します。
先ほどOAuthクライアントを作成した時のclient idとclient secretをbase 64でエンコードし、以下に指定します。また、Service Accountのトークンを保存するためのSecretも作成しておきます。ここではすべての操作ができるdeveloper-saと読み取り権限のbusiness-saを用意するため、それぞれのSecretを作成します。$echo -n 'client-id' | base64 $echo -n 'client-secret' | base64
apiVersion: v1 kind: Secret metadata: name: argo-server-sso-secret namespace: argo-workflows type: Opaque data: client-id: <base64-encoded-client-id> client-secret: <base64-encoded-client-secret> --- apiVersion: v1 kind: Secret metadata: name: developer-sa.service-account-token namespace: argo-workflows annotations: kubernetes.io/service-account.name: developer-sa type: kubernetes.io/service-account-token --- apiVersion: v1 kind: Secret metadata: name: business-sa.service-account-token namespace: argo-workflows annotations: kubernetes.io/service-account.name: business-sa type: kubernetes.io/service-account-token
- Service Accountの作成
実行用に先ほどのTerraformで作成したArgo Workflows用のSAをannotationします。また、developer-saとbusiness-saを作成し、それぞれには自身が用意したgoogleのアカウントのメールアドレスをannotationします。# 実行用SA apiVersion: v1 kind: ServiceAccount metadata: name: argo-workflows-sa namespace: argo-workflows # 先ほどterraformで作成したargo workflows用のサービスアカウントのEmail annotations: iam.gke.io/gcp-service-account: "your-gcp-service-account-email" --- # DeveloperのSSO用SA apiVersion: v1 kind: ServiceAccount metadata: name: developer-sa namespace: argo-workflows # FIXME: Replace the following value with your own annotations: workflows.argoproj.io/rbac-rule: "email == 'your-google-email-1'" workflows.argoproj.io/rbac-rule-precedence: "1" --- # BusinessのSSO用SA apiVersion: v1 kind: ServiceAccount metadata: name: business-sa namespace: argo-workflows # FIXME: Replace the following value with your own annotations: workflows.argoproj.io/rbac-rule: "email == 'your-google-email-2'" workflows.argoproj.io/rbac-rule-precedence: "1"
- ConfigMap
ConfigMapでssoの設定をします。redirectUrlには自身のドメインを設定します。# For workflow archive to Cloud SQL apiVersion: v1 kind: ConfigMap metadata: name: workflow-controller-configmap namespace: argo-workflows data: namespace: argo-workflows sso: | issuer: https://accounts.google.com sessionExpiry: 12h clientId: name: argo-server-sso-secret key: client-id clientSecret: name: argo-server-sso-secret key: client-secret # FIXME Replace the following value with your own redirectUrl: https://<your-domain>/oauth2/callback scopes: - email - profile rbac: enabled: true insecureSkipVerify: false
- Deploymentの作成
auth-modeをssoとして立ち上げます。apiVersion: apps/v1 kind: Deployment metadata: name: argo-server namespace: argo-workflows spec: selector: matchLabels: app: argo-server template: spec: containers: - name: argo-server args: ["server", "--secure=false", "--auth-mode=sso"] resources: requests: cpu: 50m memory: 200Mi limits: cpu: 100m memory: 400Mi
上記の設定以外も含めて、適用していきます。今回はKustomizeを使用します。
$ kubectl apply -k argoworkflows/overlays/dev
namespace: argo-workflowsに2つのpodが立っており、Terraformで作成した自身のドメインでArgo UIにアクセスできたらOKです。
$ kubectl get pods -n argo-workflows
NAME READY STATUS RESTARTS AGE
argo-server-xxxxxxxxx-xxx 1/1 Running 0 113s
workflow-controller-xxxxxxxxx-xxx 1/1 Running 0 26m
それでは左側のSSOをクリックしてみます。
まずは、すべての操作ができるdeveloper-saに紐付けたアカウントでログインしてみます。
以下のようにdeveloper-saとしてログインできていれば成功です。
すべての操作が許可されているので、ワークフローテンプレートを作ることもできます。
次に、読み取り権限のみを付与したbusiness-saに紐付けたアカウントでログインしてみます。
先ほどど違い、business-saでログインできていることが確認できました。
権限が変わっているか確認するためにワークフローテンプレートを作ってみます。
意図通りワークフローテンプレートは作成できませんでした。
最後に
Argo Workflowsに対して、Googleアカウントを使ったssoを使用してみました。今回はEmailでの権限の付与でしたが、Groupsなども対応しているため、チームごとなどもう少し広い範囲の管理も可能です。
簡単に導入できるので、ssoを検討してみてもいいかもしれません。
またドメインを持っていない場合でもローカル環境でkind上でArgo Serverを立て、ngrokなどを使ってトンネルすることで同様の検証が可能です。
参考文献
Discussion