You need to enable JavaScript to run this app.
导航

基于浏览器上传的表单中包含签名

最近更新时间2023.11.21 10:22:21

首次发布时间2022.08.08 17:38:55

TOS支持基于浏览器的POST上传对象请求,方便您将内容直接上传到TOS。使用POST上传对象时,您需要在表单中增加签名信息。

签名步骤

要构建表单中的签名,您需要执行如下操作:

  1. 该表单必须包含以下字段以提供签名和相关信息,以便TOS可以在收到请求时使用这些信息验证签名。

    元素名称

    描述

    是否必选

    policy

    Base64编码的安全策略,声明了POST请求必须满足的条件。对于签名计算,此策略是您的签名字符串。

    x-tos-algorithm

    指代签名的算法,目前仅支持HMAC-SHA256的签名算法。

    x-tos-credential

    提供AccessKey ID、日期、区域和服务信息。格式为<acces-key-id>/<date>/<region>/tos/request,date格式为yyyyMMdd。

    x-tos-date

    当前请求时间(UTC时间),格式为yyyyMMddTHHmmssZ。

    x-tos-signature

    计算出的签名。

    x-tos-security-token

    使用临时AK/SK鉴权时,必须加上该字段,值为SecurityToken。

  2. policy中必须包含以下元素。

    元素名称

    描述

    x-tos-algorithm

    指代签名的算法,目前仅支持HMAC-SHA256的签名算法。

    x-tos-credential

    提供AccessKey ID、日期,区域和服务信息。 格式为<acces-key-id>/<date>/<region>/tos/request,date格式为yyyyMMdd。

    x-tos-date

    当前请求时间(UTC 时间),格式为yyyyMMddTHHmmssZ。

  3. 计算表单的签名,policy就是签名字符串(StringToSign)。

计算签名

  1. 对policy内容进行UTF-8编码。
  2. 对UTF-8编码的policy进行Base64编码,生成StringToSign。
  3. 使用签名密钥(SigningKey)对StringToSign进行HMAC-SHA256计算。
  4. 将签名结果进行16 进制编码。
StringToSign = Base64(UTF-8-Encoding-Of(policy))
Signature = HexEncode(HMAC-SHA256(SigningKey, StringToSign))

Post Policy

Post请求的Policy表单域为一段经过UTF-8和Base64编码的JSON文本,声明了Post请求必须满足的条件,用于验证请求的合法性。虽然对于公开可写的Bucket上传时,Policy表单域为可选项,但强烈建议使用它来控制请求中允许的内容。
Post Policy示例如下:

{
  "expiration": "2022-01-01T12:00:00.000Z",
  "conditions": [
    {"bucket": "examplebucket" },    
    ["eq", "$acl", "public-read"],
    ["starts-with", "$key", "example"]
  ]
}

Post Policy中必须包含ExpirationConditions

Expiration

Expiration项指定了Policy的过期时间,以ISO8601 GMT时间表示。例如2022-01-01T12:00:00.000Z指定了Post请求必须在2022年1月1日12点之前。

Conditions

POST策略中的conditions是一个对象数组,每个对象都用于验证请求。您可以使用这些条件来限制请求中允许的内容。例如,上述策略条件需要以下内容:

  • 请求必须指定examplebucket存储桶名称。
  • 对象键名必须有example前缀。
  • 对象ACL必须设置为public-read

您在表单中指定的每个表单域(除了x-tos-signaturefilepolicy和具有x-ignore-前缀的域名称)必须出现在条件列表中。
Policy中支持的Conditions项请参见下表。

名称

参数类型

说明

x-tos-acl

String

指定表单提交中必须使用的ACL值。
支持的匹配类型:精确匹配、Starts With

x-tos-tagging

String

要添加到对象的指定标签集合。
支持的匹配类型:精确匹配、Starts With

bucket

String

指定可接受的桶的名称。
支持的匹配类型:精确匹配

content-length-range

Integer Array

指定上传内容的最小和最大size。
支持的匹配类型:指定范围

Cache-Control
Content-Type
Content-Disposition
Content-Encoding
Expires

String

HTTP标准头域。
支持的匹配类型:精确匹配、Starts With

key

String

对象名或者对象名的前缀。
支持的匹配类型:精确匹配、Starts With

success_action_redirect

string

成功上传后客户端重定向到的URL。
支持的匹配类型:精确匹配、Starts With

success_action_status

Integer

如果未指定success_action_redirect,则上传成功时返回给客户端的状态码。
支持的匹配类型:精确匹配

x-tos-algorithm

String

签名计算时必须使用的签名算法。对于TOS V4签名,该值为TOS4-HMAC-SHA256。
支持的匹配类型:精确匹配

x-tos-credential

String

除了您的访问密钥ID之外,这还提供了您在计算签名密钥以进行签名计算时使用的范围信息。
支持的匹配类型:精确匹配

x-tos-date

String

ISO8601格式的日期值。例如,20130728T000000Z。
与在创建签名密钥时使用的日期相同。也必须是表单域中指定的x-tos-date相同的值。
支持的匹配类型:精确匹配

x-tos-security-token

String

如果本次访问是使用STS临时授权方式,则需要指定该项为SecurityToken的值,同时AccessKeyId需要使用与之配对的临时AccessKey Id。
支持的匹配类型:精确匹配

x-tos-meta-*

String

用户指定的元数据。
支持的匹配类型:精确匹配、Starts With

x-tos-*

String

支持的匹配类型:精确匹配、Starts With

Content-MD5

String

上传文件的MD5哈希值。
支持的匹配类型:精确匹配、Starts With

如果您的工具包添加了更多表单字段(例如,Flash添加了filename),您必须将它们添加到POST Policy中。如果您可以控制此功能,请为该字段添加前缀x-ignore-

Conditions匹配方式

Condition匹配类型

精确匹配

表单域的值必须精确匹配Conditions中声明的值。例如指定key表单域的值必须为a,则可以设置为:{"key": "a"} ,等效于:["eq", "$key", "a"]

Starts With

该值必须以指定的值开头。以下示例表明对象名必须以user/user1开头:
["starts-with", "$key", "user/user1/"]

匹配任何内容

要将POST策略配置为允许表单字段中的任何内容,请使用starts-with空值 ("")。此示例允许的任何值 success_action_redirect
["starts-with", "$success_action_redirect", ""]

指定范围

对于接受范围的表单域,用逗号分隔上限和下限。以下示例允许文件大小为1到10 MiB:

["content-length-range", 1048576, 10485760]

签名示例

本章节以在examplebucket桶中上传exampleobject对象,并且设置对象ACL为公共可读为例,相关信息如下:

参数

桶名

examplebucket

对象名

exampleobject

区域

cn-beijing

时间

Sat, 1 Jan 2022 00:00:00 GMT

AccessKeyId

testAK

SecretAccessKey

testSK

创建policy

{
        "expiration": "2022-01-05T00:00:00.000Z",
        "conditions": [
        {"bucket": "examplebucket"},
        ["starts-with", "$key", "example"], 
        {"acl": "public-read"}, 
        {"success_action_redirect": "http://examplebucket.tos-cn-beijing.volces.com/successful_upload.html"},
        ["starts-with", "$Content-Type", "image/"], 
        ["starts-with", "$x-tos-meta-tag", ""], 
        
        {"x-tos-server-side-encryption": "AES256"}, 
        {"x-tos-credential": "testAK/20220101/cn-beijing/tos/request"}, 
        {"x-tos-algorithm": "TOS4-HMAC-SHA256"}, 
        {"x-tos-date": "20220101T000000Z"}
        ]
}

此POST策略对请求设置以下条件:

  • 上传必须在2022年01月05日凌晨之前进行。
  • 对象只能上传到examplebucket桶中, 存储桶必须在您在凭证范围(x-tos-credential表单参数)中指定的区域内,因为您提供的签名仅在此范围内有效。
  • 您可以上传对象名以example开头的任意文件,例如:exampleobject
  • ACL必须设置为public-read
  • 如果上传成功,浏览器将被重定向到http://examplebucket.tos-cn-beijing.volces.com/successful_upload.html
  • 上传的对象必须是image文件。
  • x-tos-meta-tag可以包含任意值。
  • x-tos-server-side-encryption必须设置为AES256

以下是此POST策略的Base64编码版本,签名计算中将其作为StringToSign。

ewogICAgICAgICJleHBpcmF0aW9uIjogIjIwMjItMDEtMDVUMDA6MDA6MDAuMDAwWiIsCiAgICAgICAgImNvbmRpdGlvbnMiOiBbCiAgICAgICAgeyJidWNrZXQiOiAiZXhhbXBsZWJ1Y2tldCJ9LAogICAgICAgIFsic3RhcnRzLXdpdGgiLCAiJGtleSIsICJleGFtcGxlIl0sIAogICAgICAgIHsiYWNsIjogInB1YmxpYy1yZWFkIn0sIAogICAgICAgIHsic3VjY2Vzc19hY3Rpb25fcmVkaXJlY3QiOiAiaHR0cDovL2V4YW1wbGVidWNrZXQudG9zLWNuLWJlaWppbmcudm9sY2VzLmNvbS9zdWNjZXNzZnVsX3VwbG9hZC5odG1sIn0sCiAgICAgICAgWyJzdGFydHMtd2l0aCIsICIkQ29udGVudC1UeXBlIiwgImltYWdlLyJdLCAKICAgICAgICBbInN0YXJ0cy13aXRoIiwgIiR4LXRvcy1tZXRhLXRhZyIsICIiXSwgCiAgICAgICAgCiAgICAgICAgeyJ4LXRvcy1zZXJ2ZXItc2lkZS1lbmNyeXB0aW9uIjogIkFFUzI1NiJ9LCAKICAgICAgICB7IngtdG9zLWNyZWRlbnRpYWwiOiAidGVzdEFLLzIwMjIwMTAxL2NuLWJlaWppbmcvdG9zL3JlcXVlc3QifSwgCiAgICAgICAgeyJ4LXRvcy1hbGdvcml0aG0iOiAiVE9TNC1ITUFDLVNIQTI1NiJ9LCAKICAgICAgICB7IngtdG9zLWRhdGUiOiAiMjAyMjAxMDFUMDAwMDAwWiJ9CiAgICAgICAgXQp9

SigningKey

HMAC-SHA256(HMAC-SHA256(HMAC-SHA256(HMAC-SHA256("testSK", "20220101"), "cn-beijing"), "tos"), "request")

Signture

94d72cb3bbd094f6d8eaa0b7e56905500029813febc9fee352474f88d093c3e5

POST请求

POST / HTTP/1.1
Host: examplebucket.tos-cn-beijing.volces.com
Accept-Encoding: encoding
Accept-Charset: character_set
Keep-Alive: 300
Connection: keep-alive
Content-Type: multipart/form-data; boundary=9431149156168
Content-Length: length

--9431149156168
Content-Disposition: form-data; name="key"

exampleobject
--9431149156168
Content-Disposition: form-data; name="success_action_redirect"

http://examplebucket.tos-cn-beijing.volces.com/successful_upload.html
--9431149156168
Content-Disposition: form-data; name="x-tos-meta-tag"

metadata
--9431149156168
Content-Disposition: form-data; name="Content-Type"

image/jpg
--9431149156168
Content-Disposition: form-data; name="x-tos-server-side-encryption"

AES256
--9431149156168
Content-Disposition: form-data; name="x-tos-algorithm"

TOS4-HMAC-SHA256
--9431149156168
Content-Disposition: form-data; name="x-tos-date"

20220101T000000Z
--9431149156168
Content-Disposition: form-data; name="x-tos-credential"

testAK/20220101/cn-beijing/tos/request
--9431149156168
Content-Disposition: form-data; name="policy"

ewogICAgICAgICJleHBpcmF0aW9uIjogIjIwMjItMDEtMDVUMDA6MDA6MDAuMDAwWiIsCiAgICAgICAgImNvbmRpdGlvbnMiOiBbCiAgICAgICAgeyJidWNrZXQiOiAiZXhhbXBsZWJ1Y2tldCJ9LAogICAgICAgIFsic3RhcnRzLXdpdGgiLCAiJGtleSIsICJleGFtcGxlIl0sIAogICAgICAgIHsiYWNsIjogInB1YmxpYy1yZWFkIn0sIAogICAgICAgIHsic3VjY2Vzc19hY3Rpb25fcmVkaXJlY3QiOiAiaHR0cDovL2V4YW1wbGVidWNrZXQudG9zLWNuLWJlaWppbmcudm9sY2VzLmNvbS9zdWNjZXNzZnVsX3VwbG9hZC5odG1sIn0sCiAgICAgICAgWyJzdGFydHMtd2l0aCIsICIkQ29udGVudC1UeXBlIiwgImltYWdlLyJdLCAKICAgICAgICBbInN0YXJ0cy13aXRoIiwgIiR4LXRvcy1tZXRhLXRhZyIsICIiXSwgCiAgICAgICAgCiAgICAgICAgeyJ4LXRvcy1zZXJ2ZXItc2lkZS1lbmNyeXB0aW9uIjogIkFFUzI1NiJ9LCAKICAgICAgICB7IngtdG9zLWNyZWRlbnRpYWwiOiAidGVzdEFLLzIwMjIwMTAxL2NuLWJlaWppbmcvdG9zL3JlcXVlc3QifSwgCiAgICAgICAgeyJ4LXRvcy1hbGdvcml0aG0iOiAiVE9TNC1ITUFDLVNIQTI1NiJ9LCAKICAgICAgICB7IngtdG9zLWRhdGUiOiAiMjAyMjAxMDFUMDAwMDAwWiJ9CiAgICAgICAgXQp9
--9431149156168
Content-Disposition: form-data;f name="x-tos-signature"

94d72cb3bbd094f6d8eaa0b7e56905500029813febc9fee352474f88d093c3e5
--9431149156168
Content-Disposition: form-data; name="file"; filename="MyFile.jpg"
Content-Type: image/jpeg

file_content
--9431149156168
Content-Disposition: form-data; name="submit"

Upload to TOS
--9431149156168--