Amazon S3 - 如何检查预签名URL是否已过期?

D-M*_*arc 8 php amazon-s3 amazon-web-services pre-signed-url

如果我生成的Presigned URL已过期,我应该get_headers()(在PHP中)查看是否403 Forbidden抛出错误,否则使用相同的URL?或者这是一个坏主意,因为这是一个不必要的GET请求?我是否应该每次只重新生成一个新的Presigned URL?我有点困惑,因为似乎没有太多关于此的信息.

hel*_*loV 12

该URL具有到期时间.

签名版本2

https://bucket.s3.amazonaws.com/foo.txt?AWSAccessKeyId = AKIAABCDEFGHIJK&Expires = 1508608760&Signature = xxxxxxxxxxx

Expires给出UTC的时间.

$ date -d @1508608760
Sat Oct 21 17:59:20 UTC 2017
Run Code Online (Sandbox Code Playgroud)

您可以提取值并将其与UTC [ time()]中的当前时间进行比较,然后决定是否重新生成.


签名版本4

https://s3.amazonaws.com/bucket/foo.txt?X-Amz-Algorithm = AWS4-HMAC-SHA256&X-Amz-Expires = 3600&X-Amz-Credential = AKIAJRZXXXXXXXXus-east-1%2Fs3%2Faws4_request&X- Amz-SignedHeaders = host&X-Amz-Date = 20171021T190750Z&X-Amz-Signature = 8b84ae9b59e9f8a8d7066ecc39e797c8dc29848abcdef61717

X-Amz-Date以ISO 8601格式给出UTC时间.

您可以提取值,将其转换为epoch/UTC并将其与UTC [time()]中的当前时间进行比较,然后决定是否重新生成.

  • 这不是完整的答案 - 您必须将过期持续时间添加到“X-Amz-Date”值中才能获取过期时间 (5认同)
  • @ D-Marc`X-Amz-*`是更新的格式,称为签名版本4.在2014年之前推出AWS服务的区域支持那些加上旧版本的称为签名版本2的区域. (2认同)

Gus*_*Bus 5

接受的答案对于Signature Version 4来说不太正确。

如果您正在寻找一种在 js 中查找过期时间的方法,请继续阅读。

import { parseISO, addSeconds } from 'date-fns';

// get the query params: https://stackoverflow.com/a/901144/9362404
const params = new Proxy(new URLSearchParams(signedUrl), {
    get: (searchParams, prop) => searchParams.get(prop),
});
const creationDate = parseISO(params['X-Amz-Date']);
const expiresInSecs = Number(params['X-Amz-Expires']);

const expiryDate = addSeconds(creationDate, expiresInSecs);
const isExpired = expiryDate < new Date();
Run Code Online (Sandbox Code Playgroud)

一旦列出查询参数,发生的事情就很明显了:

// https://bucketname.s3.ap-southeast-2.amazonaws.com/file-name.pdf
// X-Amz-Algorithm=     AWS4-HMAC-SHA256
// X-Amz-Credential=    <aws-access-key>/20220722/ap-southeast-2/s3/aws4_request
// X-Amz-Date=          20220722T101759Z
// X-Amz-Expires=       259200
// X-Amz-Signature=     gobbeldygook-signature
// X-Amz-SignedHeaders= host
Run Code Online (Sandbox Code Playgroud)