You need to enable JavaScript to run this app.
导航
签名机制
最近更新时间:2024.05.28 18:13:35首次发布时间:2024.05.28 18:13:35

本文介绍调用 OpenAPI 的签名机制。签名用于对请求参数进行加密处理,保证请求在传输过程中不被篡改。

签名构造方法

火山引擎在 SDK 中提供了签名函数或方法,开发者只需要在请求中提供访问密钥等信息, SDK 会自动计算请求签名,并将签名结果添加到请求中。这种方法简化了签名过程,降低了开发难度,尤其适用于不熟悉签名算法的开发者。

您也可以使用火山引擎开发者工具API Explorer在线发起调用,快速获取调用结果。

当您不可避免地需要自行编码构造签名时,可参考下方签名机制介绍,自行编码构造签名时,我们也为您提供了签名Demo示例:

若您在使用过程中遇到问题,可随时通过提交工单与我们的技术工程师沟通,我们将第一时间协助您解决问题。

签名机制

注意

签名需要对请求参数进行一系列处理,包括排序、拼接、加密等步骤。这种方法提供了更大的灵活性和可定制性,适用于开发者对签名算法有深入理解的情况。然而,手动签名需要开发者编写额外的代码来实现签名过程,可能会增加开发难度和出错的可能性,因此我们依然建议您使用SDK来调用API,尽量避免自行编写签名代码。若您需要了解签名计算的原理和具体过程,可参考以下文档。

火山引擎手动签名机制要求请求者对请求参数进行哈希值计算,经过加密后同 API 请求一起发送到服务器中,服务器将以同样的机制对收到的请求进行签名计算,并将其与请求者传来的签名进行比对,若签名未通过验证,请求将被拒绝。
开发者需按流程完成以下操作:
alt

获取访问密钥(Access Key)

访问密钥(Access Key)是请求火山引擎OpenAPI的安全凭证,参考 Access Key 管理获取账户的 Access Key ID 和 Secret Access Key。

构建规范请求字符串(CanonicalRequest)

在签名之前,首先需要将请求规范化,目的是让签名计算过程无异议。
构建规范化请求字符串,具体过程及伪代码如下:

CanonicalRequest = 
	HTTPRequestMethod + '\n' + 
	CanonicalURI + '\n' + 
	CanonicalQueryString + '\n' + 
	CanonicalHeaders + '\n' + 
	SignedHeaders + '\n' + 
	HexEncode(Hash(RequestPayload))

说明

Hash 代指 SHA256 算法HexEncode代指转 16 进制编码HMAC指代HMAC_SHA256

字段解释
HTTPRequestMethod指代 HTTP 请求的方法,例如:GET、POST 等。
CanonicalURI指代规范化后的 URI。如果 URI 为空,那么使用"/"作为绝对路径。在火山引擎中绝大多数接口的 URI 都为"/"。如果是复杂的 path,请通过 RFC3986 规范进行编码。

CanonicalQueryString

指代规范化后的 Query String。对于 Query String 的规范化大致的过程如下:

  • urlencode(通过 RFC3986 规范对每一个 Query String参数名称和参数值进行编码。
  • 按照 ASCII 字节顺序对参数名称严格排序,相同参数名的不同参数值需保持请求的原始顺序。
  • 将排序好的参数名称和参数值用=连接,按照排序结果将“参数对”用&连接。
    例如:CanonicalQueryString = "Action=ListUsers&Version=2018-01-01"

CanonicalHeaders

指代规范化后的Header。其中伪代码如下:CanonicalHeaders = CanonicalHeadersEntry0 + CanonicalHeadersEntry1 + ... + CanonicalHeadersEntryN其中CanonicalHeadersEntry = Lowercase(HeaderName) + ':' + Trimall(HeaderValue) + '\n' Lowcase 代表将 Header 的名称全部转化成小写,Trimall 表示去掉 Header 的值的前后多余的空格。

注意

特别注意:最后需要添加 "\n" 的换行符,Header 的顺序是以 headerName 的小写后 ASCII 排序。

SignedHeaders指参与签名的 Header,和 CanonicalHeaders 包含的 Header 是一一对应的,目的是指明哪些 Header 参与签名计算,从而忽略请求被 proxy 添加的额外 Header,其中 host、x-date 如果存在 Header 中则必选参与,伪代码如下:SignedHeaders = Lowercase(HeaderName0) + ';' + Lowercase(HeaderName1) + ";" + ... + Lowercase(HeaderNameN)
RequestPayload指代完整的请求的 Body。

构建待签名字符串(StringToSign)

签名字符串主要包含请求以及规范化请求的元数据信息,由签名算法、请求日期、信任状和规范化请求哈希值连接组成。
构建待签名字符串,伪代码如下:

StringToSign = 
	Algorithm + '\n' + 
	RequestDate + '\n' + 
	CredentialScope + '\n' + 
	HexEncode(Hash(CanonicalRequest))
字段解释
Algorithm指代签名的算法,目前火山引擎仅支持 HMAC-SHA256 的签名算法。
RequestDate指代请求 UTC 时间,即请求头公共参数中 X-Date 的取值,使用遵循 ISO 8601 标准的格式:YYYYMMDD'T'HHMMSS'Z' ,例如:20201103T104027Z
CredentialScope指代信任状,格式为: ${YYYYMMDD}/${region}/${service}/request,其中${YYYYMMDD}取 X-Date 中的日期,${region}${service} 参考公共参数的 Region 及 Service 取值,request为固定值。
CanonicalRequest构建规范请求字符串的结果。

计算签名密钥(kSigning)

在计算签名前,首先需使用访问密钥的Secret Access Key派生出签名密钥(kSigning)。

说明

访问密钥(Access Key)是请求火山引擎OpenAPI的安全凭证,参考 Access Key 管理获取账户的 Access Key ID 和 Secret Access Key。

计算派生签名密钥,计算过程及伪代码如下:

kSecret = *Your Secret Access Key*
kDate = HMAC(kSecret, Date)
kRegion = HMAC(kDate, Region)
kService = HMAC(kRegion, Service)
kSigning = HMAC(kService, "request")

说明

其中 Date 精确到日,与 RequestDate 中 YYYYMMDD 部分相同。

计算签名(Signature)

计算签名,伪代码如下:

Signature = HexEncode(HMAC(kSigning, StringToSign))

构建 Authorization

按如下格式构建 Header 的 Authorization 参数:

Authorization: HMAC-SHA256 Credential={AccessKeyId}/{CredentialScope}, SignedHeaders={SignedHeaders}, Signature={Signature}