Deploy Google Cloud Run Services

The gcp:cloudrun/service:Service resource, part of the Pulumi GCP provider, defines a Cloud Run service that deploys containers with automatic HTTPS endpoints and request-based autoscaling. This guide focuses on four capabilities: container deployment with traffic routing, Cloud SQL connections and public access policies, health probes and GPU acceleration, and multi-container deployments.

Cloud Run services reference container images from Artifact Registry or Container Registry and may connect to Cloud SQL instances or use service accounts for IAM permissions. The examples are intentionally small. Combine them with your own images, databases, and access policies.

Note: Google recommends using gcp.cloudrunv2.Service for new projects, which offers broader feature support. This resource is maintained for compatibility with existing deployments.

Deploy a container with traffic routing

Most deployments start with a container image and traffic configuration that creates an HTTPS endpoint and autoscales based on requests.

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

const _default = new gcp.cloudrun.Service("default", {
    name: "cloudrun-srv",
    location: "us-central1",
    template: {
        spec: {
            containers: [{
                image: "us-docker.pkg.dev/cloudrun/container/hello",
            }],
        },
    },
    traffics: [{
        percent: 100,
        latestRevision: true,
    }],
});
import pulumi
import pulumi_gcp as gcp

default = gcp.cloudrun.Service("default",
    name="cloudrun-srv",
    location="us-central1",
    template={
        "spec": {
            "containers": [{
                "image": "us-docker.pkg.dev/cloudrun/container/hello",
            }],
        },
    },
    traffics=[{
        "percent": 100,
        "latest_revision": True,
    }])
package main

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

func main() {
	pulumi.Run(func(ctx *pulumi.Context) error {
		_, err := cloudrun.NewService(ctx, "default", &cloudrun.ServiceArgs{
			Name:     pulumi.String("cloudrun-srv"),
			Location: pulumi.String("us-central1"),
			Template: &cloudrun.ServiceTemplateArgs{
				Spec: &cloudrun.ServiceTemplateSpecArgs{
					Containers: cloudrun.ServiceTemplateSpecContainerArray{
						&cloudrun.ServiceTemplateSpecContainerArgs{
							Image: pulumi.String("us-docker.pkg.dev/cloudrun/container/hello"),
						},
					},
				},
			},
			Traffics: cloudrun.ServiceTrafficArray{
				&cloudrun.ServiceTrafficArgs{
					Percent:        pulumi.Int(100),
					LatestRevision: pulumi.Bool(true),
				},
			},
		})
		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 @default = new Gcp.CloudRun.Service("default", new()
    {
        Name = "cloudrun-srv",
        Location = "us-central1",
        Template = new Gcp.CloudRun.Inputs.ServiceTemplateArgs
        {
            Spec = new Gcp.CloudRun.Inputs.ServiceTemplateSpecArgs
            {
                Containers = new[]
                {
                    new Gcp.CloudRun.Inputs.ServiceTemplateSpecContainerArgs
                    {
                        Image = "us-docker.pkg.dev/cloudrun/container/hello",
                    },
                },
            },
        },
        Traffics = new[]
        {
            new Gcp.CloudRun.Inputs.ServiceTrafficArgs
            {
                Percent = 100,
                LatestRevision = true,
            },
        },
    });

});
package generated_program;

import com.pulumi.Context;
import com.pulumi.Pulumi;
import com.pulumi.core.Output;
import com.pulumi.gcp.cloudrun.Service;
import com.pulumi.gcp.cloudrun.ServiceArgs;
import com.pulumi.gcp.cloudrun.inputs.ServiceTemplateArgs;
import com.pulumi.gcp.cloudrun.inputs.ServiceTemplateSpecArgs;
import com.pulumi.gcp.cloudrun.inputs.ServiceTrafficArgs;
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 default_ = new Service("default", ServiceArgs.builder()
            .name("cloudrun-srv")
            .location("us-central1")
            .template(ServiceTemplateArgs.builder()
                .spec(ServiceTemplateSpecArgs.builder()
                    .containers(ServiceTemplateSpecContainerArgs.builder()
                        .image("us-docker.pkg.dev/cloudrun/container/hello")
                        .build())
                    .build())
                .build())
            .traffics(ServiceTrafficArgs.builder()
                .percent(100)
                .latestRevision(true)
                .build())
            .build());

    }
}
resources:
  default:
    type: gcp:cloudrun:Service
    properties:
      name: cloudrun-srv
      location: us-central1
      template:
        spec:
          containers:
            - image: us-docker.pkg.dev/cloudrun/container/hello
      traffics:
        - percent: 100
          latestRevision: true

The template.spec.containers array defines which images to run. The traffics property controls how requests are distributed across revisions; setting latestRevision to true routes all traffic to the newest deployment. Cloud Run assigns a unique URL and scales containers from zero to match demand.

Connect to Cloud SQL databases

Applications needing persistent data connect to Cloud SQL through secure Unix sockets without exposing credentials.

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

const instance = new gcp.sql.DatabaseInstance("instance", {
    name: "cloudrun-sql",
    region: "us-east1",
    databaseVersion: "MYSQL_5_7",
    settings: {
        tier: "db-f1-micro",
    },
    deletionProtection: true,
});
const _default = new gcp.cloudrun.Service("default", {
    name: "cloudrun-srv",
    location: "us-central1",
    template: {
        spec: {
            containers: [{
                image: "us-docker.pkg.dev/cloudrun/container/hello",
            }],
        },
        metadata: {
            annotations: {
                "autoscaling.knative.dev/maxScale": "1000",
                "run.googleapis.com/cloudsql-instances": instance.connectionName,
                "run.googleapis.com/client-name": "demo",
            },
        },
    },
    autogenerateRevisionName: true,
});
import pulumi
import pulumi_gcp as gcp

instance = gcp.sql.DatabaseInstance("instance",
    name="cloudrun-sql",
    region="us-east1",
    database_version="MYSQL_5_7",
    settings={
        "tier": "db-f1-micro",
    },
    deletion_protection=True)
default = gcp.cloudrun.Service("default",
    name="cloudrun-srv",
    location="us-central1",
    template={
        "spec": {
            "containers": [{
                "image": "us-docker.pkg.dev/cloudrun/container/hello",
            }],
        },
        "metadata": {
            "annotations": {
                "autoscaling.knative.dev/maxScale": "1000",
                "run.googleapis.com/cloudsql-instances": instance.connection_name,
                "run.googleapis.com/client-name": "demo",
            },
        },
    },
    autogenerate_revision_name=True)
package main

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

func main() {
	pulumi.Run(func(ctx *pulumi.Context) error {
		instance, err := sql.NewDatabaseInstance(ctx, "instance", &sql.DatabaseInstanceArgs{
			Name:            pulumi.String("cloudrun-sql"),
			Region:          pulumi.String("us-east1"),
			DatabaseVersion: pulumi.String("MYSQL_5_7"),
			Settings: &sql.DatabaseInstanceSettingsArgs{
				Tier: pulumi.String("db-f1-micro"),
			},
			DeletionProtection: pulumi.Bool(true),
		})
		if err != nil {
			return err
		}
		_, err = cloudrun.NewService(ctx, "default", &cloudrun.ServiceArgs{
			Name:     pulumi.String("cloudrun-srv"),
			Location: pulumi.String("us-central1"),
			Template: &cloudrun.ServiceTemplateArgs{
				Spec: &cloudrun.ServiceTemplateSpecArgs{
					Containers: cloudrun.ServiceTemplateSpecContainerArray{
						&cloudrun.ServiceTemplateSpecContainerArgs{
							Image: pulumi.String("us-docker.pkg.dev/cloudrun/container/hello"),
						},
					},
				},
				Metadata: &cloudrun.ServiceTemplateMetadataArgs{
					Annotations: pulumi.StringMap{
						"autoscaling.knative.dev/maxScale":      pulumi.String("1000"),
						"run.googleapis.com/cloudsql-instances": instance.ConnectionName,
						"run.googleapis.com/client-name":        pulumi.String("demo"),
					},
				},
			},
			AutogenerateRevisionName: pulumi.Bool(true),
		})
		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 instance = new Gcp.Sql.DatabaseInstance("instance", new()
    {
        Name = "cloudrun-sql",
        Region = "us-east1",
        DatabaseVersion = "MYSQL_5_7",
        Settings = new Gcp.Sql.Inputs.DatabaseInstanceSettingsArgs
        {
            Tier = "db-f1-micro",
        },
        DeletionProtection = true,
    });

    var @default = new Gcp.CloudRun.Service("default", new()
    {
        Name = "cloudrun-srv",
        Location = "us-central1",
        Template = new Gcp.CloudRun.Inputs.ServiceTemplateArgs
        {
            Spec = new Gcp.CloudRun.Inputs.ServiceTemplateSpecArgs
            {
                Containers = new[]
                {
                    new Gcp.CloudRun.Inputs.ServiceTemplateSpecContainerArgs
                    {
                        Image = "us-docker.pkg.dev/cloudrun/container/hello",
                    },
                },
            },
            Metadata = new Gcp.CloudRun.Inputs.ServiceTemplateMetadataArgs
            {
                Annotations = 
                {
                    { "autoscaling.knative.dev/maxScale", "1000" },
                    { "run.googleapis.com/cloudsql-instances", instance.ConnectionName },
                    { "run.googleapis.com/client-name", "demo" },
                },
            },
        },
        AutogenerateRevisionName = true,
    });

});
package generated_program;

import com.pulumi.Context;
import com.pulumi.Pulumi;
import com.pulumi.core.Output;
import com.pulumi.gcp.sql.DatabaseInstance;
import com.pulumi.gcp.sql.DatabaseInstanceArgs;
import com.pulumi.gcp.sql.inputs.DatabaseInstanceSettingsArgs;
import com.pulumi.gcp.cloudrun.Service;
import com.pulumi.gcp.cloudrun.ServiceArgs;
import com.pulumi.gcp.cloudrun.inputs.ServiceTemplateArgs;
import com.pulumi.gcp.cloudrun.inputs.ServiceTemplateSpecArgs;
import com.pulumi.gcp.cloudrun.inputs.ServiceTemplateMetadataArgs;
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 instance = new DatabaseInstance("instance", DatabaseInstanceArgs.builder()
            .name("cloudrun-sql")
            .region("us-east1")
            .databaseVersion("MYSQL_5_7")
            .settings(DatabaseInstanceSettingsArgs.builder()
                .tier("db-f1-micro")
                .build())
            .deletionProtection(true)
            .build());

        var default_ = new Service("default", ServiceArgs.builder()
            .name("cloudrun-srv")
            .location("us-central1")
            .template(ServiceTemplateArgs.builder()
                .spec(ServiceTemplateSpecArgs.builder()
                    .containers(ServiceTemplateSpecContainerArgs.builder()
                        .image("us-docker.pkg.dev/cloudrun/container/hello")
                        .build())
                    .build())
                .metadata(ServiceTemplateMetadataArgs.builder()
                    .annotations(Map.ofEntries(
                        Map.entry("autoscaling.knative.dev/maxScale", "1000"),
                        Map.entry("run.googleapis.com/cloudsql-instances", instance.connectionName()),
                        Map.entry("run.googleapis.com/client-name", "demo")
                    ))
                    .build())
                .build())
            .autogenerateRevisionName(true)
            .build());

    }
}
resources:
  default:
    type: gcp:cloudrun:Service
    properties:
      name: cloudrun-srv
      location: us-central1
      template:
        spec:
          containers:
            - image: us-docker.pkg.dev/cloudrun/container/hello
        metadata:
          annotations:
            autoscaling.knative.dev/maxScale: '1000'
            run.googleapis.com/cloudsql-instances: ${instance.connectionName}
            run.googleapis.com/client-name: demo
      autogenerateRevisionName: true
  instance:
    type: gcp:sql:DatabaseInstance
    properties:
      name: cloudrun-sql
      region: us-east1
      databaseVersion: MYSQL_5_7
      settings:
        tier: db-f1-micro
      deletionProtection: true

The run.googleapis.com/cloudsql-instances annotation establishes a socket connection using the instance’s connectionName. Cloud Run mounts the socket at /cloudsql, allowing your application to connect without managing credentials. Setting autogenerateRevisionName to true lets Cloud Run generate revision names automatically.

Allow unauthenticated public access

Public services like webhooks accept requests from any caller by granting the run.invoker role to allUsers.

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

const _default = new gcp.cloudrun.Service("default", {
    name: "cloudrun-srv",
    location: "us-central1",
    template: {
        spec: {
            containers: [{
                image: "us-docker.pkg.dev/cloudrun/container/hello",
            }],
        },
    },
});
const noauth = gcp.organizations.getIAMPolicy({
    bindings: [{
        role: "roles/run.invoker",
        members: ["allUsers"],
    }],
});
const noauthIamPolicy = new gcp.cloudrun.IamPolicy("noauth", {
    location: _default.location,
    project: _default.project,
    service: _default.name,
    policyData: noauth.then(noauth => noauth.policyData),
});
import pulumi
import pulumi_gcp as gcp

default = gcp.cloudrun.Service("default",
    name="cloudrun-srv",
    location="us-central1",
    template={
        "spec": {
            "containers": [{
                "image": "us-docker.pkg.dev/cloudrun/container/hello",
            }],
        },
    })
noauth = gcp.organizations.get_iam_policy(bindings=[{
    "role": "roles/run.invoker",
    "members": ["allUsers"],
}])
noauth_iam_policy = gcp.cloudrun.IamPolicy("noauth",
    location=default.location,
    project=default.project,
    service=default.name,
    policy_data=noauth.policy_data)
package main

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

func main() {
	pulumi.Run(func(ctx *pulumi.Context) error {
		_default, err := cloudrun.NewService(ctx, "default", &cloudrun.ServiceArgs{
			Name:     pulumi.String("cloudrun-srv"),
			Location: pulumi.String("us-central1"),
			Template: &cloudrun.ServiceTemplateArgs{
				Spec: &cloudrun.ServiceTemplateSpecArgs{
					Containers: cloudrun.ServiceTemplateSpecContainerArray{
						&cloudrun.ServiceTemplateSpecContainerArgs{
							Image: pulumi.String("us-docker.pkg.dev/cloudrun/container/hello"),
						},
					},
				},
			},
		})
		if err != nil {
			return err
		}
		noauth, err := organizations.LookupIAMPolicy(ctx, &organizations.LookupIAMPolicyArgs{
			Bindings: []organizations.GetIAMPolicyBinding{
				{
					Role: "roles/run.invoker",
					Members: []string{
						"allUsers",
					},
				},
			},
		}, nil)
		if err != nil {
			return err
		}
		_, err = cloudrun.NewIamPolicy(ctx, "noauth", &cloudrun.IamPolicyArgs{
			Location:   _default.Location,
			Project:    _default.Project,
			Service:    _default.Name,
			PolicyData: pulumi.String(noauth.PolicyData),
		})
		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 @default = new Gcp.CloudRun.Service("default", new()
    {
        Name = "cloudrun-srv",
        Location = "us-central1",
        Template = new Gcp.CloudRun.Inputs.ServiceTemplateArgs
        {
            Spec = new Gcp.CloudRun.Inputs.ServiceTemplateSpecArgs
            {
                Containers = new[]
                {
                    new Gcp.CloudRun.Inputs.ServiceTemplateSpecContainerArgs
                    {
                        Image = "us-docker.pkg.dev/cloudrun/container/hello",
                    },
                },
            },
        },
    });

    var noauth = Gcp.Organizations.GetIAMPolicy.Invoke(new()
    {
        Bindings = new[]
        {
            new Gcp.Organizations.Inputs.GetIAMPolicyBindingInputArgs
            {
                Role = "roles/run.invoker",
                Members = new[]
                {
                    "allUsers",
                },
            },
        },
    });

    var noauthIamPolicy = new Gcp.CloudRun.IamPolicy("noauth", new()
    {
        Location = @default.Location,
        Project = @default.Project,
        Service = @default.Name,
        PolicyData = noauth.Apply(getIAMPolicyResult => getIAMPolicyResult.PolicyData),
    });

});
package generated_program;

import com.pulumi.Context;
import com.pulumi.Pulumi;
import com.pulumi.core.Output;
import com.pulumi.gcp.cloudrun.Service;
import com.pulumi.gcp.cloudrun.ServiceArgs;
import com.pulumi.gcp.cloudrun.inputs.ServiceTemplateArgs;
import com.pulumi.gcp.cloudrun.inputs.ServiceTemplateSpecArgs;
import com.pulumi.gcp.organizations.OrganizationsFunctions;
import com.pulumi.gcp.organizations.inputs.GetIAMPolicyArgs;
import com.pulumi.gcp.cloudrun.IamPolicy;
import com.pulumi.gcp.cloudrun.IamPolicyArgs;
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 default_ = new Service("default", ServiceArgs.builder()
            .name("cloudrun-srv")
            .location("us-central1")
            .template(ServiceTemplateArgs.builder()
                .spec(ServiceTemplateSpecArgs.builder()
                    .containers(ServiceTemplateSpecContainerArgs.builder()
                        .image("us-docker.pkg.dev/cloudrun/container/hello")
                        .build())
                    .build())
                .build())
            .build());

        final var noauth = OrganizationsFunctions.getIAMPolicy(GetIAMPolicyArgs.builder()
            .bindings(GetIAMPolicyBindingArgs.builder()
                .role("roles/run.invoker")
                .members("allUsers")
                .build())
            .build());

        var noauthIamPolicy = new IamPolicy("noauthIamPolicy", IamPolicyArgs.builder()
            .location(default_.location())
            .project(default_.project())
            .service(default_.name())
            .policyData(noauth.policyData())
            .build());

    }
}
resources:
  default:
    type: gcp:cloudrun:Service
    properties:
      name: cloudrun-srv
      location: us-central1
      template:
        spec:
          containers:
            - image: us-docker.pkg.dev/cloudrun/container/hello
  noauthIamPolicy:
    type: gcp:cloudrun:IamPolicy
    name: noauth
    properties:
      location: ${default.location}
      project: ${default.project}
      service: ${default.name}
      policyData: ${noauth.policyData}
variables:
  noauth:
    fn::invoke:
      function: gcp:organizations:getIAMPolicy
      arguments:
        bindings:
          - role: roles/run.invoker
            members:
              - allUsers

By default, Cloud Run requires authentication. The IamPolicy resource grants roles/run.invoker to allUsers, making the service publicly accessible. This bypasses Cloud Run’s authentication layer; use it only for services designed for public access.

Configure health checks with startup and liveness probes

Services with slow initialization use probes to signal readiness and detect failures.

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

const _default = new gcp.cloudrun.Service("default", {
    name: "cloudrun-srv",
    location: "us-central1",
    template: {
        spec: {
            containers: [{
                image: "us-docker.pkg.dev/cloudrun/container/hello",
                startupProbe: {
                    initialDelaySeconds: 0,
                    timeoutSeconds: 1,
                    periodSeconds: 3,
                    failureThreshold: 1,
                    tcpSocket: {
                        port: 8080,
                    },
                },
                livenessProbe: {
                    httpGet: {
                        path: "/",
                    },
                },
            }],
        },
    },
    traffics: [{
        percent: 100,
        latestRevision: true,
    }],
});
import pulumi
import pulumi_gcp as gcp

default = gcp.cloudrun.Service("default",
    name="cloudrun-srv",
    location="us-central1",
    template={
        "spec": {
            "containers": [{
                "image": "us-docker.pkg.dev/cloudrun/container/hello",
                "startup_probe": {
                    "initial_delay_seconds": 0,
                    "timeout_seconds": 1,
                    "period_seconds": 3,
                    "failure_threshold": 1,
                    "tcp_socket": {
                        "port": 8080,
                    },
                },
                "liveness_probe": {
                    "http_get": {
                        "path": "/",
                    },
                },
            }],
        },
    },
    traffics=[{
        "percent": 100,
        "latest_revision": True,
    }])
package main

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

func main() {
	pulumi.Run(func(ctx *pulumi.Context) error {
		_, err := cloudrun.NewService(ctx, "default", &cloudrun.ServiceArgs{
			Name:     pulumi.String("cloudrun-srv"),
			Location: pulumi.String("us-central1"),
			Template: &cloudrun.ServiceTemplateArgs{
				Spec: &cloudrun.ServiceTemplateSpecArgs{
					Containers: cloudrun.ServiceTemplateSpecContainerArray{
						&cloudrun.ServiceTemplateSpecContainerArgs{
							Image: pulumi.String("us-docker.pkg.dev/cloudrun/container/hello"),
							StartupProbe: &cloudrun.ServiceTemplateSpecContainerStartupProbeArgs{
								InitialDelaySeconds: pulumi.Int(0),
								TimeoutSeconds:      pulumi.Int(1),
								PeriodSeconds:       pulumi.Int(3),
								FailureThreshold:    pulumi.Int(1),
								TcpSocket: &cloudrun.ServiceTemplateSpecContainerStartupProbeTcpSocketArgs{
									Port: pulumi.Int(8080),
								},
							},
							LivenessProbe: &cloudrun.ServiceTemplateSpecContainerLivenessProbeArgs{
								HttpGet: &cloudrun.ServiceTemplateSpecContainerLivenessProbeHttpGetArgs{
									Path: pulumi.String("/"),
								},
							},
						},
					},
				},
			},
			Traffics: cloudrun.ServiceTrafficArray{
				&cloudrun.ServiceTrafficArgs{
					Percent:        pulumi.Int(100),
					LatestRevision: pulumi.Bool(true),
				},
			},
		})
		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 @default = new Gcp.CloudRun.Service("default", new()
    {
        Name = "cloudrun-srv",
        Location = "us-central1",
        Template = new Gcp.CloudRun.Inputs.ServiceTemplateArgs
        {
            Spec = new Gcp.CloudRun.Inputs.ServiceTemplateSpecArgs
            {
                Containers = new[]
                {
                    new Gcp.CloudRun.Inputs.ServiceTemplateSpecContainerArgs
                    {
                        Image = "us-docker.pkg.dev/cloudrun/container/hello",
                        StartupProbe = new Gcp.CloudRun.Inputs.ServiceTemplateSpecContainerStartupProbeArgs
                        {
                            InitialDelaySeconds = 0,
                            TimeoutSeconds = 1,
                            PeriodSeconds = 3,
                            FailureThreshold = 1,
                            TcpSocket = new Gcp.CloudRun.Inputs.ServiceTemplateSpecContainerStartupProbeTcpSocketArgs
                            {
                                Port = 8080,
                            },
                        },
                        LivenessProbe = new Gcp.CloudRun.Inputs.ServiceTemplateSpecContainerLivenessProbeArgs
                        {
                            HttpGet = new Gcp.CloudRun.Inputs.ServiceTemplateSpecContainerLivenessProbeHttpGetArgs
                            {
                                Path = "/",
                            },
                        },
                    },
                },
            },
        },
        Traffics = new[]
        {
            new Gcp.CloudRun.Inputs.ServiceTrafficArgs
            {
                Percent = 100,
                LatestRevision = true,
            },
        },
    });

});
package generated_program;

import com.pulumi.Context;
import com.pulumi.Pulumi;
import com.pulumi.core.Output;
import com.pulumi.gcp.cloudrun.Service;
import com.pulumi.gcp.cloudrun.ServiceArgs;
import com.pulumi.gcp.cloudrun.inputs.ServiceTemplateArgs;
import com.pulumi.gcp.cloudrun.inputs.ServiceTemplateSpecArgs;
import com.pulumi.gcp.cloudrun.inputs.ServiceTrafficArgs;
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 default_ = new Service("default", ServiceArgs.builder()
            .name("cloudrun-srv")
            .location("us-central1")
            .template(ServiceTemplateArgs.builder()
                .spec(ServiceTemplateSpecArgs.builder()
                    .containers(ServiceTemplateSpecContainerArgs.builder()
                        .image("us-docker.pkg.dev/cloudrun/container/hello")
                        .startupProbe(ServiceTemplateSpecContainerStartupProbeArgs.builder()
                            .initialDelaySeconds(0)
                            .timeoutSeconds(1)
                            .periodSeconds(3)
                            .failureThreshold(1)
                            .tcpSocket(ServiceTemplateSpecContainerStartupProbeTcpSocketArgs.builder()
                                .port(8080)
                                .build())
                            .build())
                        .livenessProbe(ServiceTemplateSpecContainerLivenessProbeArgs.builder()
                            .httpGet(ServiceTemplateSpecContainerLivenessProbeHttpGetArgs.builder()
                                .path("/")
                                .build())
                            .build())
                        .build())
                    .build())
                .build())
            .traffics(ServiceTrafficArgs.builder()
                .percent(100)
                .latestRevision(true)
                .build())
            .build());

    }
}
resources:
  default:
    type: gcp:cloudrun:Service
    properties:
      name: cloudrun-srv
      location: us-central1
      template:
        spec:
          containers:
            - image: us-docker.pkg.dev/cloudrun/container/hello
              startupProbe:
                initialDelaySeconds: 0
                timeoutSeconds: 1
                periodSeconds: 3
                failureThreshold: 1
                tcpSocket:
                  port: 8080
              livenessProbe:
                httpGet:
                  path: /
      traffics:
        - percent: 100
          latestRevision: true

The startupProbe delays traffic until the container passes its first check, preventing requests from reaching unready containers. The livenessProbe monitors ongoing health; failures trigger container restarts. Configure periodSeconds and failureThreshold to balance responsiveness against false positives.

Attach GPUs for ML inference workloads

Machine learning inference leverages GPUs to reduce latency and increase throughput.

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

const _default = new gcp.cloudrun.Service("default", {
    name: "cloudrun-srv",
    location: "us-central1",
    metadata: {
        annotations: {
            "run.googleapis.com/launch-stage": "BETA",
        },
    },
    template: {
        metadata: {
            annotations: {
                "autoscaling.knative.dev/maxScale": "1",
                "run.googleapis.com/cpu-throttling": "false",
            },
        },
        spec: {
            containers: [{
                image: "gcr.io/cloudrun/hello",
                resources: {
                    limits: {
                        cpu: "4",
                        memory: "16Gi",
                        "nvidia.com/gpu": "1",
                    },
                },
            }],
            nodeSelector: {
                "run.googleapis.com/accelerator": "nvidia-l4",
            },
        },
    },
});
import pulumi
import pulumi_gcp as gcp

default = gcp.cloudrun.Service("default",
    name="cloudrun-srv",
    location="us-central1",
    metadata={
        "annotations": {
            "run.googleapis.com/launch-stage": "BETA",
        },
    },
    template={
        "metadata": {
            "annotations": {
                "autoscaling.knative.dev/maxScale": "1",
                "run.googleapis.com/cpu-throttling": "false",
            },
        },
        "spec": {
            "containers": [{
                "image": "gcr.io/cloudrun/hello",
                "resources": {
                    "limits": {
                        "cpu": "4",
                        "memory": "16Gi",
                        "nvidia.com/gpu": "1",
                    },
                },
            }],
            "node_selector": {
                "run.googleapis.com/accelerator": "nvidia-l4",
            },
        },
    })
package main

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

func main() {
	pulumi.Run(func(ctx *pulumi.Context) error {
		_, err := cloudrun.NewService(ctx, "default", &cloudrun.ServiceArgs{
			Name:     pulumi.String("cloudrun-srv"),
			Location: pulumi.String("us-central1"),
			Metadata: &cloudrun.ServiceMetadataArgs{
				Annotations: pulumi.StringMap{
					"run.googleapis.com/launch-stage": pulumi.String("BETA"),
				},
			},
			Template: &cloudrun.ServiceTemplateArgs{
				Metadata: &cloudrun.ServiceTemplateMetadataArgs{
					Annotations: pulumi.StringMap{
						"autoscaling.knative.dev/maxScale":  pulumi.String("1"),
						"run.googleapis.com/cpu-throttling": pulumi.String("false"),
					},
				},
				Spec: &cloudrun.ServiceTemplateSpecArgs{
					Containers: cloudrun.ServiceTemplateSpecContainerArray{
						&cloudrun.ServiceTemplateSpecContainerArgs{
							Image: pulumi.String("gcr.io/cloudrun/hello"),
							Resources: &cloudrun.ServiceTemplateSpecContainerResourcesArgs{
								Limits: pulumi.StringMap{
									"cpu":            pulumi.String("4"),
									"memory":         pulumi.String("16Gi"),
									"nvidia.com/gpu": pulumi.String("1"),
								},
							},
						},
					},
					NodeSelector: pulumi.StringMap{
						"run.googleapis.com/accelerator": pulumi.String("nvidia-l4"),
					},
				},
			},
		})
		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 @default = new Gcp.CloudRun.Service("default", new()
    {
        Name = "cloudrun-srv",
        Location = "us-central1",
        Metadata = new Gcp.CloudRun.Inputs.ServiceMetadataArgs
        {
            Annotations = 
            {
                { "run.googleapis.com/launch-stage", "BETA" },
            },
        },
        Template = new Gcp.CloudRun.Inputs.ServiceTemplateArgs
        {
            Metadata = new Gcp.CloudRun.Inputs.ServiceTemplateMetadataArgs
            {
                Annotations = 
                {
                    { "autoscaling.knative.dev/maxScale", "1" },
                    { "run.googleapis.com/cpu-throttling", "false" },
                },
            },
            Spec = new Gcp.CloudRun.Inputs.ServiceTemplateSpecArgs
            {
                Containers = new[]
                {
                    new Gcp.CloudRun.Inputs.ServiceTemplateSpecContainerArgs
                    {
                        Image = "gcr.io/cloudrun/hello",
                        Resources = new Gcp.CloudRun.Inputs.ServiceTemplateSpecContainerResourcesArgs
                        {
                            Limits = 
                            {
                                { "cpu", "4" },
                                { "memory", "16Gi" },
                                { "nvidia.com/gpu", "1" },
                            },
                        },
                    },
                },
                NodeSelector = 
                {
                    { "run.googleapis.com/accelerator", "nvidia-l4" },
                },
            },
        },
    });

});
package generated_program;

import com.pulumi.Context;
import com.pulumi.Pulumi;
import com.pulumi.core.Output;
import com.pulumi.gcp.cloudrun.Service;
import com.pulumi.gcp.cloudrun.ServiceArgs;
import com.pulumi.gcp.cloudrun.inputs.ServiceMetadataArgs;
import com.pulumi.gcp.cloudrun.inputs.ServiceTemplateArgs;
import com.pulumi.gcp.cloudrun.inputs.ServiceTemplateMetadataArgs;
import com.pulumi.gcp.cloudrun.inputs.ServiceTemplateSpecArgs;
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 default_ = new Service("default", ServiceArgs.builder()
            .name("cloudrun-srv")
            .location("us-central1")
            .metadata(ServiceMetadataArgs.builder()
                .annotations(Map.of("run.googleapis.com/launch-stage", "BETA"))
                .build())
            .template(ServiceTemplateArgs.builder()
                .metadata(ServiceTemplateMetadataArgs.builder()
                    .annotations(Map.ofEntries(
                        Map.entry("autoscaling.knative.dev/maxScale", "1"),
                        Map.entry("run.googleapis.com/cpu-throttling", "false")
                    ))
                    .build())
                .spec(ServiceTemplateSpecArgs.builder()
                    .containers(ServiceTemplateSpecContainerArgs.builder()
                        .image("gcr.io/cloudrun/hello")
                        .resources(ServiceTemplateSpecContainerResourcesArgs.builder()
                            .limits(Map.ofEntries(
                                Map.entry("cpu", "4"),
                                Map.entry("memory", "16Gi"),
                                Map.entry("nvidia.com/gpu", "1")
                            ))
                            .build())
                        .build())
                    .nodeSelector(Map.of("run.googleapis.com/accelerator", "nvidia-l4"))
                    .build())
                .build())
            .build());

    }
}
resources:
  default:
    type: gcp:cloudrun:Service
    properties:
      name: cloudrun-srv
      location: us-central1
      metadata:
        annotations:
          run.googleapis.com/launch-stage: BETA
      template:
        metadata:
          annotations:
            autoscaling.knative.dev/maxScale: '1'
            run.googleapis.com/cpu-throttling: 'false'
        spec:
          containers:
            - image: gcr.io/cloudrun/hello
              resources:
                limits:
                  cpu: '4'
                  memory: 16Gi
                  nvidia.com/gpu: '1'
          nodeSelector:
            run.googleapis.com/accelerator: nvidia-l4

The resources.limits property requests GPU allocation using nvidia.com/gpu. The nodeSelector specifies which GPU type to use (here, nvidia-l4). Setting run.googleapis.com/cpu-throttling to false prevents CPU throttling during GPU operations. GPU features require the BETA launch stage annotation.

Run multiple containers with shared volumes

Applications can split responsibilities across containers, such as a main service and a logging sidecar.

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

const _default = new gcp.cloudrun.Service("default", {
    name: "cloudrun-srv",
    location: "us-central1",
    template: {
        metadata: {
            annotations: {
                "run.googleapis.com/container-dependencies": JSON.stringify({
                    "hello-1": ["hello-2"],
                }),
            },
        },
        spec: {
            containers: [
                {
                    name: "hello-1",
                    ports: [{
                        containerPort: 8080,
                    }],
                    image: "us-docker.pkg.dev/cloudrun/container/hello",
                    volumeMounts: [{
                        name: "shared-volume",
                        mountPath: "/mnt/shared",
                    }],
                },
                {
                    name: "hello-2",
                    image: "us-docker.pkg.dev/cloudrun/container/hello",
                    envs: [{
                        name: "PORT",
                        value: "8081",
                    }],
                    startupProbe: {
                        httpGet: {
                            port: 8081,
                        },
                    },
                    volumeMounts: [{
                        name: "shared-volume",
                        mountPath: "/mnt/shared",
                    }],
                },
            ],
            volumes: [{
                name: "shared-volume",
                emptyDir: {
                    medium: "Memory",
                    sizeLimit: "128Mi",
                },
            }],
        },
    },
});
import pulumi
import json
import pulumi_gcp as gcp

default = gcp.cloudrun.Service("default",
    name="cloudrun-srv",
    location="us-central1",
    template={
        "metadata": {
            "annotations": {
                "run.googleapis.com/container-dependencies": json.dumps({
                    "hello-1": ["hello-2"],
                }),
            },
        },
        "spec": {
            "containers": [
                {
                    "name": "hello-1",
                    "ports": [{
                        "container_port": 8080,
                    }],
                    "image": "us-docker.pkg.dev/cloudrun/container/hello",
                    "volume_mounts": [{
                        "name": "shared-volume",
                        "mount_path": "/mnt/shared",
                    }],
                },
                {
                    "name": "hello-2",
                    "image": "us-docker.pkg.dev/cloudrun/container/hello",
                    "envs": [{
                        "name": "PORT",
                        "value": "8081",
                    }],
                    "startup_probe": {
                        "http_get": {
                            "port": 8081,
                        },
                    },
                    "volume_mounts": [{
                        "name": "shared-volume",
                        "mount_path": "/mnt/shared",
                    }],
                },
            ],
            "volumes": [{
                "name": "shared-volume",
                "empty_dir": {
                    "medium": "Memory",
                    "size_limit": "128Mi",
                },
            }],
        },
    })
package main

import (
	"encoding/json"

	"github.com/pulumi/pulumi-gcp/sdk/v9/go/gcp/cloudrun"
	"github.com/pulumi/pulumi/sdk/v3/go/pulumi"
)

func main() {
	pulumi.Run(func(ctx *pulumi.Context) error {
		tmpJSON0, err := json.Marshal(map[string]interface{}{
			"hello-1": []string{
				"hello-2",
			},
		})
		if err != nil {
			return err
		}
		json0 := string(tmpJSON0)
		_, err = cloudrun.NewService(ctx, "default", &cloudrun.ServiceArgs{
			Name:     pulumi.String("cloudrun-srv"),
			Location: pulumi.String("us-central1"),
			Template: &cloudrun.ServiceTemplateArgs{
				Metadata: &cloudrun.ServiceTemplateMetadataArgs{
					Annotations: pulumi.StringMap{
						"run.googleapis.com/container-dependencies": pulumi.String(json0),
					},
				},
				Spec: &cloudrun.ServiceTemplateSpecArgs{
					Containers: cloudrun.ServiceTemplateSpecContainerArray{
						&cloudrun.ServiceTemplateSpecContainerArgs{
							Name: pulumi.String("hello-1"),
							Ports: cloudrun.ServiceTemplateSpecContainerPortArray{
								&cloudrun.ServiceTemplateSpecContainerPortArgs{
									ContainerPort: pulumi.Int(8080),
								},
							},
							Image: pulumi.String("us-docker.pkg.dev/cloudrun/container/hello"),
							VolumeMounts: cloudrun.ServiceTemplateSpecContainerVolumeMountArray{
								&cloudrun.ServiceTemplateSpecContainerVolumeMountArgs{
									Name:      pulumi.String("shared-volume"),
									MountPath: pulumi.String("/mnt/shared"),
								},
							},
						},
						&cloudrun.ServiceTemplateSpecContainerArgs{
							Name:  pulumi.String("hello-2"),
							Image: pulumi.String("us-docker.pkg.dev/cloudrun/container/hello"),
							Envs: cloudrun.ServiceTemplateSpecContainerEnvArray{
								&cloudrun.ServiceTemplateSpecContainerEnvArgs{
									Name:  pulumi.String("PORT"),
									Value: pulumi.String("8081"),
								},
							},
							StartupProbe: &cloudrun.ServiceTemplateSpecContainerStartupProbeArgs{
								HttpGet: &cloudrun.ServiceTemplateSpecContainerStartupProbeHttpGetArgs{
									Port: pulumi.Int(8081),
								},
							},
							VolumeMounts: cloudrun.ServiceTemplateSpecContainerVolumeMountArray{
								&cloudrun.ServiceTemplateSpecContainerVolumeMountArgs{
									Name:      pulumi.String("shared-volume"),
									MountPath: pulumi.String("/mnt/shared"),
								},
							},
						},
					},
					Volumes: cloudrun.ServiceTemplateSpecVolumeArray{
						&cloudrun.ServiceTemplateSpecVolumeArgs{
							Name: pulumi.String("shared-volume"),
							EmptyDir: &cloudrun.ServiceTemplateSpecVolumeEmptyDirArgs{
								Medium:    pulumi.String("Memory"),
								SizeLimit: pulumi.String("128Mi"),
							},
						},
					},
				},
			},
		})
		if err != nil {
			return err
		}
		return nil
	})
}
using System.Collections.Generic;
using System.Linq;
using System.Text.Json;
using Pulumi;
using Gcp = Pulumi.Gcp;

return await Deployment.RunAsync(() => 
{
    var @default = new Gcp.CloudRun.Service("default", new()
    {
        Name = "cloudrun-srv",
        Location = "us-central1",
        Template = new Gcp.CloudRun.Inputs.ServiceTemplateArgs
        {
            Metadata = new Gcp.CloudRun.Inputs.ServiceTemplateMetadataArgs
            {
                Annotations = 
                {
                    { "run.googleapis.com/container-dependencies", JsonSerializer.Serialize(new Dictionary<string, object?>
                    {
                        ["hello-1"] = new[]
                        {
                            "hello-2",
                        },
                    }) },
                },
            },
            Spec = new Gcp.CloudRun.Inputs.ServiceTemplateSpecArgs
            {
                Containers = new[]
                {
                    new Gcp.CloudRun.Inputs.ServiceTemplateSpecContainerArgs
                    {
                        Name = "hello-1",
                        Ports = new[]
                        {
                            new Gcp.CloudRun.Inputs.ServiceTemplateSpecContainerPortArgs
                            {
                                ContainerPort = 8080,
                            },
                        },
                        Image = "us-docker.pkg.dev/cloudrun/container/hello",
                        VolumeMounts = new[]
                        {
                            new Gcp.CloudRun.Inputs.ServiceTemplateSpecContainerVolumeMountArgs
                            {
                                Name = "shared-volume",
                                MountPath = "/mnt/shared",
                            },
                        },
                    },
                    new Gcp.CloudRun.Inputs.ServiceTemplateSpecContainerArgs
                    {
                        Name = "hello-2",
                        Image = "us-docker.pkg.dev/cloudrun/container/hello",
                        Envs = new[]
                        {
                            new Gcp.CloudRun.Inputs.ServiceTemplateSpecContainerEnvArgs
                            {
                                Name = "PORT",
                                Value = "8081",
                            },
                        },
                        StartupProbe = new Gcp.CloudRun.Inputs.ServiceTemplateSpecContainerStartupProbeArgs
                        {
                            HttpGet = new Gcp.CloudRun.Inputs.ServiceTemplateSpecContainerStartupProbeHttpGetArgs
                            {
                                Port = 8081,
                            },
                        },
                        VolumeMounts = new[]
                        {
                            new Gcp.CloudRun.Inputs.ServiceTemplateSpecContainerVolumeMountArgs
                            {
                                Name = "shared-volume",
                                MountPath = "/mnt/shared",
                            },
                        },
                    },
                },
                Volumes = new[]
                {
                    new Gcp.CloudRun.Inputs.ServiceTemplateSpecVolumeArgs
                    {
                        Name = "shared-volume",
                        EmptyDir = new Gcp.CloudRun.Inputs.ServiceTemplateSpecVolumeEmptyDirArgs
                        {
                            Medium = "Memory",
                            SizeLimit = "128Mi",
                        },
                    },
                },
            },
        },
    });

});
package generated_program;

import com.pulumi.Context;
import com.pulumi.Pulumi;
import com.pulumi.core.Output;
import com.pulumi.gcp.cloudrun.Service;
import com.pulumi.gcp.cloudrun.ServiceArgs;
import com.pulumi.gcp.cloudrun.inputs.ServiceTemplateArgs;
import com.pulumi.gcp.cloudrun.inputs.ServiceTemplateMetadataArgs;
import com.pulumi.gcp.cloudrun.inputs.ServiceTemplateSpecArgs;
import static com.pulumi.codegen.internal.Serialization.*;
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 default_ = new Service("default", ServiceArgs.builder()
            .name("cloudrun-srv")
            .location("us-central1")
            .template(ServiceTemplateArgs.builder()
                .metadata(ServiceTemplateMetadataArgs.builder()
                    .annotations(Map.of("run.googleapis.com/container-dependencies", serializeJson(
                        jsonObject(
                            jsonProperty("hello-1", jsonArray("hello-2"))
                        ))))
                    .build())
                .spec(ServiceTemplateSpecArgs.builder()
                    .containers(                    
                        ServiceTemplateSpecContainerArgs.builder()
                            .name("hello-1")
                            .ports(ServiceTemplateSpecContainerPortArgs.builder()
                                .containerPort(8080)
                                .build())
                            .image("us-docker.pkg.dev/cloudrun/container/hello")
                            .volumeMounts(ServiceTemplateSpecContainerVolumeMountArgs.builder()
                                .name("shared-volume")
                                .mountPath("/mnt/shared")
                                .build())
                            .build(),
                        ServiceTemplateSpecContainerArgs.builder()
                            .name("hello-2")
                            .image("us-docker.pkg.dev/cloudrun/container/hello")
                            .envs(ServiceTemplateSpecContainerEnvArgs.builder()
                                .name("PORT")
                                .value("8081")
                                .build())
                            .startupProbe(ServiceTemplateSpecContainerStartupProbeArgs.builder()
                                .httpGet(ServiceTemplateSpecContainerStartupProbeHttpGetArgs.builder()
                                    .port(8081)
                                    .build())
                                .build())
                            .volumeMounts(ServiceTemplateSpecContainerVolumeMountArgs.builder()
                                .name("shared-volume")
                                .mountPath("/mnt/shared")
                                .build())
                            .build())
                    .volumes(ServiceTemplateSpecVolumeArgs.builder()
                        .name("shared-volume")
                        .emptyDir(ServiceTemplateSpecVolumeEmptyDirArgs.builder()
                            .medium("Memory")
                            .sizeLimit("128Mi")
                            .build())
                        .build())
                    .build())
                .build())
            .build());

    }
}
resources:
  default:
    type: gcp:cloudrun:Service
    properties:
      name: cloudrun-srv
      location: us-central1
      template:
        metadata:
          annotations:
            run.googleapis.com/container-dependencies:
              fn::toJSON:
                hello-1:
                  - hello-2
        spec:
          containers:
            - name: hello-1
              ports:
                - containerPort: 8080
              image: us-docker.pkg.dev/cloudrun/container/hello
              volumeMounts:
                - name: shared-volume
                  mountPath: /mnt/shared
            - name: hello-2
              image: us-docker.pkg.dev/cloudrun/container/hello
              envs:
                - name: PORT
                  value: '8081'
              startupProbe:
                httpGet:
                  port: 8081
              volumeMounts:
                - name: shared-volume
                  mountPath: /mnt/shared
          volumes:
            - name: shared-volume
              emptyDir:
                medium: Memory
                sizeLimit: 128Mi

The containers array defines multiple containers within one service. The run.googleapis.com/container-dependencies annotation controls startup order. The volumes property creates shared storage; emptyDir provides in-memory storage that both containers can access through volumeMounts.

Beyond these examples

These snippets focus on specific Cloud Run service features: container deployment and traffic routing, Cloud SQL integration and IAM policies, health probes and GPU acceleration, and multi-container sidecars. They’re intentionally minimal rather than full application deployments.

The examples may reference pre-existing infrastructure such as Cloud SQL instances, container images in Artifact Registry or Container Registry, and service accounts with appropriate IAM roles. They focus on configuring the service rather than provisioning everything around it.

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

  • Environment variables and secrets (env, envFrom)
  • Custom domains and SSL certificates
  • VPC connectors for private networking
  • Service account assignment (serviceAccountName)
  • Resource limits (CPU, memory) beyond GPU example
  • Volume types beyond emptyDir (secrets, configMaps)

These omissions are intentional: the goal is to illustrate how each Cloud Run feature is wired, not provide drop-in production modules. See the Cloud Run Service resource reference for all available configuration options.

Let's deploy Google Cloud Run Services

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

Try Pulumi Cloud for FREE

Frequently Asked Questions

Migration & Versioning
Should I use this resource or cloudrunv2.Service?
Use gcp.cloudrunv2.Service instead. The v2 resource offers better developer experience and broader support for Cloud Run features compared to this v1 resource.
Resource Configuration & Immutability
What properties can't I change after creating a service?
The name, location, and project properties are immutable and cannot be updated after creation. Changes to these properties require replacing the resource.
Why am I getting an error with autogenerateRevisionName?
You cannot set autogenerateRevisionName to true while also setting template.metadata.name. Either enable autogeneration and omit the revision name, or disable it and provide an explicit name.
Integrations & Access Control
How do I connect my service to Cloud SQL?
Add the Cloud SQL instance connection name to template.metadata.annotations using the key run.googleapis.com/cloudsql-instances.
How do I make my service publicly accessible without authentication?
Grant the roles/run.invoker role to allUsers using an IAM policy on the service.
How do I integrate my service with Pub/Sub?
Create a Pub/Sub push subscription with your service URL as the pushEndpoint, and configure oidcToken authentication with a service account that has the roles/run.invoker role.
How do I enable Identity-Aware Proxy for my service?
Add two annotations to metadata.annotations: run.googleapis.com/launch-stage set to BETA and run.googleapis.com/iap-enabled set to true.
Advanced Container Configuration
How do I use GPUs with my Cloud Run service?
Configure three elements: set the GPU limit in containers.resources.limits (e.g., nvidia.com/gpu: "1"), specify the accelerator in nodeSelector (e.g., run.googleapis.com/accelerator: "nvidia-l4"), and add annotations for run.googleapis.com/launch-stage: "BETA" and run.googleapis.com/cpu-throttling: "false".
What's the difference between startup, liveness, and readiness probes?
startupProbe checks initial container readiness (supports tcpSocket and httpGet), livenessProbe performs ongoing health checks (supports httpGet), and readinessProbe determines traffic readiness (supports grpc, requires run.googleapis.com/launch-stage: "BETA" annotation).
How do I run multiple containers in a single service?
Define multiple containers in template.spec.containers, specify container startup dependencies using the run.googleapis.com/container-dependencies annotation in template.metadata.annotations, and optionally configure shared volumes using emptyDir in template.spec.volumes.

Using a different cloud?

Explore serverless guides for other cloud providers: