ESEN

← Fine print by exam

Google Cloud · Professional

PCSE · Professional Cloud Security Engineer

Google Cloud Certified - Professional Cloud Security Engineer

Secretless CI/CD deployments (OIDC federation)

Security● verified 34 days ago◌ no external reviewer

Without attribute_condition, GitHub's shared issuer lets any repo in

GitHub uses one issuer for all its customers, so validating the issuer isn't enough. Google requires a condition restricting tokens to your organization or repository. In Terraform the field is listed as optional and, without a condition, every valid credential from the issuer is accepted. Also, every claim you use in the condition or in a principalSet must be mapped in attribute_mapping.

⚑ Report outdated

See it in the pattern →

Security● verified 34 days ago◌ no external reviewer

Condition on numeric IDs, not on org and repo names

An organization or repository name can be released and registered again: if your condition says repository == 'org/repo', the next owner of that name inherits the trust. Google recommends immutable attributes, and GitHub sends repository_id and repository_owner_id in every token. It's the same reason GitHub changed the sub format for repos created since 2026-07-15.

⚑ Report outdated

See it in the pattern →

IAM● verified 34 days ago◌ no external reviewer

Direct access without a service account doesn't work with every service

You can grant roles directly to the federated principal, without a service account. But some APIs have limitations with federated identities, and for those you have to impersonate a service account. This module impersonates: it works with everything and leaves a single place to audit permissions. For that path Google asks you to enable four APIs: IAM, Resource Manager, Service Account Credentials and Security Token Service.

⚑ Report outdated

See it in the pattern →

Private object ingestion with expiration (TTL)

IAM● verified 34 days ago◌ no external reviewer

roles/storage.objectCreator is not enough to overwrite

Overwriting an existing object requires storage.objects.delete, which objectCreator lacks. For ingestion that's a feature (a compromised producer can't clobber files), but it breaks clients that retry with the same name. In S3, s3:PutObject does overwrite.

⚑ Report outdated

See it in the pattern →

Security● verified 34 days ago◌ no external reviewer

Uniform bucket-level access + public access prevention is the pair to declare

UBLA disables per-object ACLs (equivalent to BucketOwnerEnforced in S3) and is required for IAM Conditions. Public access prevention "enforced" blocks allUsers/allAuthenticatedUsers (equivalent to Block Public Access).

⚑ Report outdated

See it in the pattern →

Zero Trust private web API with passwordless PostgreSQL

IAM● verified 34 days ago◌ no external reviewer

Unlike Azure and AWS, the IAM login is created via API, without SQL

google_sql_user with type CLOUD_IAM_SERVICE_ACCOUNT creates the user from Terraform, and you also need roles/cloudsql.client and roles/cloudsql.instanceUser on the SA. What remains SQL are table permissions (GRANT), same as on the other clouds.

⚑ Report outdated

See it in the pattern →

IAM● verified 34 days ago◌ no external reviewer

"Internal" is a network control; authentication is separate IAM

With internal ingress, Cloud Run only accepts requests from sources such as VPCs in the same project, a VPC SC perimeter or an internal Application Load Balancer, and from products such as Cloud Scheduler, Cloud Tasks, Eventarc, Pub/Sub or Workflows if they're in the same project or perimeter and use the default run.app URL. Other sources, including the internet, can't reach it. But IAM authentication still applies: the client must present an ID token and its service account needs roles/run.invoker.

⚑ Report outdated

See it in the pattern →

Security● verified 34 days ago◌ no external reviewer

Enforce connectors so nobody connects "around" them

Automatic IAM authentication (without handling tokens manually) is done by Cloud SQL Auth Proxy or the Cloud SQL Language Connectors. connector_enforcement = REQUIRED rejects every direct connection to the IP, so the only path is with managed identity and TLS.

⚑ Report outdated

See it in the pattern →