Merge pull request #8661 from freqtrade/feat/datetimehelpers
Add datetime helpers, reduce arrow usage to a minimum
This commit is contained in:
@@ -5,7 +5,6 @@ from datetime import datetime, timedelta, timezone
|
||||
from random import randint
|
||||
from unittest.mock import MagicMock, Mock, PropertyMock, patch
|
||||
|
||||
import arrow
|
||||
import ccxt
|
||||
import pytest
|
||||
from ccxt import DECIMAL_PLACES, ROUND, ROUND_UP, TICK_SIZE, TRUNCATE
|
||||
@@ -23,6 +22,7 @@ from freqtrade.exchange.common import (API_FETCH_ORDER_RETRY_COUNT, API_RETRY_CO
|
||||
calculate_backoff, remove_exchange_credentials)
|
||||
from freqtrade.exchange.exchange import amount_to_contract_precision
|
||||
from freqtrade.resolvers.exchange_resolver import ExchangeResolver
|
||||
from freqtrade.util import dt_now, dt_ts
|
||||
from tests.conftest import (EXMS, generate_test_data_raw, get_mock_coro, get_patched_exchange,
|
||||
log_has, log_has_re, num_log_has_re)
|
||||
|
||||
@@ -644,7 +644,7 @@ def test_reload_markets(default_conf, mocker, caplog):
|
||||
exchange = get_patched_exchange(mocker, default_conf, api_mock, id="binance",
|
||||
mock_markets=False)
|
||||
exchange._load_async_markets = MagicMock()
|
||||
exchange._last_markets_refresh = arrow.utcnow().int_timestamp
|
||||
exchange._last_markets_refresh = dt_ts()
|
||||
|
||||
assert exchange.markets == initial_markets
|
||||
|
||||
@@ -655,7 +655,7 @@ def test_reload_markets(default_conf, mocker, caplog):
|
||||
|
||||
api_mock.load_markets = MagicMock(return_value=updated_markets)
|
||||
# more than 10 minutes have passed, reload is executed
|
||||
exchange._last_markets_refresh = arrow.utcnow().int_timestamp - 15 * 60
|
||||
exchange._last_markets_refresh = dt_ts(dt_now() - timedelta(minutes=15))
|
||||
exchange.reload_markets()
|
||||
assert exchange.markets == updated_markets
|
||||
assert exchange._load_async_markets.call_count == 1
|
||||
@@ -2076,7 +2076,7 @@ def test_get_historic_ohlcv(default_conf, mocker, caplog, exchange_name, candle_
|
||||
exchange = get_patched_exchange(mocker, default_conf, id=exchange_name)
|
||||
ohlcv = [
|
||||
[
|
||||
arrow.utcnow().int_timestamp * 1000, # unix timestamp ms
|
||||
dt_ts(), # unix timestamp ms
|
||||
1, # open
|
||||
2, # high
|
||||
3, # low
|
||||
@@ -2096,7 +2096,7 @@ def test_get_historic_ohlcv(default_conf, mocker, caplog, exchange_name, candle_
|
||||
ret = exchange.get_historic_ohlcv(
|
||||
pair,
|
||||
"5m",
|
||||
int((arrow.utcnow().int_timestamp - since) * 1000),
|
||||
dt_ts(dt_now() - timedelta(seconds=since)),
|
||||
candle_type=candle_type
|
||||
)
|
||||
|
||||
@@ -2114,7 +2114,7 @@ def test_get_historic_ohlcv(default_conf, mocker, caplog, exchange_name, candle_
|
||||
ret = exchange.get_historic_ohlcv(
|
||||
pair,
|
||||
"5m",
|
||||
int((arrow.utcnow().int_timestamp - since) * 1000),
|
||||
dt_ts(dt_now() - timedelta(seconds=since)),
|
||||
candle_type=candle_type
|
||||
)
|
||||
assert log_has_re(r"Async code raised an exception: .*", caplog)
|
||||
@@ -2166,7 +2166,7 @@ async def test__async_get_historic_ohlcv(default_conf, mocker, caplog, exchange_
|
||||
def test_refresh_latest_ohlcv(mocker, default_conf, caplog, candle_type) -> None:
|
||||
ohlcv = [
|
||||
[
|
||||
(arrow.utcnow().shift(minutes=-5).int_timestamp) * 1000, # unix timestamp ms
|
||||
dt_ts(dt_now() - timedelta(minutes=5)), # unix timestamp ms
|
||||
1, # open
|
||||
2, # high
|
||||
3, # low
|
||||
@@ -2174,7 +2174,7 @@ def test_refresh_latest_ohlcv(mocker, default_conf, caplog, candle_type) -> None
|
||||
5, # volume (in quote currency)
|
||||
],
|
||||
[
|
||||
arrow.utcnow().int_timestamp * 1000, # unix timestamp ms
|
||||
dt_ts(), # unix timestamp ms
|
||||
3, # open
|
||||
1, # high
|
||||
4, # low
|
||||
@@ -2364,7 +2364,7 @@ def test_refresh_latest_ohlcv_cache(mocker, default_conf, candle_type, time_mach
|
||||
async def test__async_get_candle_history(default_conf, mocker, caplog, exchange_name):
|
||||
ohlcv = [
|
||||
[
|
||||
arrow.utcnow().int_timestamp * 1000, # unix timestamp ms
|
||||
dt_ts(), # unix timestamp ms
|
||||
1, # open
|
||||
2, # high
|
||||
3, # low
|
||||
@@ -2401,7 +2401,7 @@ async def test__async_get_candle_history(default_conf, mocker, caplog, exchange_
|
||||
api_mock.fetch_ohlcv = MagicMock(side_effect=ccxt.BaseError("Unknown error"))
|
||||
exchange = get_patched_exchange(mocker, default_conf, api_mock, id=exchange_name)
|
||||
await exchange._async_get_candle_history(pair, "5m", CandleType.SPOT,
|
||||
(arrow.utcnow().int_timestamp - 2000) * 1000)
|
||||
dt_ts(dt_now() - timedelta(seconds=2000)))
|
||||
|
||||
exchange.close()
|
||||
|
||||
@@ -2410,7 +2410,7 @@ async def test__async_get_candle_history(default_conf, mocker, caplog, exchange_
|
||||
api_mock.fetch_ohlcv = MagicMock(side_effect=ccxt.NotSupported("Not supported"))
|
||||
exchange = get_patched_exchange(mocker, default_conf, api_mock, id=exchange_name)
|
||||
await exchange._async_get_candle_history(pair, "5m", CandleType.SPOT,
|
||||
(arrow.utcnow().int_timestamp - 2000) * 1000)
|
||||
dt_ts(dt_now() - timedelta(seconds=2000)))
|
||||
exchange.close()
|
||||
|
||||
|
||||
@@ -2433,7 +2433,7 @@ async def test__async_kucoin_get_candle_history(default_conf, mocker, caplog):
|
||||
with pytest.raises(DDosProtection, match=r'429 Too Many Requests'):
|
||||
await exchange._async_get_candle_history(
|
||||
"ETH/BTC", "5m", CandleType.SPOT,
|
||||
since_ms=(arrow.utcnow().int_timestamp - 2000) * 1000, count=3)
|
||||
since_ms=dt_ts(dt_now() - timedelta(seconds=2000)), count=3)
|
||||
assert num_log_has_re(msg, caplog) == 3
|
||||
|
||||
caplog.clear()
|
||||
@@ -2450,7 +2450,7 @@ async def test__async_kucoin_get_candle_history(default_conf, mocker, caplog):
|
||||
with pytest.raises(DDosProtection, match=r'429 Too Many Requests'):
|
||||
await exchange._async_get_candle_history(
|
||||
"ETH/BTC", "5m", CandleType.SPOT,
|
||||
(arrow.utcnow().int_timestamp - 2000) * 1000, count=3)
|
||||
dt_ts(dt_now() - timedelta(seconds=2000)), count=3)
|
||||
# Expect the "returned exception" message 12 times (4 retries * 3 (loop))
|
||||
assert num_log_has_re(msg, caplog) == 12
|
||||
assert num_log_has_re(msg2, caplog) == 9
|
||||
@@ -2908,14 +2908,14 @@ async def test__async_fetch_trades(default_conf, mocker, caplog, exchange_name,
|
||||
with pytest.raises(OperationalException, match=r'Could not fetch trade data*'):
|
||||
api_mock.fetch_trades = MagicMock(side_effect=ccxt.BaseError("Unknown error"))
|
||||
exchange = get_patched_exchange(mocker, default_conf, api_mock, id=exchange_name)
|
||||
await exchange._async_fetch_trades(pair, since=(arrow.utcnow().int_timestamp - 2000) * 1000)
|
||||
await exchange._async_fetch_trades(pair, since=dt_ts(dt_now() - timedelta(seconds=2000)))
|
||||
exchange.close()
|
||||
|
||||
with pytest.raises(OperationalException, match=r'Exchange.* does not support fetching '
|
||||
r'historical trade data\..*'):
|
||||
api_mock.fetch_trades = MagicMock(side_effect=ccxt.NotSupported("Not supported"))
|
||||
exchange = get_patched_exchange(mocker, default_conf, api_mock, id=exchange_name)
|
||||
await exchange._async_fetch_trades(pair, since=(arrow.utcnow().int_timestamp - 2000) * 1000)
|
||||
await exchange._async_fetch_trades(pair, since=dt_ts(dt_now() - timedelta(seconds=2000)))
|
||||
exchange.close()
|
||||
|
||||
|
||||
|
||||
Reference in New Issue
Block a user