当前页面
目录
signature = base64(HMAC-SHA256(secret_key, signingString))
其中:
signingString = http_method + "\n" + http_uri + "\n" + canonical_query_string + "\n" + access_key + "\n" + Date + "\n" + signed_headers_string
各参数说明:
http_method:HTTP协议中定义的GET、PUT、POST等请求方法,必须使用全大写的形式
http_uri:URL中的路径部分,使用标准URL解析从callback_url中提取的路径部分,要求必须以"/"开头,空路径为"/"
canonical_query_string:URL中的查询参数部分,使用标准URL解析从callback_url中提取的查询参数部分,如无查询参数则为空字符串
access_key:API标识符,固定为"vidu"
Date: 请求头中的Date(GMT格式)
signed_headers_string: 从请求头中按顺序取出X-HMAC-SIGNED-HEADERS指定的headers,并按以下格式拼接:
HeaderKey1 + ":" + HeaderValue1 + "\n" + HeaderKey2 + ":" + HeaderValue2 + "\n" + ... HeaderKeyN + ":" + HeaderValueN + "\n"
签名相关的请求头包括:
使用标准URL解析库解析完整的URL
http://127.0.0.1:8080/vidu/callback?name=james&age=36POST /vidu/callback name=james&age=36 vidu Tue, 06 May 2025 12:09:42 GMT Date:Tue, 06 May 2025 12:09:42 GMT x-request-nonce:123e4567-e89b-12d3-a456-426614174000
注意:
import base64 import hmac import hashlib import urllib.parse import uuid def generate_signature(secret_key, http_method, callback_url, date, headers, header_order): # 使用标准URL解析库解析URL parsed_url = urllib.parse.urlparse(callback_url) uri = parsed_url.path or "/" query_string = parsed_url.query or "" # 构建签名字符串 signing_string = ( f"{http_method}\n" f"{uri}\n" f"{query_string}\n" f"vidu\n" # 固定的access_key f"{date}\n" ) # 添加头部信息 for header in header_order: signing_string += f"{header}:{headers[header]}\n" # 计算签名 h = hmac.new( secret_key.encode('utf-8'), signing_string.encode('utf-8'), hashlib.sha256 ) # Base64编码 return base64.b64encode(h.digest()).decode('utf-8') # 示例使用 secret_key = 'your_secret_token' http_method = 'POST' callback_url = 'http://127.0.0.1:8080/vidu/callback?name=james&age=36' date = 'Tue, 06 May 2025 12:09:42 GMT' nonce = str(uuid.uuid4()) headers = { 'Date': date, 'x-request-nonce': nonce } header_order = ['Date', 'x-request-nonce'] signature = generate_signature(secret_key, http_method, callback_url, date, headers, header_order) print(signature) # 构建完整的HTTP请求头 request_headers = { 'Date': date, 'x-request-nonce': nonce, 'X-HMAC-SIGNED-HEADERS': ';'.join(header_order), 'X-HMAC-SIGNATURE': signature, 'X-HMAC-ALGORITHM': 'hmac-sha256', 'X-HMAC-ACCESS-KEY': 'vidu', 'Content-Type': 'application/json' }
package main import ( "crypto/hmac" "crypto/sha256" "encoding/base64" "fmt" "net/url" "strings" "time" "github.com/google/uuid" ) func generateSignature(secretKey, httpMethod, callbackURL, date string, headers map[string]string, headerOrder []string) (string, error) { // 使用标准URL解析库解析URL uri := "/" queryString := "" parsedURL, err := url.Parse(callbackURL) if err != nil { return "", err } // 获取Path部分 if parsedURL.Path != "" { uri = parsedURL.Path } // 获取查询参数部分 queryString = parsedURL.RawQuery var signingStringBuilder strings.Builder // 添加HTTP方法 signingStringBuilder.WriteString(httpMethod) signingStringBuilder.WriteString("\n") // 添加URI signingStringBuilder.WriteString(uri) signingStringBuilder.WriteString("\n") // 添加查询字符串 signingStringBuilder.WriteString(queryString) signingStringBuilder.WriteString("\n") // 添加访问密钥 signingStringBuilder.WriteString("vidu") signingStringBuilder.WriteString("\n") // 添加日期 signingStringBuilder.WriteString(date) signingStringBuilder.WriteString("\n") // 添加请求头 for _, header := range headerOrder { signingStringBuilder.WriteString(header) signingStringBuilder.WriteString(":") signingStringBuilder.WriteString(headers[header]) signingStringBuilder.WriteString("\n") } signingString := signingStringBuilder.String() // 生成HMAC-SHA256 h := hmac.New(sha256.New, []byte(secretKey)) h.Write([]byte(signingString)) // Base64编码 return base64.StdEncoding.EncodeToString(h.Sum(nil)), nil } func main() { secretKey := "your_secret_token" httpMethod := "POST" callbackURL := "http://127.0.0.1:8080/vidu/callback?name=james&age=36" currentTime := time.Now().UTC() date := currentTime.Format("Mon, 02 Jan 2006 15:04:05 GMT") nonce := uuid.New().String() headers := map[string]string{ "Date": date, "x-request-nonce": nonce, } headerOrder := []string{"Date", "x-request-nonce"} signature, err := generateSignature(secretKey, httpMethod, callbackURL, date, headers, headerOrder) if err != nil { fmt.Printf("Error generating signature: %v\n", err) return } fmt.Println("Signature:", signature) // 构建完整的HTTP请求头 requestHeaders := map[string]string{ "Date": date, "x-request-nonce": nonce, "X-HMAC-SIGNED-HEADERS": strings.Join(headerOrder, ";"), "X-HMAC-SIGNATURE": signature, "X-HMAC-ALGORITHM": "hmac-sha256", "X-HMAC-ACCESS-KEY": "vidu", "Content-Type": "application/json", } for k, v := range requestHeaders { fmt.Printf("%s: %s\n", k, v) } }