ccxt 4.2.51 → 4.2.53
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +76 -16
- package/README.md +5 -6
- package/dist/ccxt.browser.js +994 -1412
- package/dist/ccxt.browser.min.js +3 -3
- package/dist/cjs/ccxt.js +1 -4
- package/dist/cjs/src/base/Exchange.js +65 -26
- package/dist/cjs/src/binance.js +92 -3
- package/dist/cjs/src/bingx.js +32 -1
- package/dist/cjs/src/bitget.js +1 -0
- package/dist/cjs/src/bitvavo.js +1 -1
- package/dist/cjs/src/coinbase.js +186 -12
- package/dist/cjs/src/htx.js +10 -4
- package/dist/cjs/src/pro/binance.js +156 -1
- package/dist/cjs/src/pro/bitfinex2.js +3 -1
- package/dist/cjs/src/pro/bitvavo.js +1 -1
- package/dist/cjs/src/pro/blockchaincom.js +7 -25
- package/dist/cjs/src/pro/deribit.js +2 -2
- package/dist/cjs/src/pro/gate.js +2 -1
- package/dist/cjs/src/pro/gemini.js +1 -1
- package/dist/cjs/src/pro/okx.js +18 -4
- package/dist/cjs/src/woo.js +3 -1
- package/js/ccxt.d.ts +2 -5
- package/js/ccxt.js +2 -4
- package/js/src/abstract/coinbase.d.ts +1 -1
- package/js/src/base/Exchange.d.ts +65 -26
- package/js/src/base/Exchange.js +65 -26
- package/js/src/binance.d.ts +6 -0
- package/js/src/binance.js +92 -3
- package/js/src/bingx.d.ts +4 -0
- package/js/src/bingx.js +32 -1
- package/js/src/bitget.js +1 -0
- package/js/src/bitvavo.js +1 -1
- package/js/src/coinbase.d.ts +2 -0
- package/js/src/coinbase.js +186 -12
- package/js/src/deribit.js +1 -1
- package/js/src/htx.js +10 -4
- package/js/src/ndax.js +1 -1
- package/js/src/pro/binance.d.ts +3 -0
- package/js/src/pro/binance.js +156 -1
- package/js/src/pro/bingx.js +1 -1
- package/js/src/pro/bitfinex2.js +3 -1
- package/js/src/pro/bitvavo.js +1 -1
- package/js/src/pro/blockchaincom.d.ts +0 -1
- package/js/src/pro/blockchaincom.js +7 -25
- package/js/src/pro/deribit.js +2 -2
- package/js/src/pro/gate.js +2 -1
- package/js/src/pro/gemini.js +1 -1
- package/js/src/pro/okx.js +18 -4
- package/js/src/woo.js +4 -2
- package/package.json +2 -1
- package/skip-tests.json +29 -13
- package/dist/cjs/src/abstract/bitforex.js +0 -9
- package/dist/cjs/src/bitforex.js +0 -884
- package/js/src/abstract/bitforex.d.ts +0 -27
- package/js/src/abstract/bitforex.js +0 -11
- package/js/src/bitforex.d.ts +0 -39
- package/js/src/bitforex.js +0 -885
package/dist/cjs/src/coinbase.js
CHANGED
|
@@ -51,6 +51,7 @@ class coinbase extends coinbase$1 {
|
|
|
51
51
|
'createStopLimitOrder': true,
|
|
52
52
|
'createStopMarketOrder': false,
|
|
53
53
|
'createStopOrder': true,
|
|
54
|
+
'deposit': true,
|
|
54
55
|
'editOrder': true,
|
|
55
56
|
'fetchAccounts': true,
|
|
56
57
|
'fetchBalance': true,
|
|
@@ -62,6 +63,7 @@ class coinbase extends coinbase$1 {
|
|
|
62
63
|
'fetchCrossBorrowRate': false,
|
|
63
64
|
'fetchCrossBorrowRates': false,
|
|
64
65
|
'fetchCurrencies': true,
|
|
66
|
+
'fetchDeposit': true,
|
|
65
67
|
'fetchDepositAddress': 'emulated',
|
|
66
68
|
'fetchDepositAddresses': false,
|
|
67
69
|
'fetchDepositAddressesByNetwork': true,
|
|
@@ -190,6 +192,11 @@ class coinbase extends coinbase$1 {
|
|
|
190
192
|
},
|
|
191
193
|
},
|
|
192
194
|
'v3': {
|
|
195
|
+
'public': {
|
|
196
|
+
'get': [
|
|
197
|
+
'brokerage/time',
|
|
198
|
+
],
|
|
199
|
+
},
|
|
193
200
|
'private': {
|
|
194
201
|
'get': [
|
|
195
202
|
'brokerage/accounts',
|
|
@@ -207,7 +214,6 @@ class coinbase extends coinbase$1 {
|
|
|
207
214
|
'brokerage/product_book',
|
|
208
215
|
'brokerage/best_bid_ask',
|
|
209
216
|
'brokerage/convert/trade/{trade_id}',
|
|
210
|
-
'brokerage/time',
|
|
211
217
|
'brokerage/cfm/balance_summary',
|
|
212
218
|
'brokerage/cfm/positions',
|
|
213
219
|
'brokerage/cfm/positions/{product_id}',
|
|
@@ -338,6 +344,7 @@ class coinbase extends coinbase$1 {
|
|
|
338
344
|
'fetchTickers': 'fetchTickersV3',
|
|
339
345
|
'fetchAccounts': 'fetchAccountsV3',
|
|
340
346
|
'fetchBalance': 'v2PrivateGetAccounts',
|
|
347
|
+
'fetchTime': 'v2PublicGetTime',
|
|
341
348
|
'user_native_currency': 'USD', // needed to get fees for v3
|
|
342
349
|
},
|
|
343
350
|
});
|
|
@@ -349,19 +356,36 @@ class coinbase extends coinbase$1 {
|
|
|
349
356
|
* @description fetches the current integer timestamp in milliseconds from the exchange server
|
|
350
357
|
* @see https://docs.cloud.coinbase.com/sign-in-with-coinbase/docs/api-time#http-request
|
|
351
358
|
* @param {object} [params] extra parameters specific to the exchange API endpoint
|
|
359
|
+
* @param {string} [params.method] 'v2PublicGetTime' or 'v3PublicGetBrokerageTime' default is 'v2PublicGetTime'
|
|
352
360
|
* @returns {int} the current integer timestamp in milliseconds from the exchange server
|
|
353
361
|
*/
|
|
354
|
-
const
|
|
355
|
-
|
|
356
|
-
|
|
357
|
-
|
|
358
|
-
|
|
359
|
-
|
|
360
|
-
|
|
361
|
-
|
|
362
|
-
|
|
363
|
-
|
|
364
|
-
|
|
362
|
+
const defaultMethod = this.safeString(this.options, 'fetchTime', 'v2PublicGetTime');
|
|
363
|
+
const method = this.safeString(params, 'method', defaultMethod);
|
|
364
|
+
params = this.omit(params, 'method');
|
|
365
|
+
let response = undefined;
|
|
366
|
+
if (method === 'v2PublicGetTime') {
|
|
367
|
+
response = await this.v2PublicGetTime(params);
|
|
368
|
+
//
|
|
369
|
+
// {
|
|
370
|
+
// "data": {
|
|
371
|
+
// "epoch": 1589295679,
|
|
372
|
+
// "iso": "2020-05-12T15:01:19Z"
|
|
373
|
+
// }
|
|
374
|
+
// }
|
|
375
|
+
//
|
|
376
|
+
response = this.safeValue(response, 'data', {});
|
|
377
|
+
}
|
|
378
|
+
else {
|
|
379
|
+
response = await this.v3PublicGetBrokerageTime(params);
|
|
380
|
+
//
|
|
381
|
+
// {
|
|
382
|
+
// "iso": "2024-02-27T03:37:14Z",
|
|
383
|
+
// "epochSeconds": "1709005034",
|
|
384
|
+
// "epochMillis": "1709005034333"
|
|
385
|
+
// }
|
|
386
|
+
//
|
|
387
|
+
}
|
|
388
|
+
return this.safeTimestamp2(response, 'epoch', 'epochSeconds');
|
|
365
389
|
}
|
|
366
390
|
async fetchAccounts(params = {}) {
|
|
367
391
|
/**
|
|
@@ -1757,6 +1781,7 @@ class coinbase extends coinbase$1 {
|
|
|
1757
1781
|
response = await this.v3PrivateGetBrokerageAccounts(this.extend(request, params));
|
|
1758
1782
|
}
|
|
1759
1783
|
else {
|
|
1784
|
+
request['limit'] = 100;
|
|
1760
1785
|
response = await this.v2PrivateGetAccounts(this.extend(request, params));
|
|
1761
1786
|
}
|
|
1762
1787
|
//
|
|
@@ -3536,6 +3561,145 @@ class coinbase extends coinbase$1 {
|
|
|
3536
3561
|
'network': this.networkIdToCode(networkId, code),
|
|
3537
3562
|
};
|
|
3538
3563
|
}
|
|
3564
|
+
async deposit(code, amount, id, params = {}) {
|
|
3565
|
+
/**
|
|
3566
|
+
* @method
|
|
3567
|
+
* @name coinbase#deposit
|
|
3568
|
+
* @description make a deposit
|
|
3569
|
+
* @see https://docs.cloud.coinbase.com/sign-in-with-coinbase/docs/api-deposits#deposit-funds
|
|
3570
|
+
* @param {string} code unified currency code
|
|
3571
|
+
* @param {float} amount the amount to deposit
|
|
3572
|
+
* @param {string} id the payment method id to be used for the deposit, can be retrieved from v2PrivateGetPaymentMethods
|
|
3573
|
+
* @param {object} [params] extra parameters specific to the exchange API endpoint
|
|
3574
|
+
* @param {string} [params.accountId] the id of the account to deposit into
|
|
3575
|
+
* @returns {object} a [transaction structure]{@link https://docs.ccxt.com/#/?id=transaction-structure}
|
|
3576
|
+
*/
|
|
3577
|
+
await this.loadMarkets();
|
|
3578
|
+
let accountId = this.safeString2(params, 'account_id', 'accountId');
|
|
3579
|
+
params = this.omit(params, ['account_id', 'accountId']);
|
|
3580
|
+
if (accountId === undefined) {
|
|
3581
|
+
if (code === undefined) {
|
|
3582
|
+
throw new errors.ArgumentsRequired(this.id + ' deposit() requires an account_id (or accountId) parameter OR a currency code argument');
|
|
3583
|
+
}
|
|
3584
|
+
accountId = await this.findAccountId(code);
|
|
3585
|
+
if (accountId === undefined) {
|
|
3586
|
+
throw new errors.ExchangeError(this.id + ' deposit() could not find account id for ' + code);
|
|
3587
|
+
}
|
|
3588
|
+
}
|
|
3589
|
+
const request = {
|
|
3590
|
+
'account_id': accountId,
|
|
3591
|
+
'amount': this.numberToString(amount),
|
|
3592
|
+
'currency': code.toUpperCase(),
|
|
3593
|
+
'payment_method': id,
|
|
3594
|
+
};
|
|
3595
|
+
const response = await this.v2PrivatePostAccountsAccountIdDeposits(this.extend(request, params));
|
|
3596
|
+
//
|
|
3597
|
+
// {
|
|
3598
|
+
// "data": {
|
|
3599
|
+
// "id": "67e0eaec-07d7-54c4-a72c-2e92826897df",
|
|
3600
|
+
// "status": "created",
|
|
3601
|
+
// "payment_method": {
|
|
3602
|
+
// "id": "83562370-3e5c-51db-87da-752af5ab9559",
|
|
3603
|
+
// "resource": "payment_method",
|
|
3604
|
+
// "resource_path": "/v2/payment-methods/83562370-3e5c-51db-87da-752af5ab9559"
|
|
3605
|
+
// },
|
|
3606
|
+
// "transaction": {
|
|
3607
|
+
// "id": "441b9494-b3f0-5b98-b9b0-4d82c21c252a",
|
|
3608
|
+
// "resource": "transaction",
|
|
3609
|
+
// "resource_path": "/v2/accounts/2bbf394c-193b-5b2a-9155-3b4732659ede/transactions/441b9494-b3f0-5b98-b9b0-4d82c21c252a"
|
|
3610
|
+
// },
|
|
3611
|
+
// "amount": {
|
|
3612
|
+
// "amount": "10.00",
|
|
3613
|
+
// "currency": "USD"
|
|
3614
|
+
// },
|
|
3615
|
+
// "subtotal": {
|
|
3616
|
+
// "amount": "10.00",
|
|
3617
|
+
// "currency": "USD"
|
|
3618
|
+
// },
|
|
3619
|
+
// "created_at": "2015-01-31T20:49:02Z",
|
|
3620
|
+
// "updated_at": "2015-02-11T16:54:02-08:00",
|
|
3621
|
+
// "resource": "deposit",
|
|
3622
|
+
// "resource_path": "/v2/accounts/2bbf394c-193b-5b2a-9155-3b4732659ede/deposits/67e0eaec-07d7-54c4-a72c-2e92826897df",
|
|
3623
|
+
// "committed": true,
|
|
3624
|
+
// "fee": {
|
|
3625
|
+
// "amount": "0.00",
|
|
3626
|
+
// "currency": "USD"
|
|
3627
|
+
// },
|
|
3628
|
+
// "payout_at": "2015-02-18T16:54:00-08:00"
|
|
3629
|
+
// }
|
|
3630
|
+
// }
|
|
3631
|
+
//
|
|
3632
|
+
const data = this.safeDict(response, 'data', {});
|
|
3633
|
+
return this.parseTransaction(data);
|
|
3634
|
+
}
|
|
3635
|
+
async fetchDeposit(id, code = undefined, params = {}) {
|
|
3636
|
+
/**
|
|
3637
|
+
* @method
|
|
3638
|
+
* @name coinbase#fetchDeposit
|
|
3639
|
+
* @description fetch information on a deposit, fiat only, for crypto transactions use fetchLedger
|
|
3640
|
+
* @see https://docs.cloud.coinbase.com/sign-in-with-coinbase/docs/api-deposits#show-deposit
|
|
3641
|
+
* @param {string} id deposit id
|
|
3642
|
+
* @param {string} [code] unified currency code
|
|
3643
|
+
* @param {object} [params] extra parameters specific to the exchange API endpoint
|
|
3644
|
+
* @param {string} [params.accountId] the id of the account that the funds were deposited into
|
|
3645
|
+
* @returns {object} a [transaction structure]{@link https://docs.ccxt.com/#/?id=transaction-structure}
|
|
3646
|
+
*/
|
|
3647
|
+
await this.loadMarkets();
|
|
3648
|
+
let accountId = this.safeString2(params, 'account_id', 'accountId');
|
|
3649
|
+
params = this.omit(params, ['account_id', 'accountId']);
|
|
3650
|
+
if (accountId === undefined) {
|
|
3651
|
+
if (code === undefined) {
|
|
3652
|
+
throw new errors.ArgumentsRequired(this.id + ' fetchDeposit() requires an account_id (or accountId) parameter OR a currency code argument');
|
|
3653
|
+
}
|
|
3654
|
+
accountId = await this.findAccountId(code);
|
|
3655
|
+
if (accountId === undefined) {
|
|
3656
|
+
throw new errors.ExchangeError(this.id + ' fetchDeposit() could not find account id for ' + code);
|
|
3657
|
+
}
|
|
3658
|
+
}
|
|
3659
|
+
const request = {
|
|
3660
|
+
'account_id': accountId,
|
|
3661
|
+
'deposit_id': id,
|
|
3662
|
+
};
|
|
3663
|
+
const response = await this.v2PrivateGetAccountsAccountIdDepositsDepositId(this.extend(request, params));
|
|
3664
|
+
//
|
|
3665
|
+
// {
|
|
3666
|
+
// "data": {
|
|
3667
|
+
// "id": "67e0eaec-07d7-54c4-a72c-2e92826897df",
|
|
3668
|
+
// "status": "completed",
|
|
3669
|
+
// "payment_method": {
|
|
3670
|
+
// "id": "83562370-3e5c-51db-87da-752af5ab9559",
|
|
3671
|
+
// "resource": "payment_method",
|
|
3672
|
+
// "resource_path": "/v2/payment-methods/83562370-3e5c-51db-87da-752af5ab9559"
|
|
3673
|
+
// },
|
|
3674
|
+
// "transaction": {
|
|
3675
|
+
// "id": "441b9494-b3f0-5b98-b9b0-4d82c21c252a",
|
|
3676
|
+
// "resource": "transaction",
|
|
3677
|
+
// "resource_path": "/v2/accounts/2bbf394c-193b-5b2a-9155-3b4732659ede/transactions/441b9494-b3f0-5b98-b9b0-4d82c21c252a"
|
|
3678
|
+
// },
|
|
3679
|
+
// "amount": {
|
|
3680
|
+
// "amount": "10.00",
|
|
3681
|
+
// "currency": "USD"
|
|
3682
|
+
// },
|
|
3683
|
+
// "subtotal": {
|
|
3684
|
+
// "amount": "10.00",
|
|
3685
|
+
// "currency": "USD"
|
|
3686
|
+
// },
|
|
3687
|
+
// "created_at": "2015-01-31T20:49:02Z",
|
|
3688
|
+
// "updated_at": "2015-02-11T16:54:02-08:00",
|
|
3689
|
+
// "resource": "deposit",
|
|
3690
|
+
// "resource_path": "/v2/accounts/2bbf394c-193b-5b2a-9155-3b4732659ede/deposits/67e0eaec-07d7-54c4-a72c-2e92826897df",
|
|
3691
|
+
// "committed": true,
|
|
3692
|
+
// "fee": {
|
|
3693
|
+
// "amount": "0.00",
|
|
3694
|
+
// "currency": "USD"
|
|
3695
|
+
// },
|
|
3696
|
+
// "payout_at": "2015-02-18T16:54:00-08:00"
|
|
3697
|
+
// }
|
|
3698
|
+
// }
|
|
3699
|
+
//
|
|
3700
|
+
const data = this.safeValue(response, 'data', {});
|
|
3701
|
+
return this.parseTransaction(data);
|
|
3702
|
+
}
|
|
3539
3703
|
sign(path, api = [], method = 'GET', params = {}, headers = undefined, body = undefined) {
|
|
3540
3704
|
const version = api[0];
|
|
3541
3705
|
const signed = api[1] === 'private';
|
|
@@ -3556,6 +3720,11 @@ class coinbase extends coinbase$1 {
|
|
|
3556
3720
|
'Authorization': authorization,
|
|
3557
3721
|
'Content-Type': 'application/json',
|
|
3558
3722
|
};
|
|
3723
|
+
if (method !== 'GET') {
|
|
3724
|
+
if (Object.keys(query).length) {
|
|
3725
|
+
body = this.json(query);
|
|
3726
|
+
}
|
|
3727
|
+
}
|
|
3559
3728
|
}
|
|
3560
3729
|
else if (this.token && !this.checkRequiredCredentials(false)) {
|
|
3561
3730
|
headers = {
|
|
@@ -3578,6 +3747,11 @@ class coinbase extends coinbase$1 {
|
|
|
3578
3747
|
payload = body;
|
|
3579
3748
|
}
|
|
3580
3749
|
}
|
|
3750
|
+
else {
|
|
3751
|
+
if (Object.keys(query).length) {
|
|
3752
|
+
payload += '?' + this.urlencode(query);
|
|
3753
|
+
}
|
|
3754
|
+
}
|
|
3581
3755
|
const auth = nonce + method + savedPath + payload;
|
|
3582
3756
|
const signature = this.hmac(this.encode(auth), this.encode(this.secret), sha256.sha256);
|
|
3583
3757
|
headers = {
|
package/dist/cjs/src/htx.js
CHANGED
|
@@ -1231,9 +1231,10 @@ class htx extends htx$1 {
|
|
|
1231
1231
|
async fetchStatus(params = {}) {
|
|
1232
1232
|
await this.loadMarkets();
|
|
1233
1233
|
let marketType = undefined;
|
|
1234
|
-
[marketType, params] = this.handleMarketTypeAndParams('
|
|
1234
|
+
[marketType, params] = this.handleMarketTypeAndParams('fetchStatus', undefined, params);
|
|
1235
|
+
const enabledForContracts = this.handleOption('fetchStatus', 'enableForContracts', false); // temp fix for: https://status-linear-swap.huobigroup.com/api/v2/summary.json
|
|
1235
1236
|
let response = undefined;
|
|
1236
|
-
if (marketType !== 'spot') {
|
|
1237
|
+
if (marketType !== 'spot' && enabledForContracts) {
|
|
1237
1238
|
const subType = this.safeString(params, 'subType', this.options['defaultSubType']);
|
|
1238
1239
|
if (marketType === 'swap') {
|
|
1239
1240
|
if (subType === 'linear') {
|
|
@@ -1255,7 +1256,7 @@ class htx extends htx$1 {
|
|
|
1255
1256
|
response = await this.contractPublicGetHeartbeat();
|
|
1256
1257
|
}
|
|
1257
1258
|
}
|
|
1258
|
-
else {
|
|
1259
|
+
else if (marketType === 'spot') {
|
|
1259
1260
|
response = await this.statusPublicSpotGetApiV2SummaryJson();
|
|
1260
1261
|
}
|
|
1261
1262
|
//
|
|
@@ -1424,7 +1425,12 @@ class htx extends htx$1 {
|
|
|
1424
1425
|
let url = undefined;
|
|
1425
1426
|
if (marketType === 'contract') {
|
|
1426
1427
|
const statusRaw = this.safeString(response, 'status');
|
|
1427
|
-
|
|
1428
|
+
if (statusRaw === undefined) {
|
|
1429
|
+
status = undefined;
|
|
1430
|
+
}
|
|
1431
|
+
else {
|
|
1432
|
+
status = (statusRaw === 'ok') ? 'ok' : 'maintenance'; // 'ok', 'error'
|
|
1433
|
+
}
|
|
1428
1434
|
updated = this.safeString(response, 'ts');
|
|
1429
1435
|
}
|
|
1430
1436
|
else {
|
|
@@ -38,9 +38,11 @@ class binance extends binance$1 {
|
|
|
38
38
|
'fetchDepositsWs': false,
|
|
39
39
|
'fetchMarketsWs': false,
|
|
40
40
|
'fetchMyTradesWs': true,
|
|
41
|
+
'fetchOHLCVWs': true,
|
|
41
42
|
'fetchOpenOrdersWs': true,
|
|
42
43
|
'fetchOrderWs': true,
|
|
43
44
|
'fetchOrdersWs': true,
|
|
45
|
+
'fetchTradesWs': true,
|
|
44
46
|
'fetchTradingFeesWs': false,
|
|
45
47
|
'fetchWithdrawalsWs': false,
|
|
46
48
|
},
|
|
@@ -837,6 +839,94 @@ class binance extends binance$1 {
|
|
|
837
839
|
stored.append(parsed);
|
|
838
840
|
client.resolve(stored, messageHash);
|
|
839
841
|
}
|
|
842
|
+
async fetchOHLCVWs(symbol, timeframe = '1m', since = undefined, limit = undefined, params = {}) {
|
|
843
|
+
/**
|
|
844
|
+
* @method
|
|
845
|
+
* @name binance#fetchOHLCVWs
|
|
846
|
+
* @see https://binance-docs.github.io/apidocs/websocket_api/en/#klines
|
|
847
|
+
* @description query historical candlestick data containing the open, high, low, and close price, and the volume of a market
|
|
848
|
+
* @param {string} symbol unified symbol of the market to query OHLCV data for
|
|
849
|
+
* @param {string} timeframe the length of time each candle represents
|
|
850
|
+
* @param {int} since timestamp in ms of the earliest candle to fetch
|
|
851
|
+
* @param {int} limit the maximum amount of candles to fetch
|
|
852
|
+
* @param {object} params extra parameters specific to the exchange API endpoint
|
|
853
|
+
* @param {int} params.until timestamp in ms of the earliest candle to fetch
|
|
854
|
+
*
|
|
855
|
+
* EXCHANGE SPECIFIC PARAMETERS
|
|
856
|
+
* @param {string} params.timeZone default=0 (UTC)
|
|
857
|
+
* @returns {int[][]} A list of candles ordered as timestamp, open, high, low, close, volume
|
|
858
|
+
*/
|
|
859
|
+
await this.loadMarkets();
|
|
860
|
+
this.checkIsSpot('fetchOHLCVWs', symbol, params);
|
|
861
|
+
const url = this.urls['api']['ws']['ws'];
|
|
862
|
+
const requestId = this.requestId(url);
|
|
863
|
+
const messageHash = requestId.toString();
|
|
864
|
+
let returnRateLimits = false;
|
|
865
|
+
[returnRateLimits, params] = this.handleOptionAndParams(params, 'fetchOHLCVWs', 'returnRateLimits', false);
|
|
866
|
+
const payload = {
|
|
867
|
+
'symbol': this.marketId(symbol),
|
|
868
|
+
'returnRateLimits': returnRateLimits,
|
|
869
|
+
'interval': this.timeframes[timeframe],
|
|
870
|
+
};
|
|
871
|
+
const until = this.safeInteger(params, 'until');
|
|
872
|
+
params = this.omit(params, 'until');
|
|
873
|
+
if (since !== undefined) {
|
|
874
|
+
payload['startTime'] = since;
|
|
875
|
+
}
|
|
876
|
+
if (limit !== undefined) {
|
|
877
|
+
payload['limit'] = limit;
|
|
878
|
+
}
|
|
879
|
+
if (until !== undefined) {
|
|
880
|
+
payload['endTime'] = until;
|
|
881
|
+
}
|
|
882
|
+
const message = {
|
|
883
|
+
'id': messageHash,
|
|
884
|
+
'method': 'klines',
|
|
885
|
+
'params': this.extend(payload, params),
|
|
886
|
+
};
|
|
887
|
+
const subscription = {
|
|
888
|
+
'method': this.handleFetchOHLCV,
|
|
889
|
+
};
|
|
890
|
+
return await this.watch(url, messageHash, message, messageHash, subscription);
|
|
891
|
+
}
|
|
892
|
+
handleFetchOHLCV(client, message) {
|
|
893
|
+
//
|
|
894
|
+
// {
|
|
895
|
+
// "id": "1dbbeb56-8eea-466a-8f6e-86bdcfa2fc0b",
|
|
896
|
+
// "status": 200,
|
|
897
|
+
// "result": [
|
|
898
|
+
// [
|
|
899
|
+
// 1655971200000, // Kline open time
|
|
900
|
+
// "0.01086000", // Open price
|
|
901
|
+
// "0.01086600", // High price
|
|
902
|
+
// "0.01083600", // Low price
|
|
903
|
+
// "0.01083800", // Close price
|
|
904
|
+
// "2290.53800000", // Volume
|
|
905
|
+
// 1655974799999, // Kline close time
|
|
906
|
+
// "24.85074442", // Quote asset volume
|
|
907
|
+
// 2283, // Number of trades
|
|
908
|
+
// "1171.64000000", // Taker buy base asset volume
|
|
909
|
+
// "12.71225884", // Taker buy quote asset volume
|
|
910
|
+
// "0" // Unused field, ignore
|
|
911
|
+
// ]
|
|
912
|
+
// ],
|
|
913
|
+
// "rateLimits": [
|
|
914
|
+
// {
|
|
915
|
+
// "rateLimitType": "REQUEST_WEIGHT",
|
|
916
|
+
// "interval": "MINUTE",
|
|
917
|
+
// "intervalNum": 1,
|
|
918
|
+
// "limit": 6000,
|
|
919
|
+
// "count": 2
|
|
920
|
+
// }
|
|
921
|
+
// ]
|
|
922
|
+
// }
|
|
923
|
+
//
|
|
924
|
+
const result = this.safeList(message, 'result');
|
|
925
|
+
const parsed = this.parseOHLCVs(result);
|
|
926
|
+
// use a reverse lookup in a static map instead
|
|
927
|
+
const messageHash = this.safeString(message, 'id');
|
|
928
|
+
client.resolve(parsed, messageHash);
|
|
929
|
+
}
|
|
840
930
|
async watchTicker(symbol, params = {}) {
|
|
841
931
|
/**
|
|
842
932
|
* @method
|
|
@@ -2538,12 +2628,58 @@ class binance extends binance$1 {
|
|
|
2538
2628
|
const trades = await this.watch(url, messageHash, message, messageHash, subscription);
|
|
2539
2629
|
return this.filterBySymbolSinceLimit(trades, symbol, since, limit);
|
|
2540
2630
|
}
|
|
2631
|
+
async fetchTradesWs(symbol = undefined, since = undefined, limit = undefined, params = {}) {
|
|
2632
|
+
/**
|
|
2633
|
+
* @method
|
|
2634
|
+
* @name binance#fetchTradesWs
|
|
2635
|
+
* @see https://binance-docs.github.io/apidocs/websocket_api/en/#recent-trades
|
|
2636
|
+
* @description fetch all trades made by the user
|
|
2637
|
+
* @param {string} symbol unified market symbol
|
|
2638
|
+
* @param {int} [since] the earliest time in ms to fetch trades for
|
|
2639
|
+
* @param {int} [limit] the maximum number of trades structures to retrieve, default=500, max=1000
|
|
2640
|
+
* @param {object} [params] extra parameters specific to the exchange API endpoint
|
|
2641
|
+
*
|
|
2642
|
+
* EXCHANGE SPECIFIC PARAMETERS
|
|
2643
|
+
* @param {int} [params.fromId] trade ID to begin at
|
|
2644
|
+
* @returns {object[]} a list of [trade structures]{@link https://docs.ccxt.com/#/?id=trade-structure}
|
|
2645
|
+
*/
|
|
2646
|
+
await this.loadMarkets();
|
|
2647
|
+
if (symbol === undefined) {
|
|
2648
|
+
throw new errors.BadRequest(this.id + ' fetchTradesWs () requires a symbol argument');
|
|
2649
|
+
}
|
|
2650
|
+
this.checkIsSpot('fetchTradesWs', symbol, params);
|
|
2651
|
+
const url = this.urls['api']['ws']['ws'];
|
|
2652
|
+
const requestId = this.requestId(url);
|
|
2653
|
+
const messageHash = requestId.toString();
|
|
2654
|
+
let returnRateLimits = false;
|
|
2655
|
+
[returnRateLimits, params] = this.handleOptionAndParams(params, 'fetchTradesWs', 'returnRateLimits', false);
|
|
2656
|
+
const payload = {
|
|
2657
|
+
'symbol': this.marketId(symbol),
|
|
2658
|
+
'returnRateLimits': returnRateLimits,
|
|
2659
|
+
};
|
|
2660
|
+
if (limit !== undefined) {
|
|
2661
|
+
payload['limit'] = limit;
|
|
2662
|
+
}
|
|
2663
|
+
const message = {
|
|
2664
|
+
'id': messageHash,
|
|
2665
|
+
'method': 'trades.historical',
|
|
2666
|
+
'params': this.extend(payload, params),
|
|
2667
|
+
};
|
|
2668
|
+
const subscription = {
|
|
2669
|
+
'method': this.handleTradesWs,
|
|
2670
|
+
};
|
|
2671
|
+
const trades = await this.watch(url, messageHash, message, messageHash, subscription);
|
|
2672
|
+
return this.filterBySinceLimit(trades, since, limit);
|
|
2673
|
+
}
|
|
2541
2674
|
handleTradesWs(client, message) {
|
|
2675
|
+
//
|
|
2676
|
+
// fetchMyTradesWs
|
|
2542
2677
|
//
|
|
2543
2678
|
// {
|
|
2544
2679
|
// "id": "f4ce6a53-a29d-4f70-823b-4ab59391d6e8",
|
|
2545
2680
|
// "status": 200,
|
|
2546
|
-
// "result": [
|
|
2681
|
+
// "result": [
|
|
2682
|
+
// {
|
|
2547
2683
|
// "symbol": "BTCUSDT",
|
|
2548
2684
|
// "id": 1650422481,
|
|
2549
2685
|
// "orderId": 12569099453,
|
|
@@ -2562,6 +2698,25 @@ class binance extends binance$1 {
|
|
|
2562
2698
|
// ],
|
|
2563
2699
|
// }
|
|
2564
2700
|
//
|
|
2701
|
+
// fetchTradesWs
|
|
2702
|
+
//
|
|
2703
|
+
// {
|
|
2704
|
+
// "id": "f4ce6a53-a29d-4f70-823b-4ab59391d6e8",
|
|
2705
|
+
// "status": 200,
|
|
2706
|
+
// "result": [
|
|
2707
|
+
// {
|
|
2708
|
+
// "id": 0,
|
|
2709
|
+
// "price": "0.00005000",
|
|
2710
|
+
// "qty": "40.00000000",
|
|
2711
|
+
// "quoteQty": "0.00200000",
|
|
2712
|
+
// "time": 1500004800376,
|
|
2713
|
+
// "isBuyerMaker": true,
|
|
2714
|
+
// "isBestMatch": true
|
|
2715
|
+
// }
|
|
2716
|
+
// ...
|
|
2717
|
+
// ],
|
|
2718
|
+
// }
|
|
2719
|
+
//
|
|
2565
2720
|
const messageHash = this.safeString(message, 'id');
|
|
2566
2721
|
const result = this.safeValue(message, 'result', []);
|
|
2567
2722
|
const trades = this.parseTrades(result);
|
|
@@ -320,7 +320,9 @@ class bitfinex2 extends bitfinex2$1 {
|
|
|
320
320
|
const messageLength = message.length;
|
|
321
321
|
if (messageLength === 2) {
|
|
322
322
|
// initial snapshot
|
|
323
|
-
|
|
323
|
+
let trades = this.safeList(message, 1, []);
|
|
324
|
+
// needs to be reversed to make chronological order
|
|
325
|
+
trades = trades.reverse();
|
|
324
326
|
for (let i = 0; i < trades.length; i++) {
|
|
325
327
|
const parsed = this.parseWsTrade(trades[i], market);
|
|
326
328
|
stored.append(parsed);
|
|
@@ -102,7 +102,7 @@ class bitvavo extends bitvavo$1 {
|
|
|
102
102
|
// "volume": "3587.05020246",
|
|
103
103
|
// "volumeQuote": "708030.17",
|
|
104
104
|
// "bid": "199.56",
|
|
105
|
-
// "bidSize": "4.
|
|
105
|
+
// "bidSize": "4.14730802",
|
|
106
106
|
// "ask": "199.57",
|
|
107
107
|
// "askSize": "6.13642074",
|
|
108
108
|
// "timestamp": 1590770885217
|
|
@@ -34,7 +34,6 @@ class blockchaincom extends blockchaincom$1 {
|
|
|
34
34
|
},
|
|
35
35
|
'noOriginHeader': false,
|
|
36
36
|
},
|
|
37
|
-
'sequenceNumbers': {},
|
|
38
37
|
},
|
|
39
38
|
'streaming': {},
|
|
40
39
|
'exceptions': {},
|
|
@@ -678,21 +677,20 @@ class blockchaincom extends blockchaincom$1 {
|
|
|
678
677
|
// }
|
|
679
678
|
//
|
|
680
679
|
const event = this.safeString(message, 'event');
|
|
680
|
+
if (event === 'subscribed') {
|
|
681
|
+
return;
|
|
682
|
+
}
|
|
681
683
|
const type = this.safeString(message, 'channel');
|
|
682
684
|
const marketId = this.safeString(message, 'symbol');
|
|
683
685
|
const symbol = this.safeSymbol(marketId);
|
|
684
686
|
const messageHash = 'orderbook:' + symbol + ':' + type;
|
|
685
687
|
const datetime = this.safeString(message, 'timestamp');
|
|
686
688
|
const timestamp = this.parse8601(datetime);
|
|
687
|
-
|
|
688
|
-
|
|
689
|
-
orderbook = this.countedOrderBook({});
|
|
690
|
-
this.orderbooks[symbol] = orderbook;
|
|
691
|
-
}
|
|
692
|
-
if (event === 'subscribed') {
|
|
693
|
-
return;
|
|
689
|
+
if (this.safeValue(this.orderbooks, symbol) === undefined) {
|
|
690
|
+
this.orderbooks[symbol] = this.countedOrderBook();
|
|
694
691
|
}
|
|
695
|
-
|
|
692
|
+
const orderbook = this.orderbooks[symbol];
|
|
693
|
+
if (event === 'snapshot') {
|
|
696
694
|
const snapshot = this.parseOrderBook(message, symbol, timestamp, 'bids', 'asks', 'px', 'qty', 'num');
|
|
697
695
|
orderbook.reset(snapshot);
|
|
698
696
|
}
|
|
@@ -718,23 +716,7 @@ class blockchaincom extends blockchaincom$1 {
|
|
|
718
716
|
this.handleDelta(bookside, deltas[i]);
|
|
719
717
|
}
|
|
720
718
|
}
|
|
721
|
-
checkSequenceNumber(client, message) {
|
|
722
|
-
const seqnum = this.safeInteger(message, 'seqnum', 0);
|
|
723
|
-
const channel = this.safeString(message, 'channel', '');
|
|
724
|
-
const sequenceNumbersByChannel = this.safeValue(this.options, 'sequenceNumbers', {});
|
|
725
|
-
const lastSeqnum = this.safeInteger(sequenceNumbersByChannel, channel);
|
|
726
|
-
if (lastSeqnum === undefined) {
|
|
727
|
-
this.options['sequenceNumbers'][channel] = seqnum;
|
|
728
|
-
}
|
|
729
|
-
else {
|
|
730
|
-
if (seqnum !== lastSeqnum + 1) {
|
|
731
|
-
throw new errors.ExchangeError(this.id + ' ' + channel + ' seqnum ' + seqnum + ' is not the expected ' + (lastSeqnum + 1));
|
|
732
|
-
}
|
|
733
|
-
this.options['sequenceNumbers'][channel] = seqnum;
|
|
734
|
-
}
|
|
735
|
-
}
|
|
736
719
|
handleMessage(client, message) {
|
|
737
|
-
this.checkSequenceNumber(client, message);
|
|
738
720
|
const channel = this.safeString(message, 'channel');
|
|
739
721
|
const handlers = {
|
|
740
722
|
'ticker': this.handleTicker,
|
|
@@ -177,7 +177,7 @@ class deribit extends deribit$1 {
|
|
|
177
177
|
// "params": {
|
|
178
178
|
// "channel": "ticker.BTC_USDC-PERPETUAL.raw",
|
|
179
179
|
// "data": {
|
|
180
|
-
// "timestamp":
|
|
180
|
+
// "timestamp": 1655393725040,
|
|
181
181
|
// "stats": [Object],
|
|
182
182
|
// "state": "open",
|
|
183
183
|
// "settlement_price": 21729.5891,
|
|
@@ -658,7 +658,7 @@ class deribit extends deribit$1 {
|
|
|
658
658
|
const symbol = this.safeSymbol(marketId);
|
|
659
659
|
const ohlcv = this.safeValue(params, 'data', {});
|
|
660
660
|
const parsed = [
|
|
661
|
-
this.
|
|
661
|
+
this.safeInteger(ohlcv, 'tick'),
|
|
662
662
|
this.safeNumber(ohlcv, 'open'),
|
|
663
663
|
this.safeNumber(ohlcv, 'high'),
|
|
664
664
|
this.safeNumber(ohlcv, 'low'),
|
package/dist/cjs/src/pro/gate.js
CHANGED
|
@@ -383,8 +383,9 @@ class gate extends gate$1 {
|
|
|
383
383
|
const parts = channel.split('.');
|
|
384
384
|
const rawMarketType = this.safeString(parts, 0);
|
|
385
385
|
const marketType = (rawMarketType === 'futures') ? 'contract' : 'spot';
|
|
386
|
+
const result = this.safeValue(message, 'result');
|
|
386
387
|
let results = [];
|
|
387
|
-
if (
|
|
388
|
+
if (Array.isArray(result)) {
|
|
388
389
|
results = this.safeList(message, 'result', []);
|
|
389
390
|
}
|
|
390
391
|
else {
|
|
@@ -203,7 +203,7 @@ class gemini extends gemini$1 {
|
|
|
203
203
|
// "time_ms": 1655323185000,
|
|
204
204
|
// "result": "failure",
|
|
205
205
|
// "highest_bid_price": "21661.90",
|
|
206
|
-
// "lowest_ask_price": "21663.
|
|
206
|
+
// "lowest_ask_price": "21663.78",
|
|
207
207
|
// "collar_price": "21662.845"
|
|
208
208
|
// },
|
|
209
209
|
// ]
|
package/dist/cjs/src/pro/okx.js
CHANGED
|
@@ -907,9 +907,6 @@ class okx extends okx$1 {
|
|
|
907
907
|
* @param {object} params extra parameters specific to the exchange API endpoint
|
|
908
908
|
* @returns {object[]} a list of [position structure]{@link https://docs.ccxt.com/en/latest/manual.html#position-structure}
|
|
909
909
|
*/
|
|
910
|
-
if (this.isEmpty(symbols)) {
|
|
911
|
-
throw new errors.ArgumentsRequired(this.id + ' watchPositions requires a list of symbols');
|
|
912
|
-
}
|
|
913
910
|
await this.loadMarkets();
|
|
914
911
|
await this.authenticate(params);
|
|
915
912
|
symbols = this.marketSymbols(symbols);
|
|
@@ -917,7 +914,23 @@ class okx extends okx$1 {
|
|
|
917
914
|
'instType': 'ANY',
|
|
918
915
|
};
|
|
919
916
|
const channel = 'positions';
|
|
920
|
-
|
|
917
|
+
let newPositions = undefined;
|
|
918
|
+
if (symbols === undefined) {
|
|
919
|
+
const arg = {
|
|
920
|
+
'channel': 'positions',
|
|
921
|
+
'instType': 'ANY',
|
|
922
|
+
};
|
|
923
|
+
const args = [arg];
|
|
924
|
+
const nonSymbolRequest = {
|
|
925
|
+
'op': 'subscribe',
|
|
926
|
+
'args': args,
|
|
927
|
+
};
|
|
928
|
+
const url = this.getUrl(channel, 'private');
|
|
929
|
+
newPositions = await this.watch(url, channel, nonSymbolRequest, channel);
|
|
930
|
+
}
|
|
931
|
+
else {
|
|
932
|
+
newPositions = await this.subscribeMultiple('private', channel, symbols, this.extend(request, params));
|
|
933
|
+
}
|
|
921
934
|
if (this.newUpdates) {
|
|
922
935
|
return newPositions;
|
|
923
936
|
}
|
|
@@ -1015,6 +1028,7 @@ class okx extends okx$1 {
|
|
|
1015
1028
|
client.resolve(positions, messageHash);
|
|
1016
1029
|
}
|
|
1017
1030
|
}
|
|
1031
|
+
client.resolve(newPositions, channel);
|
|
1018
1032
|
}
|
|
1019
1033
|
async watchOrders(symbol = undefined, since = undefined, limit = undefined, params = {}) {
|
|
1020
1034
|
/**
|