Rob Curtis
Rob Curtis

Reputation: 2265

Are legacy Cloud storage permissions required?

My confusion is why I need to include "Legacy" cloud storage roles. I prefer to avoid things that say "legacy" as it sounds like they'll be deprecated one of these days. Am I doing it wrong?

Here's my case:

I'm using service account from an appengine project to access files from cloud storage in another project. I'm using the Google Python Client to access the data.

I have assigned roles:

Storage Object Creator
Storage Object Viewer

But when I try to access files I get an error:

<service account> does not have storage.buckets.get access

It's only once I add "legacy roles" that it finally has access:

Storage legacy bucket writer
Storage legacy bucket reader

Here's the code:

def download_blob(bucket_name, source_blob_name, destination_file_name):
    """Downloads a blob from the bucket."""
    bucket = storage_client.get_bucket(bucket_name)
    blob = bucket.blob(source_blob_name)
    blob.download_to_filename(destination_file_name)

    print('Blob {} downloaded to {}.'.format(
          source_blob_name,
          destination_file_name))

def upload_blob(bucket_name, source_file_name, destination_blob_name):
    """Uploads a file to the bucket."""
    bucket = storage_client.get_bucket(bucket_name)
    blob = bucket.blob(destination_blob_name)
    blob.upload_from_filename(source_file_name)

    print('File {} uploaded to {}.'.format(
          source_file_name,
          destination_blob_name))

Thanks Rob

Upvotes: 7

Views: 3218

Answers (1)

Frank Natividad
Frank Natividad

Reputation: 624

W.r.t to your code, I've added additional comments below:

def download_blob(bucket_name, source_blob_name, 
destination_file_name):
    """Downloads a blob from the bucket."""
    """The following .get_bucket() requires storage.buckets.get permission."""
    bucket = storage_client.get_bucket(bucket_name)
    """The following doesn't"""
    bucket = storage_client.bucket(bucket_name)
    blob = bucket.blob(source_blob_name)
    blob.download_to_filename(destination_file_name)

    print('Blob {} downloaded to {}.'.format(
          source_blob_name,
          destination_file_name))

To re-iterate:

storage_client.get_bucket(bucket_name) requires permission for storage.bucket.get because it's performing a bucket metadata GET request.

storage_cilent.bucket(bucket_name) doesn't require this permission because it does not perform a GET request and only creates a bucket object with the name defined by bucket_name.

For upload to bypass storage.buckets.get issue:

from google.cloud import storage
storage_client = storage.Client()
bucket = storage_client.bucket(bucket_name)
blob = bucket.blob(source_blob_name)
blob.upload_from_filename(source_file_name)

Upvotes: 9

Related Questions