v3.2.1: fix sign error when using cursor containing percent symbols. URI encode request parameters by default when serialising during sign.

This commit is contained in:
tiagosiebler
2022-11-15 16:22:04 +00:00
parent 226952d5d2
commit 7b10ae08a2
2 changed files with 21 additions and 4 deletions

View File

@@ -79,6 +79,8 @@ export default abstract class BaseRestClient {
enable_time_sync: false, enable_time_sync: false,
/** How often to sync time drift with bybit servers (if time sync is enabled) */ /** How often to sync time drift with bybit servers (if time sync is enabled) */
sync_interval_ms: 3600000, sync_interval_ms: 3600000,
/** Request parameter values are now URI encoded by default during signing. Set to false to override this behaviour. */
encodeSerialisedValues: true,
...restOptions, ...restOptions,
}; };
@@ -337,6 +339,7 @@ export default abstract class BaseRestClient {
const recvWindow = const recvWindow =
res.originalParams.recv_window || this.options.recv_window || 5000; res.originalParams.recv_window || this.options.recv_window || 5000;
const strictParamValidation = this.options.strict_param_validation; const strictParamValidation = this.options.strict_param_validation;
const encodeSerialisedValues = this.options.encodeSerialisedValues;
// In case the parent function needs it (e.g. USDC uses a header) // In case the parent function needs it (e.g. USDC uses a header)
res.recvWindow = recvWindow; res.recvWindow = recvWindow;
@@ -349,7 +352,8 @@ export default abstract class BaseRestClient {
? serializeParams( ? serializeParams(
res.originalParams, res.originalParams,
strictParamValidation, strictParamValidation,
sortProperties sortProperties,
encodeSerialisedValues
) )
: JSON.stringify(res.originalParams); : JSON.stringify(res.originalParams);
@@ -378,7 +382,8 @@ export default abstract class BaseRestClient {
res.serializedParams = serializeParams( res.serializedParams = serializeParams(
res.originalParams, res.originalParams,
strictParamValidation, strictParamValidation,
sortProperties sortProperties,
encodeSerialisedValues
); );
res.sign = await signMessage(res.serializedParams, this.secret); res.sign = await signMessage(res.serializedParams, this.secret);
res.paramsWithSign = { res.paramsWithSign = {

View File

@@ -20,6 +20,13 @@ export interface RestClientOptions {
/** Default: false. If true, we'll throw errors if any params are undefined */ /** Default: false. If true, we'll throw errors if any params are undefined */
strict_param_validation?: boolean; strict_param_validation?: boolean;
/**
* Default: true.
* If true, request parameters will be URI encoded during the signing process.
* New behaviour introduced in v3.2.1 to fix rare parameter-driven sign errors with unified margin cursors containing "%".
*/
encodeSerialisedValues?: boolean;
/** /**
* Optionally override API protocol + domain * Optionally override API protocol + domain
* e.g baseUrl: 'https://api.bytick.com' * e.g baseUrl: 'https://api.bytick.com'
@@ -35,12 +42,14 @@ export interface RestClientOptions {
* @param params the object to serialise * @param params the object to serialise
* @param strict_validation throw if any properties are undefined * @param strict_validation throw if any properties are undefined
* @param sortProperties sort properties alphabetically before building a query string * @param sortProperties sort properties alphabetically before building a query string
* @param encodeSerialisedValues URL encode value before serialising
* @returns the params object as a serialised string key1=value1&key2=value2&etc * @returns the params object as a serialised string key1=value1&key2=value2&etc
*/ */
export function serializeParams( export function serializeParams(
params: object = {}, params: object = {},
strict_validation = false, strict_validation = false,
sortProperties = true sortProperties = true,
encodeSerialisedValues = true
): string { ): string {
const properties = sortProperties const properties = sortProperties
? Object.keys(params).sort() ? Object.keys(params).sort()
@@ -48,7 +57,10 @@ export function serializeParams(
return properties return properties
.map((key) => { .map((key) => {
const value = params[key]; const value = encodeSerialisedValues
? encodeURI(params[key])
: params[key];
if (strict_validation === true && typeof value === 'undefined') { if (strict_validation === true && typeof value === 'undefined') {
throw new Error( throw new Error(
'Failed to sign API request due to undefined parameter' 'Failed to sign API request due to undefined parameter'