The unexpected permissions in the Viewer role on Google Cloud

guillaume blaquiere
Google Cloud - Community
3 min readJul 7, 2023

As the cloud evolves, security, permissions and IAM service follow suit. On Google Cloud, legacy roles (also named Basic Roles: Viewer, Owner and Editor), previously very used (and the only ones at the beginning), became deprecated.
Google Cloud even discourages using them because they are too wide and grant too many permissions.

In addition to having too many permissions, the naming of the role can mislead their behavior.

Ivan B alerted me to a strange behavior of the Viewer role. Its name should means:

You can only see things, but change nothing, run nothing, cost nothing to the project. Read only mode

In fact not. Lets deep dive

The list of the permissions

To understand what the Viewer role can do, we have to list the permissions of it. It’s pretty simple with gcloud

gcloud iam roles describe roles/viewer

More than 3300 permissions. This role is really too wide!!!

The unexpected possibilities

This list is too long… To reduce it, we can exclude the expected permissions (list, get, read)

gcloud iam roles describe roles/viewer \
| grep -v get | grep -v list | grep -v -i read

About 325 permissions, more acceptable.

If you have a closer look to this list, you can notice intriguing or even dangerous permissions

# Can invoke AI endpoints
aiplatform.endpoints.predict
automl.models.predict
cloudtranslate.XXX.XXXpredict # Many predict permissions
documentai.processorVersions.processBatch
documentai.processorVersions.processOnline
documentai.processors.processBatch
documentai.processors.processOnline
ml.models.predict
ml.versions.predict
retail.servingConfigs.predict
retail.placements.predict
speech.recognizers.recognize

# Run BigQuery jobs
bigquery.jobs.create

# Create Disk Snapshot
compute.disks.createSnapshot

# App Engine admin capabilities
appengine.runtimes.actAsAdmin

Most of these permissions can incur additional cost

  • Using AI models/API on documents, custom models or speech is not free!
  • BigQuery queries can be quickly expensive with on-demand mode!
  • Disk Snapshots reserve disk space, that you have to pay!
    After some tests, it appears that the current Disk Snapshot permission has changed and it is no longer used. A legacy permission in fact.

Finally, I’m not sure about the impact of the App Engine actAsAdmin permission, but the name is not reassuring!!

Permission removal

In his context , Ivan granted the Viewer role to allow some users to access projects and especially the billing of the project.
Because there are no predefined roles to only access the billing of a project, the Viewer role seemed to be the less dangerous permission with the Billing detail access.

So now, how to reduce the risk and the impact?

The IAM condition

One solution could be to exclude the use of some services to avoid the unexpected usage of expensive APIs.

Sadly, the list of services that support the IAM condition feature is very small and can’t help in this case.

The IAM deny policy

The deny policy is a pretty new feature (less than 1 year) and can discard permissions. It’s especially interesting when some users (like admin) inherit permissions on sensitive projects.

Here again, the list of supported permissions is limited. Only the disk snapshot can be denied.

The custom role

Finally, it’s not possible to limit the scope of the Viewer role. The ultimate solution is to create a custom role with only the permission required.

If you want to have a custom role similar to the Viewer role but without the dangerous permissions, you have to maintain the list of permissions and to follow the Google Cloud releases to keep the custom roles permissions list up to date.
Not a ideal solution

In the case of Ivan, it’s easier because only the project and billing access are required. In that case, you can create a very specific custom role.
That should not change, easier to maintain!

gcloud iam roles create project_biling \
--permissions=billing.resourceCosts.get,resourcemanager.projects.get \
--project=<projectId>

Replace <projectId> by your own project ID. You can also define a custom role at organization level for a wider use.

Conclusion

The weight of the legacy is sometimes surprising. Google Cloud discourages the usage of basic roles and after this experience with the Viewer role, I can’t agree more!

My recommendation is to follow the least privilege best practices, grant only the required permissions and avoid as much as you can to use too generic, too broad roles.
Silo permissions will save you!

--

--

guillaume blaquiere
Google Cloud - Community

GDE cloud platform, Group Data Architect @Carrefour, speaker, writer and polyglot developer, Google Cloud platform 3x certified, serverless addict and Go fan.