Manage IAM Permissions for GCP AI Notebooks

The gcp:notebooks/runtimeIamBinding:RuntimeIamBinding resource, part of the Pulumi GCP provider, manages IAM role bindings for Cloud AI Notebooks Runtime instances. It controls which identities can access specific runtimes by granting roles to lists of members. This guide focuses on two capabilities: granting roles to multiple members and adding individual members to roles.

RuntimeIamBinding is authoritative for a given role, meaning it replaces the member list for that role while preserving other roles on the runtime. Bindings reference existing runtime instances by name, project, and location. The examples are intentionally small. Combine them with your own runtime infrastructure and access policies.

Grant a role to multiple members

Teams managing notebook runtime access often grant the same role to multiple users or service accounts at once.

import * as pulumi from "@pulumi/pulumi";
import * as gcp from "@pulumi/gcp";

const binding = new gcp.notebooks.RuntimeIamBinding("binding", {
    project: runtime.project,
    location: runtime.location,
    runtimeName: runtime.name,
    role: "roles/viewer",
    members: ["user:jane@example.com"],
});
import pulumi
import pulumi_gcp as gcp

binding = gcp.notebooks.RuntimeIamBinding("binding",
    project=runtime["project"],
    location=runtime["location"],
    runtime_name=runtime["name"],
    role="roles/viewer",
    members=["user:jane@example.com"])
package main

import (
	"github.com/pulumi/pulumi-gcp/sdk/v9/go/gcp/notebooks"
	"github.com/pulumi/pulumi/sdk/v3/go/pulumi"
)

func main() {
	pulumi.Run(func(ctx *pulumi.Context) error {
		_, err := notebooks.NewRuntimeIamBinding(ctx, "binding", &notebooks.RuntimeIamBindingArgs{
			Project:     pulumi.Any(runtime.Project),
			Location:    pulumi.Any(runtime.Location),
			RuntimeName: pulumi.Any(runtime.Name),
			Role:        pulumi.String("roles/viewer"),
			Members: pulumi.StringArray{
				pulumi.String("user:jane@example.com"),
			},
		})
		if err != nil {
			return err
		}
		return nil
	})
}
using System.Collections.Generic;
using System.Linq;
using Pulumi;
using Gcp = Pulumi.Gcp;

return await Deployment.RunAsync(() => 
{
    var binding = new Gcp.Notebooks.RuntimeIamBinding("binding", new()
    {
        Project = runtime.Project,
        Location = runtime.Location,
        RuntimeName = runtime.Name,
        Role = "roles/viewer",
        Members = new[]
        {
            "user:jane@example.com",
        },
    });

});
package generated_program;

import com.pulumi.Context;
import com.pulumi.Pulumi;
import com.pulumi.core.Output;
import com.pulumi.gcp.notebooks.RuntimeIamBinding;
import com.pulumi.gcp.notebooks.RuntimeIamBindingArgs;
import java.util.List;
import java.util.ArrayList;
import java.util.Map;
import java.io.File;
import java.nio.file.Files;
import java.nio.file.Paths;

public class App {
    public static void main(String[] args) {
        Pulumi.run(App::stack);
    }

    public static void stack(Context ctx) {
        var binding = new RuntimeIamBinding("binding", RuntimeIamBindingArgs.builder()
            .project(runtime.project())
            .location(runtime.location())
            .runtimeName(runtime.name())
            .role("roles/viewer")
            .members("user:jane@example.com")
            .build());

    }
}
resources:
  binding:
    type: gcp:notebooks:RuntimeIamBinding
    properties:
      project: ${runtime.project}
      location: ${runtime.location}
      runtimeName: ${runtime.name}
      role: roles/viewer
      members:
        - user:jane@example.com

The role property specifies which permission set to grant (e.g., “roles/viewer”). The members array lists all identities that should have this role; RuntimeIamBinding replaces any previous member list for this role. The runtimeName, location, and project properties identify which runtime to configure.

Add a single member to a role

When onboarding individual users, you can add them one at a time without affecting existing members.

import * as pulumi from "@pulumi/pulumi";
import * as gcp from "@pulumi/gcp";

const member = new gcp.notebooks.RuntimeIamMember("member", {
    project: runtime.project,
    location: runtime.location,
    runtimeName: runtime.name,
    role: "roles/viewer",
    member: "user:jane@example.com",
});
import pulumi
import pulumi_gcp as gcp

member = gcp.notebooks.RuntimeIamMember("member",
    project=runtime["project"],
    location=runtime["location"],
    runtime_name=runtime["name"],
    role="roles/viewer",
    member="user:jane@example.com")
package main

import (
	"github.com/pulumi/pulumi-gcp/sdk/v9/go/gcp/notebooks"
	"github.com/pulumi/pulumi/sdk/v3/go/pulumi"
)

func main() {
	pulumi.Run(func(ctx *pulumi.Context) error {
		_, err := notebooks.NewRuntimeIamMember(ctx, "member", &notebooks.RuntimeIamMemberArgs{
			Project:     pulumi.Any(runtime.Project),
			Location:    pulumi.Any(runtime.Location),
			RuntimeName: pulumi.Any(runtime.Name),
			Role:        pulumi.String("roles/viewer"),
			Member:      pulumi.String("user:jane@example.com"),
		})
		if err != nil {
			return err
		}
		return nil
	})
}
using System.Collections.Generic;
using System.Linq;
using Pulumi;
using Gcp = Pulumi.Gcp;

return await Deployment.RunAsync(() => 
{
    var member = new Gcp.Notebooks.RuntimeIamMember("member", new()
    {
        Project = runtime.Project,
        Location = runtime.Location,
        RuntimeName = runtime.Name,
        Role = "roles/viewer",
        Member = "user:jane@example.com",
    });

});
package generated_program;

import com.pulumi.Context;
import com.pulumi.Pulumi;
import com.pulumi.core.Output;
import com.pulumi.gcp.notebooks.RuntimeIamMember;
import com.pulumi.gcp.notebooks.RuntimeIamMemberArgs;
import java.util.List;
import java.util.ArrayList;
import java.util.Map;
import java.io.File;
import java.nio.file.Files;
import java.nio.file.Paths;

public class App {
    public static void main(String[] args) {
        Pulumi.run(App::stack);
    }

    public static void stack(Context ctx) {
        var member = new RuntimeIamMember("member", RuntimeIamMemberArgs.builder()
            .project(runtime.project())
            .location(runtime.location())
            .runtimeName(runtime.name())
            .role("roles/viewer")
            .member("user:jane@example.com")
            .build());

    }
}
resources:
  member:
    type: gcp:notebooks:RuntimeIamMember
    properties:
      project: ${runtime.project}
      location: ${runtime.location}
      runtimeName: ${runtime.name}
      role: roles/viewer
      member: user:jane@example.com

RuntimeIamMember adds a single identity to a role without replacing other members who already have that role. The member property specifies one identity (user, service account, or group). This approach works alongside RuntimeIamBinding as long as they don’t manage the same role.

Beyond these examples

These snippets focus on specific runtime IAM features: role-based access control and member list management. They’re intentionally minimal rather than full access control policies.

The examples reference pre-existing infrastructure such as Cloud AI Notebooks Runtime instances. They focus on configuring IAM bindings rather than provisioning runtimes themselves.

To keep things focused, common IAM patterns are omitted, including:

  • Conditional IAM bindings (condition property)
  • Full policy replacement (RuntimeIamPolicy resource)
  • Custom role definitions

These omissions are intentional: the goal is to illustrate how runtime IAM bindings are wired, not provide drop-in access control modules. See the Runtime IAM Binding resource reference for all available configuration options.

Let's manage IAM Permissions for GCP AI Notebooks

Get started with Pulumi Cloud, then follow our quick setup guide to deploy this infrastructure.

Try Pulumi Cloud for FREE

Frequently Asked Questions

Resource Selection & Compatibility
Which IAM resource should I use for managing runtime permissions?

You have three options:

  1. RuntimeIamPolicy - Authoritative, replaces the entire IAM policy
  2. RuntimeIamBinding - Authoritative per role, preserves other roles
  3. RuntimeIamMember - Non-authoritative, preserves other members for the role
Can I use RuntimeIamPolicy with RuntimeIamBinding or RuntimeIamMember?
No, gcp.notebooks.RuntimeIamPolicy cannot be used together with gcp.notebooks.RuntimeIamBinding or gcp.notebooks.RuntimeIamMember because they will conflict over the IAM policy.
Can I use RuntimeIamBinding and RuntimeIamMember together?
Yes, but only if they don’t grant privileges to the same role. Using both for the same role will cause conflicts.
Can I create multiple RuntimeIamBinding resources for the same runtime?
Yes, but only one gcp.notebooks.RuntimeIamBinding can be used per role. You can have multiple bindings for different roles on the same runtime.
IAM Configuration
What member identity formats are supported?

The members property supports:

  • allUsers and allAuthenticatedUsers (special identifiers)
  • user:{email}, serviceAccount:{email}, group:{email}
  • domain:{domain} (G Suite domains)
  • projectOwner:{projectid}, projectEditor:{projectid}, projectViewer:{projectid}
  • Federated identities (e.g., principal://iam.googleapis.com/...)
How do I specify custom roles?
Custom roles must use the format [projects|organizations]/{parent-name}/roles/{role-name}. For example, projects/my-project/roles/my-custom-role or organizations/my-org/roles/my-custom-role.
Common Patterns
How do I grant viewer access to a specific user?
Create a gcp.notebooks.RuntimeIamBinding with role: "roles/viewer" and members: ["user:jane@example.com"], along with the required project, location, and runtimeName properties.
What properties are required to identify a runtime?
You need runtimeName (required), location (required), and project (required). If location or project aren’t specified, they’re parsed from the parent identifier or provider configuration.

Using a different cloud?

Explore iam guides for other cloud providers: