diff --git a/freqtrade/data/dataprovider.py b/freqtrade/data/dataprovider.py index 7e4fc36d48a..b979faff618 100644 --- a/freqtrade/data/dataprovider.py +++ b/freqtrade/data/dataprovider.py @@ -79,7 +79,7 @@ def _set_dataframe_max_index(self, limit_index: int): def _set_dataframe_max_date(self, limit_date: datetime): """ - Limit infomrative dataframe to max specified index. + Limit informative dataframe to max specified index. Only relevant in backtesting. :param limit_date: "current date" """ diff --git a/freqtrade/optimize/backtesting.py b/freqtrade/optimize/backtesting.py index 81784c9a3f1..a1ef29fa117 100644 --- a/freqtrade/optimize/backtesting.py +++ b/freqtrade/optimize/backtesting.py @@ -1486,8 +1486,9 @@ def backtest(self, processed: dict, start_date: datetime, end_date: datetime) -> current_detail_time: datetime = row[DATE_IDX].to_pydatetime() trade_dir: LongShort | None = self.check_for_trade_entry(row) + pair_has_open_trades = len(LocalTrade.bt_trades_open_pp[pair]) > 0 if ( - (trade_dir is not None or len(LocalTrade.bt_trades_open_pp[pair]) > 0) + (trade_dir is not None or pair_has_open_trades) and self.timeframe_detail and pair in self.detail_data ): @@ -1525,6 +1526,9 @@ def backtest(self, processed: dict, start_date: datetime, end_date: datetime) -> ) current_time_det += self.timeframe_detail_td is_first = False + if pair_has_open_trades and not len(LocalTrade.bt_trades_open_pp[pair]) > 0: + # Auto-lock pair for the rest of the candle if the trade has been closed. + break else: self.dataprovider._set_dataframe_max_date(current_time) self.backtest_loop(row, pair, current_time, trade_dir, not is_last_row) diff --git a/tests/optimize/test_backtesting.py b/tests/optimize/test_backtesting.py index 20db3088a29..81d63cf64fa 100644 --- a/tests/optimize/test_backtesting.py +++ b/tests/optimize/test_backtesting.py @@ -1647,8 +1647,8 @@ def _trend_alternate_hold(dataframe=None, metadata=None): if use_detail: # Backtest loop is called once per candle per pair # Exact numbers depend on trade state - but should be around 3_800 - assert bl_spy.call_count > 1_350 - assert bl_spy.call_count < 1_500 + assert bl_spy.call_count > 1_220 + assert bl_spy.call_count < 1_300 else: assert bl_spy.call_count < 995 @@ -1896,7 +1896,7 @@ def _trend_alternate_hold(dataframe=None, metadata=None): if use_detail: # Backtest loop is called once per candle per pair - assert bl_spy.call_count == 1523 + assert bl_spy.call_count == 1484 else: assert bl_spy.call_count == 479