Fix unreliable backtest-result when using webserver mode
This commit is contained in:
parent
4c268847d4
commit
6319c104fe
@ -149,6 +149,8 @@ class DataProvider:
|
||||
Clear pair dataframe cache.
|
||||
"""
|
||||
self.__cached_pairs = {}
|
||||
self.__cached_pairs_backtesting = {}
|
||||
self.__slice_index = 0
|
||||
|
||||
# Exchange functions
|
||||
|
||||
|
@ -85,18 +85,7 @@ class Backtesting:
|
||||
"configuration or as cli argument `--timeframe 5m`")
|
||||
self.timeframe = str(self.config.get('timeframe'))
|
||||
self.timeframe_min = timeframe_to_minutes(self.timeframe)
|
||||
# Load detail timeframe if specified
|
||||
self.timeframe_detail = str(self.config.get('timeframe_detail', ''))
|
||||
if self.timeframe_detail:
|
||||
self.timeframe_detail_min = timeframe_to_minutes(self.timeframe_detail)
|
||||
if self.timeframe_min <= self.timeframe_detail_min:
|
||||
raise OperationalException(
|
||||
"Detail timeframe must be smaller than strategy timeframe.")
|
||||
|
||||
else:
|
||||
self.timeframe_detail_min = 0
|
||||
self.detail_data: Dict[str, DataFrame] = {}
|
||||
|
||||
self.init_backtest_detail()
|
||||
self.pairlists = PairListManager(self.exchange, self.config)
|
||||
if 'VolumePairList' in self.pairlists.name_list:
|
||||
raise OperationalException("VolumePairList not allowed for backtesting.")
|
||||
@ -119,14 +108,6 @@ class Backtesting:
|
||||
else:
|
||||
self.fee = self.exchange.get_fee(symbol=self.pairlists.whitelist[0])
|
||||
|
||||
Trade.use_db = False
|
||||
Trade.reset_trades()
|
||||
PairLocks.timeframe = self.config['timeframe']
|
||||
PairLocks.use_db = False
|
||||
PairLocks.reset_locks()
|
||||
|
||||
self.wallets = Wallets(self.config, self.exchange, log=False)
|
||||
|
||||
self.timerange = TimeRange.parse_timerange(
|
||||
None if self.config.get('timerange') is None else str(self.config.get('timerange')))
|
||||
|
||||
@ -135,9 +116,7 @@ class Backtesting:
|
||||
# Add maximum startup candle count to configuration for informative pairs support
|
||||
self.config['startup_candle_count'] = self.required_startup
|
||||
self.exchange.validate_required_startup_candles(self.required_startup, self.timeframe)
|
||||
|
||||
self.progress = BTProgress()
|
||||
self.abort = False
|
||||
self.init_backtest()
|
||||
|
||||
def __del__(self):
|
||||
self.cleanup()
|
||||
@ -147,6 +126,28 @@ class Backtesting:
|
||||
PairLocks.use_db = True
|
||||
Trade.use_db = True
|
||||
|
||||
def init_backtest_detail(self):
|
||||
# Load detail timeframe if specified
|
||||
self.timeframe_detail = str(self.config.get('timeframe_detail', ''))
|
||||
if self.timeframe_detail:
|
||||
self.timeframe_detail_min = timeframe_to_minutes(self.timeframe_detail)
|
||||
if self.timeframe_min <= self.timeframe_detail_min:
|
||||
raise OperationalException(
|
||||
"Detail timeframe must be smaller than strategy timeframe.")
|
||||
|
||||
else:
|
||||
self.timeframe_detail_min = 0
|
||||
self.detail_data: Dict[str, DataFrame] = {}
|
||||
|
||||
def init_backtest(self):
|
||||
|
||||
self.prepare_backtest(False)
|
||||
|
||||
self.wallets = Wallets(self.config, self.exchange, log=False)
|
||||
|
||||
self.progress = BTProgress()
|
||||
self.abort = False
|
||||
|
||||
def _set_strategy(self, strategy: IStrategy):
|
||||
"""
|
||||
Load strategy into backtesting
|
||||
@ -226,7 +227,8 @@ class Backtesting:
|
||||
Trade.reset_trades()
|
||||
self.rejected_trades = 0
|
||||
self.dataprovider.clear_cache()
|
||||
self._load_protections(self.strategy)
|
||||
if enable_protections:
|
||||
self._load_protections(self.strategy)
|
||||
|
||||
def check_abort(self):
|
||||
"""
|
||||
|
@ -47,33 +47,34 @@ async def api_start_backtest(bt_settings: BacktestRequest, background_tasks: Bac
|
||||
not ApiServer._bt
|
||||
or lastconfig.get('timeframe') != strat.timeframe
|
||||
or lastconfig.get('timeframe_detail') != btconfig.get('timeframe_detail')
|
||||
or lastconfig.get('dry_run_wallet') != btconfig.get('dry_run_wallet', 0)
|
||||
or lastconfig.get('timerange') != btconfig['timerange']
|
||||
):
|
||||
from freqtrade.optimize.backtesting import Backtesting
|
||||
ApiServer._bt = Backtesting(btconfig)
|
||||
if ApiServer._bt.timeframe_detail:
|
||||
ApiServer._bt.load_bt_data_detail()
|
||||
|
||||
else:
|
||||
ApiServer._bt.config = btconfig
|
||||
ApiServer._bt.init_backtest()
|
||||
# Only reload data if timeframe changed.
|
||||
if (
|
||||
not ApiServer._bt_data
|
||||
or not ApiServer._bt_timerange
|
||||
or lastconfig.get('stake_amount') != btconfig.get('stake_amount')
|
||||
or lastconfig.get('enable_protections') != btconfig.get('enable_protections')
|
||||
or lastconfig.get('protections') != btconfig.get('protections', [])
|
||||
or lastconfig.get('timeframe') != strat.timeframe
|
||||
):
|
||||
lastconfig['timerange'] = btconfig['timerange']
|
||||
lastconfig['protections'] = btconfig.get('protections', [])
|
||||
lastconfig['enable_protections'] = btconfig.get('enable_protections')
|
||||
lastconfig['dry_run_wallet'] = btconfig.get('dry_run_wallet')
|
||||
lastconfig['timeframe'] = strat.timeframe
|
||||
ApiServer._bt_data, ApiServer._bt_timerange = ApiServer._bt.load_bt_data()
|
||||
|
||||
lastconfig['timerange'] = btconfig['timerange']
|
||||
lastconfig['timeframe'] = strat.timeframe
|
||||
|
||||
lastconfig['protections'] = btconfig.get('protections', [])
|
||||
lastconfig['enable_protections'] = btconfig.get('enable_protections')
|
||||
lastconfig['dry_run_wallet'] = btconfig.get('dry_run_wallet')
|
||||
|
||||
ApiServer._bt.abort = False
|
||||
min_date, max_date = ApiServer._bt.backtest_one_strategy(
|
||||
strat, ApiServer._bt_data, ApiServer._bt_timerange)
|
||||
|
||||
ApiServer._bt.results = generate_backtest_stats(
|
||||
ApiServer._bt_data, ApiServer._bt.all_results,
|
||||
min_date=min_date, max_date=max_date)
|
||||
|
Loading…
Reference in New Issue
Block a user