GCPのCloud IAMを試してみた | サイバーエージェント 公式エンジニアブログ

(2019/04 追記 この記事の情報は古いです。今では、GCPのIAMでも IAM Custom Roles によってカスタマイズしたロールが作れたり、Cloud IAM Conditions が登場してリソースの制限がしやすくなったりしています。また、メディア管轄のAWS Organizationsの活用については 「これ危ない設定じゃないでしょうか」とヒアリングするための仕組み @AWS Summit Tokyo 2018 もご覧ください)

 

メディア事業(アメーバなど)を中心にAWS/GCPを担当している柿島大貴です。前回は、Google Cloud Platform(GCP)の各プロジェクトでコストを追える環境を作る を書きました。前回の続報としては、一部には使ってもらいつつも、可視化の部分で cloudyn を検証中です。

 

今回は、GCPのリソースの認可の話になります。GCPの利用がメディア事業でも増えてきています。パブリッククラウドを組織としてそれなりの人数で利用していると、やはり気になってくるのが権限の管理です。セキュリティや作業事故防止を考えると、メンバー全員に強い権限を渡すというわけにもいかず、メンバーの役割ごとに権限を与えるということが必要になります。

Cloud IAM の登場

先日の GCP NEXT で、Google Cloud Identity and Access Management (Cloud IAM) が発表されました。AWSの AWS Identity and Access Management (IAM) に比べて、GCPはこの部分が弱いと思っていたので、首を長くして待っていた機能になります。Youtubeにある紹介動画 Introduction to Cloud IAM が4分くらいで概要をつかめるのでオススメです。

 

ベストプラクティスの資料もすでに用意されています。

 

IAM best practice guides available now

以上です!

 

.....とはいかないので、

  • Cloud IAM の紹介
  • 実際に触ってみる
  • その他、試した所感

の流れで、自分なりに理解した説明と試した記録を残します。もし間違い等がありましたらご指摘ください。

Cloud IAM の紹介

Cloud IAM の話に登場する大きな要素は、「Identity」、「Role(とPermission)」、「Resource」の3つです。IdentityはGoogle AccountやService Accountといった誰に対応する部分です。所属するメンバーを一括管理するために Google GroupGoogle Apps Domain をIdentityとして指定することもできます。Roleは、何ができるかという役割(Permissionの集まり)です。ResourceはProject 、Project内のGCEといった特定のサービス、GCE内のインスタンスといったような GCPの各種リソースです。

 

(引用: https://cloud.google.com/iam/docs/ )

After Google authenticates the identity making a request, Cloud IAM makes an authorization decision whether that identity is allowed to perform an operation on a resource.

https://cloud.google.com/iam/docs/overview#concepts_related_to_access_management

 

このIdentityとRoleとResource(後述するRerouce Hierarchyのレベル)の組み合わせで誰が何にどのようにアクセスできるかを定義すると、そのIdentityがResouceへアクセスをする際に権限があるかどうかをCloud IAMがチェックしてくれます。

 

また、Cloud IAM には重要な概念として、Resource Hierarchy というものがあります。冒頭に紹介したベストプラクティスの Using Resource Hierarchy for Access Control で詳しく説明がされています。HierarchyのrootとしてOrganizationが存在し、その子としてProject、Projectの子として、GCEなどのResourceが存在します。Organizationは、Google Apps for Work の顧客向けに提供されています(現在Alpha)。


(引用: https://cloud.google.com/iam/docs/resource-hierarchy-access-control )

 

Hierarchyの上位で許可した権限は下位に引き継がれます。下に引用した図はOrganizationに対して、compute.networkAdmin のRoleが付与されているbob@example.comさんが各プロジェクトのGCEでnetworkリソースの追加作業ができることを表した図です。

 

(引用: https://cloud.google.com/iam/docs/resource-hierarchy-access-control#example_compute_engine )

 

複数の箇所で有効なPolicyが指定されている場合は、和集合となるようです。各RoleがどのHierarchyのレベルに対応しているかは、こちらのページの表のResource Typeに書かれています。例えば、Projectにだけ対応しているRoleもあれば、OrganizationとProjectの両方に対応しているRoleもあります。Organization専用のRoleである roles/
resourcemanager.organizationAdmin
というRoleを持ったIdentityはそのOrganizationに属するどのProjectのどのResourceに対しても管理者権限を持つことができるようです。

Role/Resourceに関して

これまでものGCPでも、前回書いた記事 でも使ったように、BigqueryではProjectやDatasetごとにACLを設定できたり、ほかにもGCSでBucketsやObjectsに対して ACLでのアクセスコントロールができたりと、一部のサービスでは細かな権限にも対応していました。しかし、GCP全体となるとチームメンバーのGoogle Accountに設定できるのは、Owner(is Owner)、Editor(can Edit)、Viewer(can View)という3種類だけでした。

Team members may be authorized to have one of three levels of access:

  • “can View” (called Viewer in App Engine Console) allows read-only access.
  • “can Edit” (called Developer in App Engine Console) allows modify and delete access.
    This allows a developer to deploy the application and modify or configure its resources.
  • “is Owner” (called Owner in App Engine Console) allows full administrative access.
    This includes the ability to add members and set the authorization level of team members.

https://cloud.google.com/docs/permissions-overview#h.bgs0oxofvnoo

 

これらのRoleしかない場合、特定のリソースにアクセスをさせたいだけの場合でも、強めの権限を付与する必要がありました。今後は、必要最低限の権限しか渡したくない(貰いたくない)場合には、今回登場した新しいRoleの Curated roles を使うことができます。これまでの Owner、Editor、Viewer というRoleは、Primitive roles と呼ばれるようになります。


Curated rolesには例えば、VMインスタンス(やディスク)の作成、編集、削除が許されたRoleとして compute.instanceAdmin が用意されています。他にどのようなCurated rolesがあるかは https://cloud.google.com/iam/docs/understanding-roles#curated_roles をご覧下さい。

 

AWSで例えると、これまでは、AdministratorAccess、PowerUserAccess、ReadOnlyAccessのポリシーしかアタッチできなかったのが、AmazonEC2FullAccessなども選べるようになったというイメージでしょうか。

 

各サービスのIAMへの対応状況は、以下のようにまだまだBetaが多いです(2016/03/31現在)。Betaのものは、後方互換のない変更が起こる可能性があるため、プロダクション環境への利用は推奨されていません。また、すでに別のアクセス制限方法があるBigqueryは未対応だったりと、すべてのサービスがIAMに対応をしているわけではないようです。(今後どうなるかはわかりません)。また、Beta期間ではGCEのrolling updatesなど一部のオペレーションも未対応のようです。

 

(引用: https://cloud.google.com/iam/docs/ 2016/03/30時点)

 

Curated RoleはPermissionの集まりとなっていて、Permissionは以下のようなフォーマットで表現されます。

Service.Resource.Verb

例えば roles/compute.securityAdminという Curated Role は、以下のPermissionの集合になっています。

compute.firewalls.*
compute.networks.{get|list}
compute.operations.get
compute.projects.get
compute.regions.*
compute.routes.{get|list}
compute.sslCertificates.*
compute.zones.*

 

動画に出てきた例は、pubsub.topics.list と storage.bucket.create でした。AWSのaction風に書くと pubsub:listTopics, storage:createBucketでしょうか(実際に存在するものではありません)。

 

Permissionは、通常REST APIのMethodと1対1で対応しているようです。

Permissions usually, but not always, correspond 1:1 with REST methods. 

https://cloud.google.com/iam/docs/overview#permissions

 

例えば、以下に対応するPermissionはcompute.networks.insertだと思われます。

insert POST  /project/global/networks

https://cloud.google.com/compute/docs/reference/latest/#Networks

実際に触ってみる

では実際に触っていきます。Cloud IAMは、GCP Console、REST API、gcloudコマンドで設定ができます。注意点としては別のユーザのPermissionの設定には、ProjectのOwner権限が必要になります。

 

登場するProject:

example-project(仮名)

 

登場するIdentity:

(1) 今回の権限のテスト対象となるGoogle Account (マスクまたはtarget@example.com 仮名)

(2) 権限付与時に使用するOwner Roleを持った Google Account (owner@example.com 仮名)

 

登場するRoleとそのPermission

(1) Compute Security Admin(roles/compute.securityAdmin)

  • compute.firewalls.*
  • compute.networks.{get|list}
  • compute.operations.get
  • compute.projects.get
  • compute.regions.*
  • compute.routes.{get|list}
  • compute.sslCertificates.*
  • compute.zones.*

 (2) Compute Instance Admin(roles/compute.instanceAdmin)

  • compute.{global}addresses.{get|list|aggregatedList}
  • compute.autoscalers.*
  • compute.disks.{insert|delete|get|list|aggregatedList}
  • compute.disksTypes.{get|list|aggregatedList}
  • compute.globalOperations.{get|list}
  • compute.licenses.{list}
  • compute.machineTypes.{get|list|aggregatedList}
  • compute.networks.{get|list}
  • compute.images.{get|list}
  • compute.instances.*
  • compute.instanceGroups.*
  • compute.instanceGroupManagers.*
  • compute.instanceTemplates.*
  • compute.projects.get
  • compute.regions.{get|list}
  • compute.regionOperations.{get|list}
  • compute.subnetworks.{get|list|aggregatedList}
  • compute.zones.{get|list}
  • compute.zoneOperations.{get|list}

Also permits users to connect to an instance using SSH.

(3) Storage Object Viewer ※名前のみ

 

試す操作の流れ:

(1) owner@gmail.comで GCP Console から target@example.com に Compute Security Admin のRoleを設定

(2) target@example.com でGCP Console から ネットワークの一覧(許可されている操作)

(3) target@example.com でGCP Console から VMインスタンスの一覧(許可されていない操作)

(4) target@example.com で認証した gcloudコマンドから プロジェクト内のサーバ(test)にSSH(許可されていない操作)

(5) owner@example.com で GCP Console から target@example.com に Compute Instance Admin のRoleを追加

(6) target@example.com で GCP Console から インスタンスの一覧(新たに許可した操作)

(7) target@example.com で認証した gcloudコマンドから プロジェクト内のサーバ(test)にSSH(新たに許可した操作)

(8) owner@example.com で認証した gcloudコマンドから target@example.com に Storage Object Viewer のRoleを追加

(1) owner@example.comで GCP Console から target@example.com に Compute Security Admin のRoleを設定

GCPのConsoleの左上メニューからPermissionsを選びます。

 

 

Permisionsタブ(デフォルトで選択されている)の中から Add members ボタン をクリックします。

 

 

Roleがこれまでと違いOwner、Editor、Viewer以外も選べるようになっています。Compute Security Adminを選択して Add します。

 

 

これで、target@example.comにCompute Security Admin のRoleが付与されました。これまでのOwnerなどと並んで、Curated Roleごとに表示されるようです。

 

 

(2) target@example.com でGCP Console から ネットワークの一覧(許可されている操作)

この権限の状態で、実際に操作をしてみます。まずは、許可されている操作の確認としてネットワークの一覧が見れるか確認します。Compute Security Adminは、compute.networks.{get|list} のPermissionを持っているので、ネットワークの一覧が閲覧できます。(ただ、 compute.networks.insert権限はないため"ネットワークを作成"ボタンはグレーアウトされて押せなくなっています。)

 

 

(3) target@example.com でGCP Console から VMインスタンスの一覧(許可されていない操作)

許可されていない操作の確認として、 Compute EngineのVMインスタンスの一覧を見てみます。 Compute Security Adminには、 compute.instances.{get|list} のPermissionは含まれない You don't have permission to view the instances in this project とエラーが表示されます。

 

 

(4) target@example.com で認証した gcloudコマンドから プロジェクト内のサーバ(test)にSSH(許可されていない操作)

gcloudコマンドやGCP ConsoleからのSSHは、Compute Instance Admin(roles/compute.instanceAdmin) Roleが必要です。Compute Security Admin のRoleしか付与していないtarget@example.comからは接続できないはずです。

 

$ gcloud compute --project "example-project" ssh --zone "asia-east1-a" "test"
ERROR: (gcloud.compute.ssh) Could not fetch instance:
- The resource 'projects/example-project' was not found

 

エラーメッセージは若干わかりづらいものの予定通り失敗しました。(他の権限がなくてその手前でこけているのかもしれません)

(5) owner@example.com で GCP Console から target@example.com に Compute Instance Admin のRoleを追加

owner権限のGoogle Accountに戻って、target@example.comにCompute Instance AdminのRoleを追加してみます。PermissionのページからRoleを追加したいMemberのRoleの部分をクリックするとRoleが選べる状態になります(複数選択可)。今回は Compute Instance Admin にチェックを付けて Save します。 

 

 

Compute Security Adminと並んで、Compute Instance AdminのRoleが画面に現れ、追加したtarget@example.comがmemberとして表示されました。

 

(6) target@example.com で GCP Console から インスタンスの一覧(新たに許可した操作)

target@example.comに戻って(再ログインが必要な可能性あり)、先ほどはPermissionがなくて閲覧できなかったVMインスタンスの一覧 を見てみます。新しく付与したRoleのCompute Instance Admin は  compute.instances.* のPermissionを持っているため無事閲覧ができました。

 

(7) target@example.com で認証した gcloudコマンドから プロジェクト内のサーバにSSH(新たに許可した操作)

Compute Instance AdminにはSSHログインの権限がありますので、こちらもログインできるようになりました。

 

$ gcloud compute --project "example-project" ssh --zone "asia-east1-a" "test"
Warning: Permanently added 'x.x.x.x' (RSA) to the list of known hosts.
[hoge@test ~]$ 

(8) owner@example.com で認証した gcloudコマンドから target@example.com に Storage Object Viewer のRoleを追加

最後に、gcloudコマンドからCloud IAMの設定や確認をしてみます。 まだ、Cloud IAMはbetaとなるので、gcloudコマンドのアップデートとbetaコマンドのインストールをします。

 

$ gcloud components update

 

$ gcloud components update beta

 

まずはgcloud beta projects get-iam-policyコマンドで、現在のProjectに対する設定の確認をします。

 

$ gcloud beta projects get-iam-policy example-project
bindings:
- members:
  - serviceAccount:hogehoge@appspot.gserviceaccount.com
  role: roles/editor
- members:
  - user:owner@example.com
  role: roles/owner
- members:
  - serviceAccount:fugafuga@developer.gserviceaccount.com
  role: roles/viewer
- members:
  - user:target@example.com
  role: roles/compute.securityAdmin
- members:
  - user:target@example.com
  role: roles/compute.instanceAdmin
etag: HogeFuga
version: 1

 

次に、gcloud beta projects add-iam-policy-binding コマンドで設定を追加します。

 

$ gcloud beta projects add-iam-policy-binding example-project --member user:target@example.com --role roles/storage.objectViewer
(略)
- members:
  - user:target@example.com
  role: roles/compute.securityAdmin
- members:
  - user:target@example.com
  role: roles/compute.instanceAdmin
- members:
  - user:target@example.com
  role: roles/storage.objectViewer

 

コマンドの実行結果や、先ほども叩いた gcloud beta projects get-iam-policy で確認すると、role: roles/storage.objectViewer の記述が増えていることがわかります。他にもjsonを使った設定方法もあるようです。詳しくは、Access control via the gcloud tool をご覧ください。

Service Account とCloud IAM

Service Accountは人が介在しない状況で、アプリやGCEなどからサービスを使いたい場合に使います。記事が長くなってしまったので、Service AccountでのCloud IAMの利用は注意事項の引用で終わります。

Keep in mind that:

  • IAM roles are currently in Beta and not all services support IAM. For example, there are no IAM roles to grant access to BigQuery. We recommend using IAM only if there are IAM roles to support all the access the default service account needs. For example, if a default service account requires access to Google Cloud Storage and Google BigQuery, we recommend you use access scopes for now.

  • You must still set access scopes to authorize access from the instance. IAM roles do not replace access scopes. The level of access a service account has is determined by a combination of access scopes and IAM roles. Learn more about access scopes and IAM roles.

(引用: https://cloud.google.com/compute/docs/authentication?hl=ja#usingroles )

その他、試した所感

  • 嬉しいこと
    • Google AppsのGoogle AccountやGoogle Groupを利用可能
      • Google Appsを利用しているので相性がいい
      • 例えば、projectname_engineer@example.com グループや network_team@example.com グループとか security_team@example.com グループなどなどを作ってGroup単位での権限管理は楽にできそう
    • Resource Hierarchyの仕組みは、うまく設計ができれば便利そう
      • 例えば、network_team@example.comやsecurity_team@example.comをOrginizationレベルで管理に必要なRoleを付与することでプロジェクトを横断した管理が楽になりそう
  • 悩んでいること
  • 他、試していないが便利そうなのでこれから試したいもの

AWSと比べてしまうと、もう少し細かく制限ができるといいなと思う部分もありますが、Cloud IAMが出てきただけで非常に嬉しいです。Organizationなど管理が楽になる部分もありそうなので、ベストプラクティスの資料を読みつつ検証を進めGCPでのIAM戦略を練って、各Resourceへの対応がBetaではなくなってきたら順次各Projectの権限の見直しをしていく予定です。

 

ではでは!