用python获取当前用户的硬币账户汇款余额

m4pnthwp  于 2022-12-21  发布在  Python
关注(0)|答案(1)|浏览(117)

我想通过Python获取当前用户的硬币账户汇款余额。
这是文件:https://developers.remitano.com/api-explorer/https://developers.remitano.com/docs/getting-started/access-key
这是我的代码:

import requests
import hashlib
import hmac
import base64
import time

ACCESS_KEY = "my_key"
SECRET_KEY = "my_SECRET"

# The API endpoint
API_ENDPOINT = "https://api.remitano.com/api/v1/users/coin_accounts"

def sign_request(method, url, body=""):
    # Set the Content-Type header to "application/json"
    headers = {
        "Content-Type": "application/json",
    }

    # Hash the request body with MD5, base64 encode the hash, and set the Content-MD5 header
    if body:
        m = hashlib.md5()
        m.update(body.encode())
        headers["Content-MD5"] = base64.b64encode(m.digest()).decode()

    # Set the "date" header to the current UTC time in the format "Wed, 21 Oct 2015 07:28:00 GMT"
    headers["date"] = time.strftime("%a, %d %b %Y %H:%M:%S %Z", time.gmtime())

    # Construct the request string
    request_string = f"{method},application/json,{headers.get('Content-MD5', '')},{url},{headers['date']}"

    # Use the SECRET_KEY to create a hash of the request string using the HMAC-SHA1 algorithm, base64 encode the hash, and set the "Authorization" header
    sig = hmac.new(SECRET_KEY.encode(), request_string.encode(), hashlib.sha1).digest()
    headers["Authorization"] = f"APIAuth {ACCESS_KEY}:{base64.b64encode(sig).decode()}"

    return headers

def make_request(method, url, body=""):
    headers = sign_request(method, url, body)
    return requests.request(method, url, headers=headers, data=body)

# Make a signed GET request
response = make_request("GET", API_ENDPOINT)
print(response.text) ```

I got the error: "{"error":"invalid signature"}" , how to fix this problem?

Thank you
ar5n3qh5

ar5n3qh51#

我认为有三个问题。
1.绝对URL(https://api.remitano.com/api/v1/users/coin_accounts)用于签名,但根据文档,应使用相对URL(/api/v1/users/coin_accounts
1.获取时间字符串时使用了%Z参数,但它返回当前时区。请将其替换为GMT-time.strftime("%a, %d %b %Y %H:%M:%S GMT", time.gmtime())
1.如果不存在请求主体,则代码将放置空字符串而不是Content-MD5,但实际上空字符串的MD5散列是d41d8cd98f00b204e9800998ecf8427e

import hashlib

print(hashlib.md5("".encode()).hexdigest())

新代码:

import requests
import hashlib
import hmac
import base64
import time

ACCESS_KEY = "my_key"
SECRET_KEY = "my_SECRET"

API_BASE_URL = "https://api.remitano.com"
# The API endpoint
API_ENDPOINT = "/api/v1/users/coin_accounts"

def sign_request(method, url, body=""):
    # Set the Content-Type header to "application/json"
    headers = {
        "Content-Type": "application/json",
    }

    # Hash the request body with MD5, base64 encode the hash,
    # and set the Content-MD5 header
    if body:
        m = hashlib.md5()
        m.update(body.encode())
        headers["Content-MD5"] = base64.b64encode(m.digest()).decode()
    else:
        # MD5 hash of an empty string - d41d8cd98f00b204e9800998ecf8427e
        # base64 of this hash is 1B2M2Y8AsgTpgAmY7PhCfg==
        headers["Content-MD5"] = "1B2M2Y8AsgTpgAmY7PhCfg=="

    # Set the "date" header to the current UTC time in
    # the format "Wed, 21 Oct 2015 07:28:00 GMT"
    headers["date"] = time.strftime("%a, %d %b %Y %H:%M:%S GMT", time.gmtime())

    # Construct the request string
    request_string = f"{method},application/json,{headers.get('Content-MD5')},{url},{headers['date']}"

    # Use the SECRET_KEY to create a hash of the request string
    # using the HMAC-SHA1 algorithm, base64 encode the hash,
    # and set the "Authorization" header
    sig = hmac.new(
        SECRET_KEY.encode(),
        request_string.encode(),
        hashlib.sha1).digest()

    headers["Authorization"] = f"APIAuth {ACCESS_KEY}:{base64.b64encode(sig).decode()}"

    return headers

def make_request(method, base_url, api_endpoint, body=""):
    headers = sign_request(method, api_endpoint, body)
    return requests.request(
        method,
        base_url + api_endpoint,
        headers=headers,
        data=body)

# Make a signed GET request
response = make_request("GET", API_BASE_URL, API_ENDPOINT)
print(response.text)

不幸的是,我不能自己检查代码是否工作,因为我没有API证书,而且要获得它们并不太容易。

相关问题