如何使用Python脚本实现TOS的API签名

存储基础存储服务技术服务知识库
问题描述

如何通过TOS API实现对存储对象的GetObject

问题分析

对象存储会对每个访问的请求进行身份验证,因此您需要在请求中包含签名信息,如何通过Python脚本实现API的签名机制

解决方案

下面展示如何使用Python实现API签名并执行GetObject操作

完整Get Object示例代码如下:

import sys, os, base64, datetime, hashlib, hmac
import requests  # pip install requests
import json

# ************* REQUEST VALUES *************
method = 'GET'
host = 'bucket-name.tos-cn-beijing.volces.com'
region = 'cn-beijing'
endpoint = 'https://bucket-name.tos-cn-beijing.volces.com'


def sign(key, msg):
    return hmac.new(key, msg.encode('utf-8'), hashlib.sha256).digest()


def getSignatureKey(key, dateStamp, regionName, serviceName):
    kDate = sign(key.encode('utf-8'), dateStamp)
    kRegion = sign(kDate, regionName)
    kService = sign(kRegion, serviceName)
    kSigning = sign(kService, 'request')
    return kSigning


def sigv4(access_key, secret_key, service, request_parameters):
    if access_key is None or secret_key is None:
        print('No access key is available.')
        sys.exit()
    t = datetime.datetime.utcnow()
    current_date = t.strftime('%Y%m%dT%H%M%SZ')
    datestamp = t.strftime('%Y%m%d')  # Date w/o time, used in credential scope
    canonical_uri = '/test.txt'
    canonical_querystring = request_parameters
    signed_headers = 'host;range;x-tos-content-sha256;x-tos-date'
    payload_hash = hashlib.sha256(('').encode('utf-8')).hexdigest()
    content_type = 'bytes=0-10'
    # 注意:将需要参与签名的header的key全部转成小写, 然后以ASCII排序后以key-value的方式组合后换行构建。
    canonical_headers ='host:' + host + '\n' + 'range:' + content_type + '\n' +'x-tos-content-sha256:' + payload_hash +         '\n' + 'x-tos-date:' + current_date + '\n'
    canonical_request = method + '\n' + canonical_uri + '\n' + canonical_querystring + '\n' + canonical_headers + '\n' +       signed_headers + '\n' + payload_hash
    print("1.创建规范请求示例"+'\n',canonical_request)

    algorithm = 'TOS4-HMAC-SHA256'
    credential_scope = datestamp + '/' + region + '/' + service + '/' + 'request'
    string_to_sign = algorithm + '\n' + current_date + '\n' + credential_scope + '\n' + hashlib.sha256(
    canonical_request.encode('utf-8')).hexdigest()
    print("2.创建待签字符串示例"+'\n',string_to_sign)
    
    signing_key = getSignatureKey(secret_key, datestamp, region, service)
    signature = hmac.new(signing_key, (string_to_sign).encode('utf-8'), hashlib.sha256).hexdigest()
    print("3.Signature示例"+'\n',signature)

    authorization_header = algorithm + ' ' + 'Credential=' + access_key + '/' + credential_scope + ', ' + 'SignedHeaders='     + signed_headers + ', ' + 'Signature=' + signature
    print("4.Authorization示例"+'\n',authorization_header)
    
    headers = {'x-tos-date': current_date,
               'Authorization': authorization_header,
               'x-tos-Content-sha256': payload_hash,
               'range': content_type,
               }
    #打印返回状态码和内容
    print('Response code: %d\n' % r.status_code)
    print(json.dumps(parsed, indent=4, sort_keys=True))


if __name__ == "__main__":
    access_key = 'AKLTYThhOWZkNDU*********mMyZGE1MGMxMTliM2Q'
    secret_key = 'WW1Oak1tUTRNekV*********Raamd6WVRObU9UZzRZVGN4WVdRNU1ETQ=='
    service = 'tos'
    formatted_parameters=''
    sigv4(access_key, secret_key, service, formatted_parameters)

Python脚本API签名过程如下:

1.创建一个正规化的请求, 将下面的bucket-name换成自己的S3桶名字,最终CanonicalRequest示例

 GET
/test.txt

host:bucket-name.tos-cn-beijing.volces.com
range:bytes=0-10
x-tos-content-sha256:e3b0c44298fc1c149afbf4c8996fb92427ae41e4649b934ca495991b7852b855
x-tos-date:20220211T091839Z

host;range;x-tos-content-sha256;x-tos-date
e3b0c44298fc1c149afbf4c8996fb92427ae41e4649b934ca495991b7852b855

2.最终StringToSign

TOS4-HMAC-SHA256
20220211T091839Z
20220211/cn-beijing/tos/request
f7c9062a711358c2b0a525b2b76b478f87065537357089438a58789c168e4b11

3.最终Signature示例

 439e82fbeb16feb064a096b7a3916b21a57dc9aae281a0ae6c9c10062049c701

4.最终Authorization示例

TOS4-HMAC-SHA256 Credential=AKLTYThhOWZkNDUwOTdlNDkxOTkzMmMyZGE1MGMxMTliM2Q/20220211/cn-beijing/tos/request, SignedHeaders=host;range;x-tos-content-sha256;x-tos-date, Signature=439e82fbeb16feb064a096b7a3916b21a57dc9aae281a0ae6c9c10062049c701
参考连接

https://www.volcengine.com/docs/6349/74839 https://www.volcengine.com/docs/6349/74856 如果您有其他问题,欢迎您联系火山引擎技术支持服务

0
0
0
0
评论
未登录
看完啦,登录分享一下感受吧~
暂无评论