ccxt 4.5.51 → 4.5.52

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.
@@ -107,7 +107,6 @@ class Exchange {
107
107
  this.validateClientSsl = false;
108
108
  this.timeout = 10000; // milliseconds
109
109
  this.verbose = false;
110
- this.twofa = undefined; // two-factor authentication (2-FA)
111
110
  this.balance = {};
112
111
  this.liquidations = undefined;
113
112
  this.orderbooks = {};
@@ -135,10 +134,10 @@ class Exchange {
135
134
  this.markets = undefined;
136
135
  this.features = undefined;
137
136
  this.status = undefined;
138
- this.rateLimit = undefined; // milliseconds
137
+ this.rateLimit = 2000; // milliseconds
139
138
  this.tokenBucket = undefined;
140
139
  this.throttler = undefined;
141
- this.enableRateLimit = undefined;
140
+ this.enableRateLimit = true;
142
141
  this.rollingWindowSize = 0.0; // set to 0.0 to use leaky bucket rate limiter
143
142
  this.rateLimiterAlgorithm = 'leakyBucket';
144
143
  this.httpExceptions = undefined;
@@ -162,10 +161,8 @@ class Exchange {
162
161
  this.exceptions = {};
163
162
  this.timeframes = {};
164
163
  this.version = undefined;
165
- this.marketsByAltname = undefined;
166
164
  this.name = undefined;
167
165
  this.targetAccount = undefined;
168
- this.stablePairs = {};
169
166
  this.httpProxyAgentModule = undefined;
170
167
  this.httpsProxyAgentModule = undefined;
171
168
  this.socksProxyAgentModule = undefined;
@@ -699,7 +696,7 @@ class Exchange {
699
696
  if (typeof userAgent === 'string') {
700
697
  headers = this.extend({ 'User-Agent': userAgent }, headers);
701
698
  }
702
- else if ((typeof userAgent === 'object') && ('User-Agent' in userAgent)) {
699
+ else if (this.isDictionary(userAgent) && ('User-Agent' in userAgent)) {
703
700
  headers = this.extend(userAgent, headers);
704
701
  }
705
702
  }
@@ -1793,15 +1790,16 @@ class Exchange {
1793
1790
  // METHODS BELOW THIS LINE ARE TRANSPILED FROM TYPESCRIPT
1794
1791
  describe() {
1795
1792
  return {
1796
- 'id': undefined,
1797
- 'name': undefined,
1798
- 'countries': undefined,
1799
- 'enableRateLimit': true,
1800
- 'rateLimit': 2000,
1793
+ 'id': this.id,
1794
+ 'name': this.name,
1795
+ 'countries': this.countries,
1796
+ 'enableRateLimit': this.enableRateLimit,
1797
+ 'rateLimit': this.rateLimit,
1798
+ 'rateLimiterAlgorithm': this.rateLimiterAlgorithm,
1801
1799
  'timeout': this.timeout,
1802
- 'certified': false,
1803
- 'pro': false,
1804
- 'alias': false,
1800
+ 'certified': this.certified,
1801
+ 'pro': this.pro,
1802
+ 'alias': this.alias,
1805
1803
  'dex': false,
1806
1804
  'has': {
1807
1805
  'publicAPI': true,
@@ -2047,9 +2045,12 @@ class Exchange {
2047
2045
  'urls': {
2048
2046
  'logo': undefined,
2049
2047
  'api': undefined,
2048
+ 'test': undefined,
2050
2049
  'www': undefined,
2051
2050
  'doc': undefined,
2051
+ 'api_management': undefined,
2052
2052
  'fees': undefined,
2053
+ 'referral': undefined,
2053
2054
  },
2054
2055
  'api': undefined,
2055
2056
  'requiredCredentials': {
@@ -2086,6 +2087,7 @@ class Exchange {
2086
2087
  'updated': undefined,
2087
2088
  'eta': undefined,
2088
2089
  'url': undefined,
2090
+ 'info': undefined,
2089
2091
  },
2090
2092
  'exceptions': undefined,
2091
2093
  'httpExceptions': {
@@ -2176,7 +2178,7 @@ class Exchange {
2176
2178
  if (value === undefined) {
2177
2179
  return defaultValue;
2178
2180
  }
2179
- if ((typeof value === 'object') && !Array.isArray(value)) {
2181
+ if (this.isDictionary(value)) {
2180
2182
  return value;
2181
2183
  }
2182
2184
  return defaultValue;
@@ -2192,7 +2194,7 @@ class Exchange {
2192
2194
  if (value === undefined) {
2193
2195
  return defaultValue;
2194
2196
  }
2195
- if ((typeof value === 'object') && !Array.isArray(value)) {
2197
+ if (this.isDictionary(value)) {
2196
2198
  return value;
2197
2199
  }
2198
2200
  return defaultValue;
@@ -2222,6 +2224,9 @@ class Exchange {
2222
2224
  }
2223
2225
  return defaultValue;
2224
2226
  }
2227
+ isDictionary(value) {
2228
+ return (value !== undefined) && (typeof value === 'object') && !Array.isArray(value);
2229
+ }
2225
2230
  safeList2(dictionaryOrList, key1, key2, defaultValue = undefined) {
2226
2231
  /**
2227
2232
  * @ignore
@@ -5974,7 +5979,7 @@ class Exchange {
5974
5979
  if (triggerPrice === undefined) {
5975
5980
  throw new errors.ArgumentsRequired(this.id + ' createTriggerOrder() requires a triggerPrice argument');
5976
5981
  }
5977
- params['triggerPrice'] = triggerPrice;
5982
+ params = this.extend(params, { 'triggerPrice': triggerPrice });
5978
5983
  if (this.has['createTriggerOrder']) {
5979
5984
  return await this.createOrder(symbol, type, side, amount, price, params);
5980
5985
  }
@@ -5997,7 +6002,7 @@ class Exchange {
5997
6002
  if (triggerPrice === undefined) {
5998
6003
  throw new errors.ArgumentsRequired(this.id + ' createTriggerOrderWs() requires a triggerPrice argument');
5999
6004
  }
6000
- params['triggerPrice'] = triggerPrice;
6005
+ params = this.extend(params, { 'triggerPrice': triggerPrice });
6001
6006
  if (this.has['createTriggerOrderWs']) {
6002
6007
  return await this.createOrderWs(symbol, type, side, amount, price, params);
6003
6008
  }
@@ -6020,7 +6025,7 @@ class Exchange {
6020
6025
  if (stopLossPrice === undefined) {
6021
6026
  throw new errors.ArgumentsRequired(this.id + ' createStopLossOrder() requires a stopLossPrice argument');
6022
6027
  }
6023
- params['stopLossPrice'] = stopLossPrice;
6028
+ params = this.extend(params, { 'stopLossPrice': stopLossPrice });
6024
6029
  if (this.has['createStopLossOrder']) {
6025
6030
  return await this.createOrder(symbol, type, side, amount, price, params);
6026
6031
  }
@@ -6043,7 +6048,7 @@ class Exchange {
6043
6048
  if (stopLossPrice === undefined) {
6044
6049
  throw new errors.ArgumentsRequired(this.id + ' createStopLossOrderWs() requires a stopLossPrice argument');
6045
6050
  }
6046
- params['stopLossPrice'] = stopLossPrice;
6051
+ params = this.extend(params, { 'stopLossPrice': stopLossPrice });
6047
6052
  if (this.has['createStopLossOrderWs']) {
6048
6053
  return await this.createOrderWs(symbol, type, side, amount, price, params);
6049
6054
  }
@@ -6066,7 +6071,7 @@ class Exchange {
6066
6071
  if (takeProfitPrice === undefined) {
6067
6072
  throw new errors.ArgumentsRequired(this.id + ' createTakeProfitOrder() requires a takeProfitPrice argument');
6068
6073
  }
6069
- params['takeProfitPrice'] = takeProfitPrice;
6074
+ params = this.extend(params, { 'takeProfitPrice': takeProfitPrice });
6070
6075
  if (this.has['createTakeProfitOrder']) {
6071
6076
  return await this.createOrder(symbol, type, side, amount, price, params);
6072
6077
  }
@@ -6089,7 +6094,7 @@ class Exchange {
6089
6094
  if (takeProfitPrice === undefined) {
6090
6095
  throw new errors.ArgumentsRequired(this.id + ' createTakeProfitOrderWs() requires a takeProfitPrice argument');
6091
6096
  }
6092
- params['takeProfitPrice'] = takeProfitPrice;
6097
+ params = this.extend(params, { 'takeProfitPrice': takeProfitPrice });
6093
6098
  if (this.has['createTakeProfitOrderWs']) {
6094
6099
  return await this.createOrderWs(symbol, type, side, amount, price, params);
6095
6100
  }
@@ -6514,7 +6519,7 @@ class Exchange {
6514
6519
  return false;
6515
6520
  }
6516
6521
  handleWithdrawTagAndParams(tag, params) {
6517
- if ((tag !== undefined) && (typeof tag === 'object')) {
6522
+ if (this.isDictionary(tag)) {
6518
6523
  params = this.extend(tag, params);
6519
6524
  tag = undefined;
6520
6525
  }
@@ -6567,7 +6572,7 @@ class Exchange {
6567
6572
  return undefined;
6568
6573
  }
6569
6574
  const market = this.market(symbol);
6570
- return this.decimalToPrecision(cost, TRUNCATE, market['precision']['price'], this.precisionMode, this.paddingMode);
6575
+ return this.decimalToPrecision(cost, TRUNCATE, this.safeString2(market['precision'], 'cost', 'price'), this.precisionMode, this.paddingMode);
6571
6576
  }
6572
6577
  priceToPrecision(symbol, price) {
6573
6578
  if (price === undefined) {
@@ -13,6 +13,9 @@ class bequant extends hitbtc["default"] {
13
13
  'name': 'Bequant',
14
14
  'pro': true,
15
15
  'countries': ['MT'],
16
+ 'has': {
17
+ 'swap': false,
18
+ },
16
19
  'urls': {
17
20
  'logo': 'https://github.com/user-attachments/assets/0583ef1f-29fe-4b7c-8189-63565a0e2867',
18
21
  'api': {
@@ -1496,6 +1496,7 @@ class binance extends binance$1["default"] {
1496
1496
  'BUSD': 'USD',
1497
1497
  },
1498
1498
  'defaultWithdrawPrecision': 0.00000001,
1499
+ 'defaultFiatWithdrawPrecision': 0.01,
1499
1500
  },
1500
1501
  'features': {
1501
1502
  'spot': {
@@ -3059,59 +3060,48 @@ class binance extends binance$1["default"] {
3059
3060
  // ]
3060
3061
  // }
3061
3062
  //
3063
+ // some coins (e.g. ETH, BIGTIME, SONIC, etc) return extra fields under network entry
3064
+ //
3065
+ // "specialTips": "",
3066
+ // "specialWithdrawTips": "",
3067
+ // "withdrawInternalMin": "0",
3068
+ // "contractAddressUrl": "https://etherscan.io/address/",
3069
+ // "contractAddress": "0x64bc2ca1be492be7185faa2c8835d9b824c8a194"
3070
+ //
3062
3071
  const entry = responseCurrencies[i];
3063
3072
  const id = this.safeString(entry, 'coin');
3064
3073
  const name = this.safeString(entry, 'name');
3065
3074
  const code = this.safeCurrencyCode(id);
3066
3075
  const isFiat = this.safeBool(entry, 'isLegalMoney');
3067
- let minPrecision = undefined;
3068
- let isWithdrawEnabled = true;
3069
- let isDepositEnabled = true;
3070
3076
  const networkList = this.safeList(entry, 'networkList', []);
3071
3077
  const fees = {};
3072
- let fee = undefined;
3073
3078
  const networks = {};
3079
+ let isETF = false;
3074
3080
  for (let j = 0; j < networkList.length; j++) {
3075
3081
  const networkItem = networkList[j];
3076
3082
  const network = this.safeString(networkItem, 'network');
3077
3083
  const networkCode = this.networkIdToCode(network, code);
3078
- const isETF = (network === 'ETF'); // e.g. BTCUP, ETHDOWN
3084
+ isETF = (network === 'ETF'); // ETF currencies (e.g. BTCUP, ETHDOWN) have only 1 "network" entry and are deterministic to set
3079
3085
  // const name = this.safeString (networkItem, 'name');
3080
3086
  const withdrawFee = this.safeNumber(networkItem, 'withdrawFee');
3081
3087
  const depositEnable = this.safeBool(networkItem, 'depositEnable');
3082
3088
  const withdrawEnable = this.safeBool(networkItem, 'withdrawEnable');
3083
- isDepositEnabled = isDepositEnabled || depositEnable;
3084
- isWithdrawEnabled = isWithdrawEnabled || withdrawEnable;
3085
3089
  fees[network] = withdrawFee;
3086
- const isDefault = this.safeBool(networkItem, 'isDefault');
3087
- if (isDefault || (fee === undefined)) {
3088
- fee = withdrawFee;
3089
- }
3090
+ this.safeBool(networkItem, 'isDefault');
3090
3091
  // todo: default networks in "setMarkets" overload
3091
3092
  // if (isDefault) {
3092
3093
  // this.options['defaultNetworkCodesForCurrencies'][code] = networkCode;
3093
3094
  // }
3094
- const precisionTick = this.safeString(networkItem, 'withdrawIntegerMultiple');
3095
- let withdrawPrecision = precisionTick;
3096
- // avoid zero values, which are mostly from fiat or leveraged tokens or some abandoned coins : https://github.com/ccxt/ccxt/pull/14902#issuecomment-1271636731
3097
- if (!Precise["default"].stringEq(precisionTick, '0')) {
3098
- minPrecision = (minPrecision === undefined) ? precisionTick : Precise["default"].stringMin(minPrecision, precisionTick);
3099
- }
3100
- else {
3101
- if (!isFiat && !isETF) {
3102
- // non-fiat and non-ETF currency, there are many cases when precision is set to zero (probably bug, we've reported to binance already)
3103
- // in such cases, we can set default precision of 8 (which is in UI for such coins)
3104
- withdrawPrecision = this.omitZero(this.safeString(networkItem, 'withdrawInternalMin'));
3105
- if (withdrawPrecision === undefined) {
3106
- withdrawPrecision = this.safeString(this.options, 'defaultWithdrawPrecision');
3107
- }
3108
- }
3095
+ let withdrawPrecision = this.omitZero(this.safeString2(networkItem, 'withdrawIntegerMultiple', 'withdrawInternalMin'));
3096
+ // zero values happen only on fiat or leveraged(ETF) tokens: https://t.me/binance_api_english/393075
3097
+ if (withdrawPrecision === undefined && isFiat) {
3098
+ withdrawPrecision = this.safeString(this.options, 'defaultFiatWithdrawPrecision');
3109
3099
  }
3110
3100
  networks[networkCode] = {
3111
3101
  'info': networkItem,
3112
3102
  'id': network,
3113
3103
  'network': networkCode,
3114
- 'active': depositEnable && withdrawEnable,
3104
+ 'active': undefined,
3115
3105
  'deposit': depositEnable,
3116
3106
  'withdraw': withdrawEnable,
3117
3107
  'fee': withdrawFee,
@@ -3128,8 +3118,17 @@ class binance extends binance$1["default"] {
3128
3118
  },
3129
3119
  };
3130
3120
  }
3121
+ let type = undefined;
3122
+ if (isETF) {
3123
+ type = 'other';
3124
+ }
3125
+ else if (isFiat) {
3126
+ type = 'fiat';
3127
+ }
3128
+ else {
3129
+ type = 'crypto';
3130
+ }
3131
3131
  const trading = this.safeBool(entry, 'trading');
3132
- const active = (isWithdrawEnabled && isDepositEnabled && trading);
3133
3132
  const marginEntry = this.safeDict(marginablesById, id, {});
3134
3133
  //
3135
3134
  // {
@@ -3141,22 +3140,22 @@ class binance extends binance$1["default"] {
3141
3140
  // userMinRepay: "0",
3142
3141
  // }
3143
3142
  //
3144
- result[code] = {
3143
+ result[code] = this.safeCurrencyStructure({
3145
3144
  'id': id,
3146
3145
  'name': name,
3147
3146
  'code': code,
3148
- 'type': isFiat ? 'fiat' : 'crypto',
3149
- 'precision': this.parseNumber(minPrecision),
3147
+ 'type': type,
3148
+ 'precision': undefined,
3150
3149
  'info': entry,
3151
- 'active': active,
3152
- 'deposit': isDepositEnabled,
3153
- 'withdraw': isWithdrawEnabled,
3150
+ 'active': trading,
3151
+ 'deposit': undefined,
3152
+ 'withdraw': undefined,
3154
3153
  'networks': networks,
3155
- 'fee': fee,
3154
+ 'fee': undefined,
3156
3155
  'fees': fees,
3157
- 'limits': this.limits,
3156
+ 'limits': undefined,
3158
3157
  'margin': this.safeBool(marginEntry, 'isBorrowable'),
3159
- };
3158
+ });
3160
3159
  }
3161
3160
  return result;
3162
3161
  }
@@ -33,6 +33,7 @@ class binanceusdm extends binance["default"] {
33
33
  'fetchMarkets': {
34
34
  'types': ['linear'],
35
35
  },
36
+ 'defaultType': 'swap',
36
37
  'defaultSubType': 'linear',
37
38
  // https://www.binance.com/en/support/faq/360033162192
38
39
  // tier amount, maintenance margin, initial margin,
@@ -487,13 +487,17 @@ class grvt extends grvt$1["default"] {
487
487
  * @returns response from exchange
488
488
  */
489
489
  async signIn(params = {}) {
490
- if (this.usesPrivateKey()) {
491
- await this.signInWithPrivateKey(params);
492
- await this.initializeClient(params);
493
- }
494
- else {
495
- await this.signInWithApiKey(params);
490
+ // if (this.usesPrivateKey ()) {
491
+ // await this.signInWithPrivateKey (params);
492
+ // await this.initializeClient (params);
493
+ // } else {
494
+ // await this.signInWithApiKey (params);
495
+ // }
496
+ if (this.privateKey === undefined || this.privateKey === '') {
497
+ throw new errors.PermissionDenied('Private key is required for this operation. If you used joined GRVT through email registration instead of Web3 wallet, then read: https://github.com/ccxt/ccxt/wiki/FAQ#how-to-use-the-grvt-exchange-in-ccxt');
496
498
  }
499
+ await this.signInWithPrivateKey(params);
500
+ await this.initializeClient(params);
497
501
  await this.loadAccountInfos();
498
502
  return true;
499
503
  }
@@ -1966,7 +1970,10 @@ class grvt extends grvt$1["default"] {
1966
1970
  else {
1967
1971
  throw new errors.InvalidOrder(this.id + ' createOrder(): order side must be either "buy" or "sell"');
1968
1972
  }
1969
- const clientOrderId = this.safeString(params, 'clientOrderId');
1973
+ let clientOrderId = this.safeString(params, 'clientOrderId');
1974
+ if (clientOrderId === undefined) {
1975
+ clientOrderId = this.nonce().toString() + '000' + this.requestId().toString();
1976
+ }
1970
1977
  params = this.omit(params, ['clientOrderId']);
1971
1978
  const isMarketOrder = (type === 'market');
1972
1979
  const orderRequest = {
@@ -1975,7 +1982,7 @@ class grvt extends grvt$1["default"] {
1975
1982
  'legs': [orderLeg],
1976
1983
  'signature': this.defaultSignature(),
1977
1984
  'metadata': {
1978
- 'client_order_id': clientOrderId !== undefined ? clientOrderId : this.nonce().toString() + '000' + this.requestId().toString(),
1985
+ 'client_order_id': clientOrderId,
1979
1986
  },
1980
1987
  'is_market': isMarketOrder,
1981
1988
  'post_only': false,
@@ -649,6 +649,10 @@ class kraken extends kraken$1["default"] {
649
649
  const result = [];
650
650
  for (let i = 0; i < keys.length; i++) {
651
651
  const id = keys[i];
652
+ let isSynthetic = false;
653
+ if (id.indexOf(':BTNL') >= 0) {
654
+ isSynthetic = true;
655
+ }
652
656
  const market = markets[id];
653
657
  const baseIdRaw = this.safeString(market, 'base');
654
658
  const quoteIdRaw = this.safeString(market, 'quote');
@@ -686,10 +690,11 @@ class kraken extends kraken$1["default"] {
686
690
  }
687
691
  const status = this.safeString(market, 'status');
688
692
  const isActive = status === 'online';
693
+ const symbol = (!isSynthetic) ? (base + '/' + quote) : id;
689
694
  result.push({
690
695
  'id': id,
691
696
  'wsId': this.safeString(market, 'wsname'),
692
- 'symbol': base + '/' + quote,
697
+ 'symbol': symbol,
693
698
  'base': base,
694
699
  'quote': quote,
695
700
  'settle': undefined,