生成StringToSign

3 投票
1 回答
1266 浏览
提问于 2025-04-17 01:18

我正在阅读关于如何将查询字符串传递给亚马逊的S3进行认证的文档,但我就是搞不懂StringToSign是怎么创建和使用的。我希望能有一个具体的例子来说明(1)如何构建StringToSign,以及(2)一旦我有了签名,如何调用表单。

为了举个例子,假设以下是我的信息:

Content-type='image/jpeg'
Bucket='test-bucket'
Key = 'filename'
ACL = 'public-read'
Expiration = '(never expires)'
Access Key = '12345'
Secret Password = '1a2b3c'
File = <file the user uploads>

我该如何从这些信息中获取StringToSign的值?一旦我得到了这个值,我又该如何创建以下表单:

<form action="??" method="post" enctype='multipart/form-data' class="upload-form">
    <input name="file" type="file"> 
</form>

另外,供参考:http://docs.amazonwebservices.com/AmazonS3/latest/dev/index.html?RESTAuthentication.html#RESTAuthenticationQueryStringAuth。谢谢。

1 个回答

2

根据你描述的情况,听起来你想通过POST方式支持浏览器上传文件。AWS的文档中有一部分专门讲这个内容,你可以查看这里

简单来说,你需要让你的存储桶(bucket)可以公开写入,或者提供一个策略文档。我假设你会选择使用策略文档(如果你不想这样,可以查看文档了解更多):

策略文档其实就是一段JSON格式的文本,用来验证请求的合法性,并且列出在上传数据之前必须满足的一些条件。例如:

"expiration": "2020-12-01T12:00:00.000Z",
"conditions": [
    {"acl": "public-read" },
    {"bucket": "test-bucket" },
    ["eq", "$key", "filename"],
  ]
}

这段内容的意思是,允许上传的操作在2020年之前有效,前提是这个存储桶只能公开读取,存储桶的名字是'test-bucket',而且文件的键(key)必须完全等于'filename'。

接下来,要生成你的签名,你需要把上面的JSON文档进行UTF-8编码,然后再进行base64编码,最后用你的秘密访问密钥(使用hmac sha1算法)对整个内容进行签名,最后再把这个结果进行一次base64编码。

policy_data = ... # stuff above
enc_policy = base64.b64_encode(policy_data.encode('utf8'))
signed = base64.b64_encode(hmac.new(AWS_SECRET, enc_policy, hashlib.sha1))

最后,你的表单大概会是这样的:

 <form action="http://test-bucket.s3.amazonaws.com/" method="post" enctype="multipart/form-data">
    Key to upload: <input type="input" name="key" value="filename" /><br />
    <input type="hidden" name="acl" value="public-read" />
    <input type="hidden" name="success_action_redirect" value="http://test-bucket.s3.amazonaws.com/successful_upload.html" />
    Content-Type: <input type="input" name="Content-Type" value="image/jpeg" /><br />
    <input type="hidden" name="AWSAccessKeyId" value="YOUR_ACCESS_KEY_ID" />
    <input type="hidden" name="Policy" value="<enc_policy from above>" />
    <input type="hidden" name="Signature" value="<signed from above>" />
    File: <input type="file" name="file" /> <br />
    <!-- The elements after this will be ignored -->
    <input type="submit" name="submit" value="Upload to Amazon S3" />
  </form>

撰写回答