@@ -1412,6 +1412,27 @@ def backtest_loop_inner(
14121412 return exiting_dir
14131413 return None
14141414
1415+ def get_detail_data (self , pair : str , row : tuple ) -> DataFrame | None :
1416+ """
1417+ Spread into detail data
1418+ """
1419+ current_detail_time : datetime = row [DATE_IDX ].to_pydatetime ()
1420+ exit_candle_end = current_detail_time + self .timeframe_td
1421+ detail_data = self .detail_data [pair ]
1422+ detail_data = detail_data .loc [
1423+ (detail_data ["date" ] >= current_detail_time ) & (detail_data ["date" ] < exit_candle_end )
1424+ ].copy ()
1425+
1426+ if len (detail_data ) == 0 :
1427+ return None
1428+ detail_data .loc [:, "enter_long" ] = row [LONG_IDX ]
1429+ detail_data .loc [:, "exit_long" ] = row [ELONG_IDX ]
1430+ detail_data .loc [:, "enter_short" ] = row [SHORT_IDX ]
1431+ detail_data .loc [:, "exit_short" ] = row [ESHORT_IDX ]
1432+ detail_data .loc [:, "enter_tag" ] = row [ENTER_TAG_IDX ]
1433+ detail_data .loc [:, "exit_tag" ] = row [EXIT_TAG_IDX ]
1434+ return detail_data
1435+
14151436 def time_pair_generator (
14161437 self , start_date : datetime , end_date : datetime , increment : timedelta , pairs : list [str ]
14171438 ):
@@ -1483,7 +1504,6 @@ def backtest(self, processed: dict, start_date: datetime, end_date: datetime) ->
14831504 is_last_row = current_time == end_date
14841505 self .dataprovider ._set_dataframe_max_index (self .required_startup + row_index )
14851506 self .dataprovider ._set_dataframe_max_date (current_time )
1486- current_detail_time : datetime = row [DATE_IDX ].to_pydatetime ()
14871507 trade_dir : LongShort | None = self .check_for_trade_entry (row )
14881508
14891509 pair_has_open_trades = len (LocalTrade .bt_trades_open_pp [pair ]) > 0
@@ -1495,24 +1515,13 @@ def backtest(self, processed: dict, start_date: datetime, end_date: datetime) ->
14951515 # Spread out into detail timeframe.
14961516 # Should only happen when we are either in a trade for this pair
14971517 # or when we got the signal for a new trade.
1498- exit_candle_end = current_detail_time + self .timeframe_td
1499-
1500- detail_data = self .detail_data [pair ]
1501- detail_data = detail_data .loc [
1502- (detail_data ["date" ] >= current_detail_time )
1503- & (detail_data ["date" ] < exit_candle_end )
1504- ].copy ()
1505- if len (detail_data ) == 0 :
1518+ detail_data = self .get_detail_data (pair , row )
1519+
1520+ if detail_data is None or len (detail_data ) == 0 :
15061521 # Fall back to "regular" data if no detail data was found for this candle
15071522 self .dataprovider ._set_dataframe_max_date (current_time )
15081523 self .backtest_loop (row , pair , current_time , trade_dir , not is_last_row )
15091524 continue
1510- detail_data .loc [:, "enter_long" ] = row [LONG_IDX ]
1511- detail_data .loc [:, "exit_long" ] = row [ELONG_IDX ]
1512- detail_data .loc [:, "enter_short" ] = row [SHORT_IDX ]
1513- detail_data .loc [:, "exit_short" ] = row [ESHORT_IDX ]
1514- detail_data .loc [:, "enter_tag" ] = row [ENTER_TAG_IDX ]
1515- detail_data .loc [:, "exit_tag" ] = row [EXIT_TAG_IDX ]
15161525 is_first = True
15171526 current_time_det = current_time
15181527 for det_row in detail_data [HEADERS ].values .tolist ():
0 commit comments