Prepare and test your skills
Prepare and test your skills
Automated processes are non-interactive workloads that run without a person signing in, while human interaction depends on user accounts with passwords or federated login and access to a user interface. Service accounts provide the non-human identity for automation such as API scripts, delivery pipelines, runtime application code, and component-to-component calls. Using a service account instead of a human credential removes dependence on an individual login, allows least-privilege scoping to one function, and lets operations stop automation by disabling its identity.
API-only identities are service accounts that hold API credentials but cannot sign in through the user interface. A best practice is to create one dedicated service account for each API script and grant only the permissions that script needs, such as only access_data for a query script. Dedicated accounts compartmentalize access by script, so compromise of one script does not expose administrative functions. Stopping a script is done by disabling or deleting only that script's account without affecting other automation or human users. Automation identities still consume authorization resources by role, where an account with multiple roles consumes a license from the highest tier among those roles.
Cloud Deploy (opens in a new tab) execution identities are the service accounts that Cloud Deploy runs as to render manifests and deploy releases to runtimes. The identity is configured in the target definition with the executionConfigs.privatePool.serviceAccount property or the executionConfigs.defaultPool.serviceAccount property. Any account set in those properties must have the Cloud Deploy Runner role (roles/clouddeploy.jobRunner) in the Cloud Deploy project, plus runtime permissions such as Container Developer and Service Account User for Google Kubernetes Engine (GKE) or Cloud Run Developer and Service Account User for Cloud Run. Pipeline automation often uses more than one execution identity, such as separate accounts per delivery pipeline or specific accounts reserved for restricted targets like production.
Using an execution service account from a different project than the target requires explicit cross-project trust. The workflow depends on both the Cloud Deploy service agent and the Cloud Build service agent in sequence:
iam.serviceAccounts.actAs or the Service Account User role on each remote execution service account.iam.serviceAccounts.actAs or the Service Account User role on the execution service account.The render identity must be able to access the Cloud Storage bucket holding delivery pipelines, releases, and rollouts, while the deploy identity must be able to access that bucket and deploy to the target cluster.
Runtime service identities are service accounts attached to compute resources so code can call Google Cloud APIs without human credentials. A Compute Engine instance can have only one associated service account, and changing that account requires stopping and restarting the instance. A Cloud Run instance configures its identity with the serviceAccountName field in YAML or with deployment commands, and command-line automation can switch from user credentials to service account credentials with key-file activation.
Service accounts also serve as network identity for VPC firewall rules (opens in a new tab), which is distinct from arbitrary grouping with network tags. A network tag is an arbitrary attribute that any principal with instance-edit permission, such as a Compute Engine Instance Admin, can add or remove while the instance is running. A service account represents the instance identity and can only be used to start an instance by a principal who holds the Service Account User role on that account plus permission to create instances.
| Selector | What it represents | Who can change applicability | Operational effect |
|---|---|---|---|
| Network tags | Arbitrary attribute on the instance | Any principal who can edit the instance | Tags can be added or removed while running; rule applies to primary internal IP |
| Service accounts | Identity associated with the instance | Only principals granted Service Account User on that account | Changing the account requires stop and restart; GKE rules apply to the node, not the Pod |
Service accounts and network tags cannot be mixed in any firewall rule, so target service accounts cannot be combined with target network tags, and ingress rules with tag-based targets cannot use service-account sources.
Exam tip: A firewall rule cannot mix service accounts and network tags — a rule with target service accounts cannot use network-tag sources, and a rule with target network tags cannot use service-account sources.
Apigee hybrid (opens in a new tab) component identities show how production automation separates duties by function while non-production automation consolidates them. In production, each function uses its own Google service account key stored as a Kubernetes secret and referenced in configuration, including apigee-cassandra, apigee-guardrails, apigee-mart, apigee-metrics, apigee-runtime, apigee-synchronizer, and apigee-watcher. Both the mart component and the connectAgent component use the same apigee-mart service account, so traffic from those two components to Google Cloud flows under one shared automation identity. Environment-scoped components reference their secrets through serviceAccountSecretRefs for synchronizer and runtime, while org-level components use serviceAccountRef.
Non-production environments use a single apigee-non-prod service account for all components, including datastore, operator, org, telemetry, guardrails, mart, logger, metrics, watcher, backup, and task scheduler. The production pattern limits the scope of a leaked key to one component's permissions, while the non-production pattern trades isolation for simpler management. Credential configuration files for workload identity map each Kubernetes workload to its intended Google service account, so each automated component authenticates as only its assigned identity.
Automation running under standard user accounts (opens in a new tab) can be identified by the absence of human login characteristics. A standard account is a candidate for migration to an API-only service account when it meets all three conditions: it does not use an identity provider such as Google, SAML, or OpenID Connect; it has no password set for email credentials; and it has not logged in for the last seven days. Flagged accounts indicate workloads that are already operating non-interactively, such as long-running scripts using individually owned API credentials, but are still consuming user-style identities. Migration converts the eligible user into a service account that retains groups, roles, and API access without interactive login capability, and the migration control appears only for eligible accounts.
Evaluating security and least privilege for service accounts means deciding when a non-human identity needs its own narrowly scoped permissions tied to an application or resource lifecycle. A service account (opens in a new tab) that can access a Cloud Storage bucket with sensitive information is effectively as valuable as the bucket itself, so an attacker who cannot access the bucket directly may try to take control of the service account and then impersonate it. Least privilege therefore requires granting only the roles needed for the task at the smallest resource scope, enforcing separation of duties between users and service accounts, and minimizing long-lived credential exposure.
Privilege escalation through service accounts describes how a lower-privileged user gains higher-privileged access by using a service account's identity or permissions. When a user authenticates as the service account, code runs on an attached resource as the service account, or an allow policy is changed to grant access to the service account, the resulting access flows from the service account to the user-controlled action. The trust boundary that matters is between the human user's permissions and the service account's permissions, and escalation occurs whenever that boundary lets the user borrow more access than they own directly.
Three escalation categories create this risk:
Because running code on a VM with SSH access lets the user reach every resource the VM's attached service account can reach, shell access, deployment rights, and impersonation rights must be treated as equivalent to the data access they can unlock.
Least privilege for service accounts requires scoping each account to only the resources and operations its workload needs for its lifecycle. A user-managed service account should be created for a specific application or VM, granted narrow Identity and Access Management (IAM) roles, and attached to only the resources that need it. Access grants at the Google Cloud project or folder level must be avoided because they expand the blast radius beyond the intended bucket, instance, or function.
| Service account type | Scope of a role change | Least-privilege tradeoff |
|---|---|---|
| User-managed service account | Change applies only to workloads explicitly attached to that account | Narrow blast radius, preferred when fine-grained separation of duties is required |
| Compute Engine default service account | Change applies to all VMs running as the default account in the project | Broad blast radius and risk of over-privilege; replace Editor with less permissive roles after checking impact with Policy Simulator |
A Compute Engine default service account is shared by every VM that runs as that account, so granting it roles/storage.objectAdmin gives that access to all such VMs. Depending on organization policy, the default service account might automatically receive the Editor role (roles/editor), and automatic grants should be disabled by enforcing the iam.automaticIamGrantsForDefaultServiceAccounts organization policy constraint. For Compute Engine VMs, the recommended pattern is to create a new user-managed service account, attach it to the VM, and set the cloud-platform access scope so IAM permissions control access. Additional isolation follows the same principle: deploy agent applications in a dedicated project separate from critical resources, and use VPC Service Controls to define a service perimeter that controls which Cloud Run functions and services the agent service account can call.
Exam tip: Do not let a user impersonate, attach, or change the allow policy of a service account that is more privileged than the user, unless temporary elevation like sudo is explicitly intended.
Separation of duties and credential minimization require keeping human administration apart from the service account's runtime permissions and avoiding long-lived secrets. Permissions that let a user impersonate or attach a service account include iam.serviceAccounts.getAccessToken, iam.serviceAccounts.getOpenIdToken, iam.serviceAccounts.actAs, iam.serviceAccounts.implicitDelegation, iam.serviceAccounts.signBlob, iam.serviceAccounts.signJwt, iam.serviceAccountKeys.create, deploymentmanager.deployments.create, and cloudbuild.builds.create. Roles containing these permissions include Owner (roles/owner), Editor (roles/editor), Service Account User (roles/iam.serviceAccountUser), Service Account Token Creator (roles/iam.serviceAccountTokenCreator), Service Account Key Admin (roles/iam.serviceAccountKeyAdmin), Service Account Admin (roles/iam.serviceAccountAdmin), and Workload Identity User (roles/iam.workloadIdentityUser).
Protection depends on removing unnecessary paths to the credential and its metadata:
constraints/iam.disableServiceAccountKeyCreation and constraints/iam.disableServiceAccountKeyUpload and use short-lived impersonation or Workload Identity Federation instead.When these controls are combined, the human user manages the workload, the service account accesses only its assigned resources, and no standing key or broad project grant bridges the two identities.
Long-running and managed-service integration needs mandate a service account (opens in a new tab) when a workload must authenticate consistently without a person signing in. A service account is a non-human account managed by Identity and Access Management (IAM) and identified by a unique email address. Applications authenticate as the service account itself to make authorized API calls, and the service account then provides access to every Google Cloud resource its IAM roles permit.
Stable workload identity is the core reason to choose a service account over a user account for automation and long-lived applications. User accounts are managed in Cloud Identity or Google Workspace, have passwords, support browser sign-in, and follow joiner-mover-leaver processes where joining creates an account, moving updates it, and leaving suspends or deletes it. Service accounts have no password, cannot be used for browser sign-in, belong to a Google Cloud project as a resource, and are specific to Google Cloud. Because service accounts are not tied to any employee, a workload that runs overnight, on a schedule, or for months keeps the same identity even when the people who built it change teams or leave. Traffic flows from the application to Google Cloud APIs with the service account as the principal, while the authorization decision flows from IAM allow policies on the target resources back to the service account.
Attaching a service account to a managed compute resource is the preferred authentication method for production code running in Google Cloud. The attachment binds the workload to the identity so applications on the resource obtain short-lived credentials automatically without embedding secret keys or user credentials in instance images or application code. For most services, the service account must be attached when the resource that will run the code is created and cannot be added or replaced later. Compute Engine (opens in a new tab) is an exception because it lets an operator attach or change the service account on a virtual machine (VM) instance at any time.
A Compute Engine instance illustrates the attachment rules and dependencies that apply to managed integration:
instances.setServiceAccount.A single VM can have only one attached service account, but the same service account can be attached to multiple VMs. If the same service account is attached to multiple VMs, any change to the service account affects all VMs that use it, including granting or removing IAM roles. Google Kubernetes Engine (GKE) requires an additional mapping because GKE uses two account systems: a Kubernetes ServiceAccount object scoped to a namespace that identifies Pods with a short-lived bearer token, and an IAM service account scoped to a project that identifies callers to Google Cloud APIs. Workload Identity Federation for GKE connects the two systems by attaching IAM service accounts to Kubernetes Pods, so container code authenticates as a Google Cloud service account without using keys.
The service account type (opens in a new tab) determines who creates the identity, who manages it, and whether it is safe for long-term production use. Google Cloud provides user-managed accounts that operators create, default accounts created automatically when services are enabled, and service agents that Google Cloud creates and manages to let services act on behalf of customers.
| Type | Created and managed by | Integration use |
|---|---|---|
| User-managed service account | Operator creates in a project with the IAM API, Google Cloud console, or Google Cloud CLI; operator can update, disable, enable, and delete it | Dedicated identity for an application or VM, with email format service-account-name@project-id.iam.gserviceaccount.com; preferred for consistent authentication across environments |
| Default service account | Created automatically when App Engine or Compute Engine is enabled or used; operator is responsible for managing it after creation | Lets a service deploy jobs that access other resources, with emails such as project-id@appspot.gserviceaccount.com for App Engine and PROJECT_NUMBER-compute@developer.gserviceaccount.com for Compute Engine; attached by default to new VMs unless overridden |
| Service agent | Created and managed automatically by Google Cloud and assigned to the project, for example PROJECT_NUMBER@cloudservices.gserviceaccount.com for the Google APIs Service Agent | Runs internal Google processes on behalf of the customer; cannot be attached to a Compute Engine instance |
Default service accounts carry elevated risk for long-running integration because they may automatically receive the Editor role (roles/editor) on the project depending on organization policy configuration. Administrators should enforce the iam.automaticIamGrantsForDefaultServiceAccounts organization policy constraint to disable automatic grants, a default already enforced for organizations created after May 3, 2024. For stable, least-privilege integration, create a dedicated single-purpose service account for each application and avoid reusing default service accounts across multiple applications.
Authorization for an attached workload is limited by the intersection of IAM roles and access scopes, and both configurations must allow access before the application can reach a resource. IAM roles granted to the service account define fine-grained permissions on specific resources, such as Storage Object Viewer on a Cloud Storage bucket. Access scopes set on the Compute Engine instance define coarse-grained API boundaries that apply in addition to allow policies. The application depends on both controls, so a broad IAM grant does not override a narrow scope and a broad scope does not override a narrow IAM grant.
Common access scopes show why scopes alone are not a replacement for IAM:
https://www.googleapis.com/auth/cloud-platform views and manages data across Google Cloud services in the projecthttps://www.googleapis.com/auth/compute provides full control of Compute Engine methodshttps://www.googleapis.com/auth/compute.readonly provides read-only access to Compute Engine methodshttps://www.googleapis.com/auth/devstorage.read_only provides read-only access to Cloud Storagehttps://www.googleapis.com/auth/logging.write provides write access to Compute Engine logsIf an instance has the cloud-platform scope but its service account has only roles/compute.instanceAdmin.v1, roles/storage.objectViewer, and roles/compute.networkAdmin, applications on the instance have only the permissions in those three roles. Conversely, if the service account has roles/storage.objectAdmin but the instance has only the devstorage.read_only scope, requests from client libraries cannot manage objects because the scope does not authorize writes.
Exam tip: Access succeeds only when both the IAM role on the service account and the access scope on the Compute Engine instance allow it; a permissive setting on one side does not override a restriction on the other.
Use a service account for non-interactive workloads such as API scripts, delivery pipelines, runtime application code, and component-to-component calls that run without a person signing in. Using a service account instead of a human credential removes dependence on an individual login, allows least-privilege scoping to one function, and lets operations stop automation by disabling its identity.
No, service accounts and network tags cannot be mixed in any firewall rule, so a rule with target service accounts cannot use network-tag sources and a rule with target network tags cannot use service-account sources. Service accounts represent instance identity and changing the account requires stop and restart, while network tags are arbitrary attributes that can be added or removed while the instance is running.
Access succeeds only when both the Identity and Access Management (IAM) role on the service account and the access scope on the Compute Engine instance allow it, and a permissive setting on one side does not override a restriction on the other. For example, a service account with Storage Object Admin cannot manage objects if the instance has only read-only storage scope, and a broad scope does not override a narrow IAM grant.
An enterprise is refactoring its security architecture on Google Cloud to adhere to the principle of least privilege and strict separation of duties. Currently, developers run automated deployment pipelines and scheduled tasks using their personal corporate user accounts, which requires assigning them broad, standing permissions. Furthermore, developers have generated and downloaded service account JSON keys to authenticate external CI/CD runners, and they occasionally impersonate service accounts directly in production to resolve urgent incidents.
The security engineering team has established the following mandatory requirements:
Which strategy should the security engineer implement to satisfy these requirements?
Last updated