How to get an pre-signed signature or link that have infinite expire in AWS. Or it is possible to create a permanent signature, using accesskey and secure key?
Except for AWS Access Keys, all other credentials, pre-signed URLs, etc. are temporary credentials.
All pre-signed URLs expire. The minimum expiration value is 1 second and the maximum is seven days (604,800 seconds).
Authenticating Requests: Using Query Parameters (AWS Signature Version 4)
Related
We have a lambda function with an execution role which has s3 access. Maximum session duration we kept with default option of 1 hour for the role.
When creating a s3 pre signed URL using this lambda function its observed that its valid for limited time only (less than 7 days). Sample code used from https://docs.aws.amazon.com/AWSJavaScriptSDK/latest/AWS/S3.html#getSignedUrl-property
Error observed is expired token issue.
We want it to be valid for 7 days. Is it possible to create s3 presigned URL from lambda function with nodejs?
A pre-signed URL is simply a 'normal' URL, with the addition of an Access Key and a Signature.
Amazon S3 will attempt to retrieve the object using the permissions associated with the provided Access Key. It verifies that the Signature matches both the request and the Secret Key associated with the Access Key.
This means that a pre-signed URL only has the same permissions as the underlying Access Key. If the Access Key only has a validity period of 1 hour, then the pre-signed URL will only work for 1 hour (since it is effectively using that Access Key).
To create a long-lived pre-signed URL, you will need to use equally long-lived credentials to generate the pre-signed URL.
By the way, it should be quite rare to need a pre-signed URL that is valid for a long period. A pre-signed URL should be generated as close as possible to when it will actually be used. For example, imagine a Dropbox-like service where a user is shown a list of files and they can click the filename to view the file. This page can be generated with pre-signed URLs as the links, each with a validity of perhaps 5-10 minutes. If the user refreshes the page, then new pre-signed URLs will be generated. There should be very little need to have pre-signed URLs valid for 7 days.
I have a s3 bucket that is private and I want specific user to have access to some objects in this bucket. What is the correct way to do that?
For individuals objects, you should use Pre-signed URL.
It allows the user who access the URL to issue a request as the person who pre-signed the URL (inheriting the permissions of the IAM user that generated the URL). It can be generated with SDK or CLI. It is valid for 3600s by default, but you can change this duration.
https://docs.aws.amazon.com/AmazonS3/latest/userguide/using-presigned-url.html
For multiple objetcs (if you want a path with wildcard), you can use Signed cookies. It need you to first implements a CloudFront distribution in front of you s3 bucket.
https://docs.aws.amazon.com/AmazonCloudFront/latest/DeveloperGuide/private-content-signed-cookies.html
CloudFront also allow to provide Signed URLs, which are different from S3 Presigned-URL: https://docs.aws.amazon.com/AmazonCloudFront/latest/DeveloperGuide/private-content-signed-urls.html
I want to create a s3 presigned url for reading an object in S3 to my clients. My application is running in ECS.
I want to use the ECS Task Role to create the S3 Pre-signed URL using python sdk like this
s3_client.generate_presigned_url('get_object',
Params={'Bucket': bucket_name,
'Key': object_name},
ExpiresIn=expiration)
Question:
If a client receives a presigned url right at the boundary of task role credential rotation wont it stop working ?
This article mentions to use permanent credentials - https://aws.amazon.com/premiumsupport/knowledge-center/presigned-url-s3-bucket-expiration/
If you created a presigned URL using a temporary token, then the URL expires when the token expires, even if the URL was created with a later expiration time.
Is there a way to make sure the presigned url is valid around the credential rotation boundary. I would like to provide atleast 10 mins of validity for the presigned url.
Note: This answer also recommends using IAM user credentials - Avoid pre-signed URL expiry when IAM role key rotates
I am thinking if there is any way ECS can take advantage of the Task Role ?
By using the ECS task role alone you are limited to whenever it expires for your signed URL. The credentials by default last 6 hours but you would need to validate the meta-data endpoint to understand how long is left.
An example response from the meta-data endpoint is below, as you can see there's a attribute containing the Expiration value.
{
"AccessKeyId": "ACCESS_KEY_ID",
"Expiration": "EXPIRATION_DATE",
"RoleArn": "TASK_ROLE_ARN",
"SecretAccessKey": "SECRET_ACCESS_KEY",
"Token": "SECURITY_TOKEN_STRING"
}
If it must be at least 10 minutes you can do this by creating another role (one that has the permissions) then using STS with assume-role. One of the argument you can pass is duration-seconds which provides upto 12 hours to be specified.
If you do this you can then assume the role and generate the presigned URL, which can be used for the length of the duration-seconds you specified. Your task role would have permissions to assume the role, which would mean you do not require an IAM user.
This only works if you require the link for shorter than 12 hours, otherwise you would have been limited to IAM user.
If a client receives a presigned url right at the boundary of task role credential rotation wont it stop working
Yes. Pre-signed urls are linked to the IAM entities that created them. Thus, in your case, if you generate the url just before IAM role expires, the url will expire as well. This happens regardless of expiry time of the url itself.
To avoid that, IAM user should be used to generated the pre-signed urls, since IAM user's credentials are permanent, unlike those of IAM roles.
You can also reduce the impact of the role's credentials expire time by increasing it to 12h for example:
I need to validate client and then generate temporary credentials (valid for few seconds) using which client can upload a file on my S3 bucket. I cannot create a user for the client. First I validate the client using OAuth and if the client is valid, I need to enable it to upload the file to S3. I know about presigned URL way, but am wondering is there another way.
using which client can upload a file on my S3 bucket.
..
know about presigned URL way, but am wondering is there another way
As already answered, I see two ways. The presigned url or assumed IAM role (e. g. though cognito or own/custom identity broker)
There is a significant difference.
While using the presign url, it allows the client to upload/update a very specific object defined by the url in S3. I like this approach because of its simplicity, more control over expiration and I imho more secure (less work around managing permissions)
When using the assumed credentials, you may give the user more privileges (e. g. upload any object with specific prefix, tag the object, ,..). However you may have more work to manage the permission and control the expiration (default lifetime of the assumed role credentials is 15min and can be prolonged to 12h).
First I validate the client using OAuth
Still you may create a presigned url using the assumed (temporary) identity
You could use Amazon Cognito with OAuth. This will assume an IAM role and generate temporary credentials for you.
Well I have a service which generate PDF files every day and I need to share a download link to this pdf files through email to send to our clients.
I am thinking to save these files to a s3 bucket, but we need to make sure these download links will works all the time, I went through Amazon S3 Pre-Signed URLs but asfaik presigned urls only valid for a maximum of 7 days but the links should be valid all the time, is there any other way to give access to s3 objects for longer term?
It's not possible to generate Amazon S3 pre-signed URLs with a validity of more than one week.
For longer term, you need to use CloudFront Signed URLs for which you can set an expiry date far in the future.
See Serving Private Content with Signed URLs and Signed Cookies and Using Signed URLs in the CloudFront documentation and Using CloudFront Signed URLs to Serve Private S3 Content on Medium.
You can create a custom download link that hits your backend service (use a jwt, or something else with expiry of your choice).
After validating the JWT on your server, generate a new S3 Pre-signed link(short expiry) and proceed with download.