How to upload a file to S3 and make it public using boto3?

48,225

Solution 1

I was able to do it using objectAcl API:

s3 = boto3.resource('s3')
object_acl = s3.ObjectAcl('bucket_name','object_key')
response = object_acl.put(ACL='public-read')

For details: http://boto3.readthedocs.io/en/latest/reference/services/s3.html#objectacl

Solution 2

To upload and set permission to publicly-readable in one step, you can use:

bucket.upload_file(file, key, ExtraArgs={'ACL':'public-read'})

See https://boto3.amazonaws.com/v1/documentation/api/latest/guide/s3-uploading-files.html#the-extraargs-parameter

Solution 3

Adi's way works. However, if you were like me, you might have run into an access denied issue. This is normally caused by broken permissions of the user. I fixed it by adding the following to the Action array:

"s3:GetObjectAcl",
"s3:PutObjectAcl"
Share:
48,225
Adi
Author by

Adi

Turning insomniac nights into code since 4 years.

Updated on July 05, 2022

Comments

  • Adi
    Adi almost 2 years

    I am able to upload an image file using:

    s3 = session.resource('s3')
    bucket = s3.Bucket(S3_BUCKET)
    bucket.upload_file(file, key)
    

    However, I want to make the file public too. I tried looking up for some functions to set ACL for the file but seems like boto3 have changes their API and removed some functions. Is there a way to do it in the latest release of boto3?

  • openwonk
    openwonk about 6 years
    One liner if you're only updating one object boto3.resource('s3').ObjectAcl('bucket_name','object_key').p‌​ut(ACL='public-read'‌​)
  • Dave Land
    Dave Land almost 5 years
    Doesn't work with boto3, anyway: botocore.exceptions.ParamValidationError: Parameter validation failed: Unknown parameter in input: "ExtraArgs", must be one of: ACL, Body, Bucket, CacheControl, ContentDisposition, ContentEncoding, ContentLanguage, ContentLength, ContentMD5, ContentType, Expires, GrantFullControl, GrantRead, GrantReadACP, GrantWriteACP, Key, Metadata, ServerSideEncryption, StorageClass, WebsiteRedirectLocation, SSECustomerAlgorithm, SSECustomerKey, SSECustomerKeyMD5, SSEKMSKeyId, RequestPayer, Tagging, ObjectLockMode, ObjectLockRetainUntilDate, ObjectLockLegalHoldStatus
  • Dave Land
    Dave Land almost 5 years
    This works as well as ACL = 'public-read': GrantRead = 'uri="http://acs.amazonaws.com/groups/global/AllUsers"'
  • Oded
    Oded almost 5 years
    For anyone reading this in the future, apparently public-read is the default, for now. See the giant warning in django-storages.readthedocs.io/en/latest/backends/…
  • fnaquira
    fnaquira over 4 years
    Where do you declare the Action array?
  • yardstick17
    yardstick17 over 3 years
    Worked for me with boto3
  • contrariwise
    contrariwise over 2 years
    It must be public-read and not public_read
  • Rylan Schaeffer
    Rylan Schaeffer about 2 years
    @Rohan, could you explain in more detail what this Action array is?
  • Rohan Bagchi
    Rohan Bagchi about 2 years
    Wrote this a long time ago and missed the comments. Sorry for the confusion. Check: docs.aws.amazon.com/IAM/latest/UserGuide/…
  • sebaslh12
    sebaslh12 about 2 years
    Works with boto3 and Object. Object(bucket, key).upload_file(path, ExtraArgs={'ACL':'public-read'})