Coinbase Pro API - неверная подпись

Это отредактировано из оригинального сообщения:

Из документов:

Подписание сообщения Заголовок CB-ACCESS-SIGN генерируется путем создания sha256 HMAC с использованием секретного ключа, декодированного с помощью base64, в строке прехеширования timestamp + method + requestPath + body (где + представляет собой конкатенацию строк) и base64-кодирования вывода. Значение отметки времени совпадает с заголовком CB-ACCESS-TIMESTAMP.

Вот информация из ключа, который я удалил. Это из песочницы Coinbase Pro:

publicKey:

06057d5b5e03d0f8587a248330402b21

passPhrase:

gcgs6k6rp0f

secretKey: EFAToD5heo66GIgZlT2TIZzJf8TYlmxyeRxRYDHTBv3lTt9XN6uaNS0RNAy0os/caR47x6EiPDOV3Ik+YzrfEA==

Я использую angular, в частности, крипто-js библиотеку node.js:

private generateSignaturePro(timestamp: string, method: string, resourceUrl: string, requestBody: string): string {
    var prehash: string = timestamp + method + resourceUrl + requestBody;
    var key = (Buffer.from(this.secretKey, 'base64')).toString();
    return crypto.enc.Base64.stringify(crypto.HmacSHA256(prehash, key));
}

Время сервера - время: 2019-05-20T19: 01: 38.711Z Эпоха: 1558378898.711 (с / конечная точка времени)

вот мой запрос и ответ сервера:

Запрос:

Request URL: https://api-public.sandbox.pro.coinbase.com/accounts
Request Method: GET
Status Code: 400 
Remote Address: 104.16.161.226:443
Referrer Policy: no-referrer-when-downgrade

Заголовки запроса:

Provisional headers are shown
Accept: application/json, text/plain, */*
CB-ACCESS-KEY: 06057d5b5e03d0f8587a248330402b21
CB-ACCESS-PASSPHRASE: gcgs6k6rp0f
CB-ACCESS-SIGN: 0cc2BnQYdUhLucXSPwMTjpHjJ32G3RXSH44rSsEopvjAtY90uRCMVy6xUrzg/A/aRJBLqx390fcZc7lmJeP++g==
CB-ACCESS-TIMESTAMP: 1558378899
Referer: https://localhost:44342/dashboard
User-Agent: Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/74.0.3729.157 Safari/537.36

Заголовки ответа:

access-control-allow-headers: Content-Type, Accept, cb-session, cb-fp
access-control-allow-methods: GET,POST,DELETE,PUT
access-control-allow-origin: *
access-control-expose-headers: cb-before, cb-after, cb-gdpr
access-control-max-age: 7200
cache-control: no-store
cf-cache-status: MISS
cf-ray: 4da08f74ba97cf68-IAD
content-length: 31
content-type: application/json; charset=utf-8
date: Mon, 20 May 2019 19:01:38 GMT
etag: W/"1f-4RjKVp8I05+xcnQ5/G16yRoMSKU"
expect-ct: max-age=604800, report-uri="https://report-uri.cloudflare.com/cdn-cgi/beacon/expect-ct"
server: cloudflare
status: 400
strict-transport-security: max-age=15552000; includeSubDomains
vary: Accept-Encoding
x-content-type-options: nosniff
x-dns-prefetch-control: off
x-download-options: noopen
x-frame-options: SAMEORIGIN
x-xss-protection: 1; mode=block

Ответ:

{"message":"invalid signature"}

Что я делаю неправильно?

РЕДАКТИРОВАТЬ: изменен метод на версию SHA 256. По-прежнему не работает.


person Kriil    schedule 19.05.2019    source источник


Ответы (2)


Из gdax-java (как она была названа до" coinbase pro "), метод создания подписи:

 String prehash = timestamp + method.toUpperCase() + requestPath + body;

 byte[] secretDecoded = Base64.getDecoder().decode(secretKey);
 keyspec = new SecretKeySpec(secretDecoded, "HmacSHA256");
 sha256 = (Mac) GdaxConstants.SHARED_MAC.clone();
 sha256.init(keyspec);
 return Base64.getEncoder().encodeToString(sha256.doFinal(prehash.getBytes()));

По крайней мере, при первоначальной проверке код, который вы используете, указывает на использование SHA512, а не HmacSHA256, поэтому я подозреваю, что это вероятная причина.

Здесь также есть дополнительная помощь по NodeJS в правом столбце для генерации подписей. https://docs.pro.coinbase.com/#creating-a-request < / а>

person Rob Evans    schedule 29.05.2019
comment
Я проверил свой код, и он действительно имел SHA 256 ... Я просто скопировал не ту строку. Раньше я смотрел библиотеку Java, но, поскольку я пишу на TypeScript, это не помогает, и я нигде не могу найти пример JavaScript (который действительно работает). - person Kriil; 01.06.2019
comment
FWIW, я также точно следую коду, предложенному на полях документации API, и я также не могу заставить его работать. Раньше я занимался криптовалютой, и, как правило, когда я следую указанному протоколу, это работает, но здесь .... не знаю, что не так. - person Jon Watte; 12.04.2020
comment
вы используете строку prehash или байты из строки prehash? Я не совсем знаком с тем, как crypto.enc.Base64.stringify(crypto.HmacSHA256(prehash, key)); использует prehash, но в версии Java берутся байты, а не String. - person Rob Evans; 22.04.2020

Я столкнулся с той же проблемой, и мой код в основном был таким же, как ваш. Я перешел на следующее (С #), и, наконец, это сработало. Странно то, что coinbase pro - это единственная биржа, с которой у меня до сих пор были проблемы с подписью. В любом случае вот код, который у меня сработал. Надеюсь это поможет. Сэкономил бы мне часы

public string ComputeSignature(
        HttpMethod httpMethod,
        string secret,
        double timestamp,
        string requestUri,
        string contentBody = "")
    {
        var convertedString = System.Convert.FromBase64String(secret);
        var prehash = timestamp.ToString("F0", CultureInfo.InvariantCulture) + httpMethod.ToString().ToUpper() + requestUri + contentBody;
        return HashString(prehash, convertedString);
    }

private string HashString(string str, byte[] secret)
{
        var bytes = Encoding.UTF8.GetBytes(str);
        using (var hmaccsha = new HMACSHA256(secret))
        {
            return System.Convert.ToBase64String(hmaccsha.ComputeHash(bytes));
        }
}
person Maxqueue    schedule 06.06.2021