Backtrader Community

    • Login
    • Search
    • Categories
    • Recent
    • Tags
    • Popular
    • Users
    • Groups
    • Search
    For code/output blocks: Use ``` (aka backtick or grave accent) in a single line before and after the block. See: http://commonmark.org/help/

    SELF.CANCEL() not working as expected.

    General Code/Help
    1
    1
    43
    Loading More Posts
    • Oldest to Newest
    • Newest to Oldest
    • Most Votes
    Reply
    • Reply as topic
    Log in to reply
    This topic has been deleted. Only users with topic management privileges can see it.
    • Jerry Inyang
      Jerry Inyang last edited by

      Re: Cancel Order

      Hello @backtrader. Self.cancel() doesn't seem to work in my strategy class. Can you help me check what I have implemented wrongly.

      CODE:

      import backtrader as bt
      from backtrader import indicators as ind
      from collections import deque
      from utils.tv_functions import na, nz, ternary
      from indicators import StGrab, AtrTrailStop, HullSuite, Halftrend, PPS, HtfEma
      
      import random
      
      class ParthStrategy(bt.Strategy):
          lines = ('sl',)
      
          def __init__(self):
              self.data_0 = self.datas[0]
              self.data_240 = self.datas[1]
      
              # Indicators
              self.stgrab = StGrab(self.data_240)
              self.htfema = HtfEma(self.data_240)
              self.hull_suite = HullSuite(self.data_240)
      
              self.halftrend = Halftrend(self.data_0)
              self.pps = PPS(self.data_0)
              self.ats = AtrTrailStop(self.data_0)
      
              # Variables
              self.window_cond_hull = deque([], maxlen=500)
              self.window_cond_touch_line = deque(['False', 'False'], maxlen=2)
              self.pend_long = False
              self.sl = bt.LineNum(float('nan'))
      
              # Strategy Variables
              self.order_entry = None
              self.order_close = None
              self.order_cancel = None
      
              self.active_trade = None
              self.active_trail = None
              
              self.trade_count = 0
          
          def log(self, _text, dt=None):
              dt = dt or self.datas[0].datetime.datetime(0)
              print(f'{dt.strftime("%Y-%m-%d %H:%M:%S")} : {_text}')
      
          def next(self):
              bar = self.data_0
      
              # region ----- CONDITIONS
              # St Grab
              cond_above_st = bar.close[0] > self.stgrab.lines.ema_high[0]
              cond_below_st = bar.close[0] < self.stgrab.lines.ema_low[0]
      
              # HTF EMAs
              cond_ema_long = (self.htfema.lines.ema_1[0] > self.htfema.lines.ema_2[0]) and (self.htfema.lines.ema_2[0] > self.htfema.lines.ema_3[0])
      
              # Hull Suite
              _hull_long = self.hull_suite.lines.hull[0] > self.hull_suite.lines.shull[0]
              self.window_cond_hull.appendleft(_hull_long)
              cond_hull_long = any(self.window_cond_hull)
      
              # Halftrend
              cond_ht_long = (not na(self.halftrend.lines.arrowUp[0])) and self.halftrend.lines.trend[0] == 0 and self.halftrend.lines.trend[-1] == 1
              cond_ht_short = (not na(self.halftrend.lines.arrowDown[0])) and self.halftrend.lines.trend[0] == 1 and self.halftrend.lines.trend[-1] == 0
      
              # ATR Trailing Stop
              cond_ats_long = self.ats.lines.cond_ats_long[0]
              cond_ats_short = self.ats.lines.cond_ats_short[0]
      
              sl_line = \
                  ternary((bar.close[0] > self.pps.l.Trailingsl[0]) and (bar.close[0] > self.ats.l.xATRTrailingStop), 
                  ternary((abs(bar.close[0] - self.pps.l.Trailingsl[0]) < abs(bar.close[0] - self.ats.l.xATRTrailingStop)), self.pps.l.Trailingsl[0], self.ats.l.xATRTrailingStop), 
                  ternary((bar.close[0] > self.pps.l.Trailingsl[0]), self.pps.l.Trailingsl[0], self.ats.l.xATRTrailingStop))
              
              cond_touch_line = bar.high[0] >= sl_line and bar.low[0] <= sl_line
              self.window_cond_touch_line.append(cond_touch_line)
      
              if self.window_cond_touch_line[0] and not self.window_cond_touch_line[1]:
                  self.sl[0] = sl_line - ((.45/100) * sl_line)
          
              # endregion
      
              # region ----- ENTRY
              if (not self.pend_long) and (cond_ht_long and cond_above_st ) and (self.position.size == 0) and (cond_ats_long): # Halftrend Long Signal, while Price Above Halftrend, and Halftrend above ST_GRaB
                  self.pend_long = True
                  
                  self.order_entry = self.buy(bar, price=bar.high, exectype=bt.Order.Stop) # strategy.entry('Buy', strategy.long, stop=high, comment = i_message_enter)  
                  self.log(f'<--- buy order sent ({bar.high[0]})--->')     
                  
              if self.pend_long and self.order_entry and (self.position.size == 0):
                  # Cancel Pending Orders
                  if (cond_ht_short or cond_ats_short or (not cond_hull_long) or (not cond_ema_long)):
                      # Cancel Buy Sequence If:
                      # - Short Signal from Halftrend
                      # - Current Price is below the ATR Line
                      # - No Buy Signal from Hull Suite in the last 500 bars
                      # - 4-hour EMA not in the right order, and MAPD is not within 4 and -4
                      self.pend_long = False
                      self.broker.cancel(self.order_entry) # strategy.cancel('Buy')
                      self.log(f'<--- cancel buy order sent --->')
      
                      self.sell(exectype=bt.Order.Stop, price=0.1, size=0)
              
              # endregion
      
              # region ----- EXIT
              if self.position.size > 0:
                  self.pend_long = False
                  
                  # MANUALLY MONITOR TRAILING STOP EXIT :
                  if (bar.low[0] <= self.sl[0]) and (bar.low[-1] > self.sl[-1]):
                      self.close()
                      self.log('<--- exit buy order sent : trailing stop triggered --->')
      
                  if cond_ats_short:
                      self.close()
                      self.log('<--- close buy signal sent : price below atr line --->')
              
              # endregion
      
          def notify_order(self, order):
              bar = self.data_0
      
              if order.status in [order.Accepted]:
                  self.log(f'<--- order recieved --->')
                  return
      
              # Check if an order has been completed
              # Attention: broker could reject order if not enough cash
              if order.status in [order.Completed]:
                  if order.isbuy():
                      pass
                  
                  elif order.issell():
                      pass
      
              elif order.status == order.Cancelled:
                  self.log(f'--- Cancel Buy Signal Sent (Confirmed)')
      
                      
          #         elif order.issell():
          #             self.log('--- Stop Loss Updated (Confirmed)')
      
          #     elif order.status in [order.Margin, order.Rejected]:
          #         self.log('ERROR: Order Margin/Rejected')
          #         self.pend_long = False
          #         self.order_entry = None
          #         self.trade_active = None
      
          def notify_trade(self, trade):
              if trade.justopened and trade.size > 0:
                  self.log(f'TRADE EXECUTED at {trade.price: .2f}')
              
              if trade.isclosed:
                  self.log(f'TRADE CLOSED at {trade.price: .2f}')
                  self.trade_count += 1
      
          def stop(self):
              print('Trades Completed : ', self.trade_count)
      
      
      
      1 Reply Last reply Reply Quote 0
      • 1 / 1
      • First post
        Last post
      Copyright © 2016, 2017, 2018, 2019, 2020, 2021 NodeBB Forums | Contributors