Merge remote-tracking branch 'upstream/develop' into feature/fetch-public-trades

This commit is contained in:
Joe Schr
2023-12-18 10:34:20 +01:00
124 changed files with 7802 additions and 2380 deletions

View File

@@ -521,11 +521,14 @@ class Exchange:
except ccxt.BaseError:
logger.exception('Unable to initialize markets.')
def reload_markets(self) -> None:
def reload_markets(self, force: bool = False) -> None:
"""Reload markets both sync and async if refresh interval has passed """
# Check whether markets have to be reloaded
if (self._last_markets_refresh > 0) and (
self._last_markets_refresh + self.markets_refresh_interval > dt_ts()):
if (
not force
and self._last_markets_refresh > 0
and (self._last_markets_refresh + self.markets_refresh_interval > dt_ts())
):
return None
logger.debug("Performing scheduled market reload..")
try:
@@ -1263,16 +1266,16 @@ class Exchange:
return order
except ccxt.InsufficientFunds as e:
raise InsufficientFundsError(
f'Insufficient funds to create {ordertype} sell order on market {pair}. '
f'Tried to sell amount {amount} at rate {limit_rate}. '
f'Message: {e}') from e
except ccxt.InvalidOrder as e:
f'Insufficient funds to create {ordertype} {side} order on market {pair}. '
f'Tried to {side} amount {amount} at rate {limit_rate} with '
f'stop-price {stop_price_norm}. Message: {e}') from e
except (ccxt.InvalidOrder, ccxt.BadRequest) as e:
# Errors:
# `Order would trigger immediately.`
raise InvalidOrderException(
f'Could not create {ordertype} sell order on market {pair}. '
f'Tried to sell amount {amount} at rate {limit_rate}. '
f'Message: {e}') from e
f'Could not create {ordertype} {side} order on market {pair}. '
f'Tried to {side} amount {amount} at rate {limit_rate} with '
f'stop-price {stop_price_norm}. Message: {e}') from e
except ccxt.DDoSProtection as e:
raise DDosProtection(e) from e
except (ccxt.NetworkError, ccxt.ExchangeError) as e:
@@ -1531,8 +1534,9 @@ class Exchange:
@retrier
def fetch_bids_asks(self, symbols: Optional[List[str]] = None, cached: bool = False) -> Dict:
"""
:param symbols: List of symbols to fetch
:param cached: Allow cached result
:return: fetch_tickers result
:return: fetch_bids_asks result
"""
if not self.exchange_has('fetchBidsAsks'):
return {}
@@ -1581,6 +1585,12 @@ class Exchange:
raise OperationalException(
f'Exchange {self._api.name} does not support fetching tickers in batch. '
f'Message: {e}') from e
except ccxt.BadSymbol as e:
logger.warning(f"Could not load tickers due to {e.__class__.__name__}. Message: {e} ."
"Reloading markets.")
self.reload_markets(True)
# Re-raise exception to repeat the call.
raise TemporaryError from e
except ccxt.DDoSProtection as e:
raise DDosProtection(e) from e
except (ccxt.NetworkError, ccxt.ExchangeError) as e:
@@ -2032,7 +2042,7 @@ class Exchange:
results = await asyncio.gather(*input_coro, return_exceptions=True)
for res in results:
if isinstance(res, Exception):
if isinstance(res, BaseException):
logger.warning(f"Async code raised an exception: {repr(res)}")
if raise_:
raise
@@ -2642,6 +2652,7 @@ class Exchange:
from_id = t[-1][1]
else:
logger.debug("Stopping as no more trades were returned.")
break
except asyncio.CancelledError:
logger.debug("Async operation Interrupted, breaking trades DL loop.")
@@ -2667,6 +2678,11 @@ class Exchange:
try:
t = await self._async_fetch_trades(pair, since=since)
if t:
# No more trades to download available at the exchange,
# So we repeatedly get the same trade over and over again.
if since == t[-1][0] and len(t) == 1:
logger.debug("Stopping because no more trades are available.")
break
since = t[-1][0]
trades.extend(t)
# Reached the end of the defined-download period
@@ -2675,6 +2691,7 @@ class Exchange:
f"Stopping because until was reached. {t[-1][0]} > {until}")
break
else:
logger.debug("Stopping as no more trades were returned.")
break
except asyncio.CancelledError:
logger.debug("Async operation Interrupted, breaking trades DL loop.")
@@ -3208,17 +3225,19 @@ class Exchange:
:param amount: Trade amount
:param open_date: Open date of the trade
:return: funding fee since open_date
:raises: ExchangeError if something goes wrong.
"""
if self.trading_mode == TradingMode.FUTURES:
if self._config['dry_run']:
funding_fees = self._fetch_and_calculate_funding_fees(
pair, amount, is_short, open_date)
else:
funding_fees = self._get_funding_fees_from_exchange(pair, open_date)
return funding_fees
else:
return 0.0
try:
if self._config['dry_run']:
funding_fees = self._fetch_and_calculate_funding_fees(
pair, amount, is_short, open_date)
else:
funding_fees = self._get_funding_fees_from_exchange(pair, open_date)
return funding_fees
except ExchangeError:
logger.warning(f"Could not update funding fees for {pair}.")
return 0.0
def get_liquidation_price(
self,