Navigation

    Backtrader Community

    • Register
    • 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/

    Orders not executing with sufficient broker cash

    Indicators/Strategies/Analyzers
    1
    1
    53
    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.
    • V
      Vypy1 last edited by

      Hi, I am not sure why trades will not execute for certain stocks although there is enough balance for them to execute. I am giving my code below, it is based on random entry.

      Because I am using np.random.randint, my results will not be the same as yours so I will just give an outline of the result.

      Since I am asking the code to execute a trade randomly whenever rand_int = 20 and I have 10 datas in my feeds, it should execute 10 trades whenever the condition is met, of course that also means that I should have enough cash in the broker to execute all 10 trades. I am also asking the code to exit after 10 days.

      Now my problem is that after creation of my orders on 2016-06-30 all but 3 get executed on 2016-07-01. Have Look at Bajajfinsv, NTPC and ICICI in the results code, these are the orders that hit margin. My broker balance after execution of 7 of the 10 orders created is 19334, while Bajajfinsv trade cannot be executed since the order value (23216) is much more than the broker cash (19334), NTPC order value (1302.5) and ICICI (2186.8) should have got executed, but they didn't. Why would that be?

      class random_strat(bt.Strategy):
         
          
          def __init__(self):
              
              self.inds = {}
      
              for d in self.datas:
                  
                  self.inds[d] = {}
                  self.inds[d]['close'] = d.close
                  self.inds[d]['open'] = d.open
                  self.orders = {}
      
      
                   
          def log(self, txt, dt=None):
              dt = self.datas[0].datetime.date()
              print(f'Date: {dt}, {txt}')
              
          
          def notify_order(self, order):
              
                  
              if order.status in [order.Submitted, order.Accepted]:
                  return
      
      
              if order.status in [order.Completed]:
                  
                  if order.isbuy():
                      
                      self.log(f'BUY EXECUTED: {order.executed.price}, Cost: {order.executed.value}')
      
                      self.execprice = order.executed.price
                      self.totalcost = order.executed.value
                      self.bar_executed = len(self)
      
      
      #                 o2 = self.sell(data = order.data, exectype=bt.Order.Stop, price= 0.95 * self.execprice, )
      #                 o3 = self.sell(data = order.data, exectype=bt.Order.Limit, price = 1.10 * self.execprice, oco = o2)
      
      #                 self.log(f'STOP AT: {o2.created.price}, TARGET AT: {o3.created.price}')
      
      #                 self.orders[order.data].append(o2)
      #                 self.orders[order.data].append(o3)
                      
      #                 print(f'NEWLY ADDED: {self.orders}')
      
      
                  elif order.issell():
                      self.sellprice = order.executed.price
                      self.sellcost = order.executed.value
                      self.log(f'SELL EXECUTED: {self.sellprice}, Cost: {self.sellcost}')
      
              elif order.status in [order.Canceled, order.Margin, order.Rejected]:
                  self.log('Order Canceled/Margin/Rejected')
      
                  
              order_name = ['main', 'stop', 'limit', 'close']
              if not order.alive():
                  dorders = self.orders[order.data]
      #             print(f'DORDERS: {dorders}')
                  idx = dorders.index(order)
      #             print(f'IDX: {idx}')
                  dorders[idx] = None
      #             print(f'DORORDERSIDX: {dorders[idx]}')
                  self.log('-- No longer alive {} Ref'.format(order_name[idx]))
                  self.log(f'Account Balance: {cerebro.broker.getcash()}')
      
                  if all(x is None for x in dorders):
                      dorders[:] = []
      
      
          
          def notify_trade(self, trade):
              if trade.isopen:
                  return  
              
              
              else:
                  self.log(f'OPERATION PROFIT: GROSS {trade.pnl}, NET {trade.pnlcomm}, Trade PnL: {trade.pnlcomm/self.totalcost}')
                  self.log(f'Updated Account Balance: {cerebro.broker.getcash()}')
          
          
                  
                  
          def next(self):
              
              rand_int = np.random.randint(1, 50)
              print(f'RANDINT: {rand_int}')
              
              for d in self.datas:
                  
                  name = d._name
                  pos = self.getposition(d).size
                  self.log(f'{name}, Close: {d.close[0]}, Pos: {pos}')
                  
              
                  if not pos and not self.orders.get(d, None):
      
                      if self.inds[d]['open'][0] > 0 and rand_int == 20:
      
                          o1 = self.buy(data = d)
      
                          self.log(f'NAME: {name}, BUY CREATED: {o1.created.price}')
      
                          self.orders[d] = [o1]
              
                  elif pos:
                      if len(self) >= (self.bar_executed + 9):
                          o2 = self.sell(data = d)
                          self.log(f'NAME:{name}, SELL CREATED: {o2.created.price}')
                          self.orders[d].append(o2)
      
      
                      
      cerebro = bt.Cerebro()
      cerebro.broker.set_cash(250000)
      
      print(f'Starting Portfolio Value: {cerebro.broker.getvalue()}')
      
      
      for n in range(len(stock_df[:10])):
          dataset = list(zip(stock_df, names))
          data = bt.feeds.PandasData(dataname=dataset[n][0], datetime=None, open=-1, high=-1, low=-1, close=-1, volume=-1)
          cerebro.adddata(data, name = dataset[n][1])
      
      cerebro.addstrategy(random_strat)
      cerebro.addsizer(bt.sizers.FixedSize, stake=10)
      cerebro.addanalyzer(trades_list, _name = 'tradelist')
      # cerebro.addanalyzer(bt.analyzers.TradeAnalyzer, _name = 'ta')
      
      
      strat = cerebro.run(tradehistory = True)
      strats = strat[0].analyzers.tradelist.get_analysis()
      # strats_two = strat[0].analyzers.ta.get_analysis()
      trades = pd.DataFrame(strats)
      
      
      print(f'Final Portfolio Value: {cerebro.broker.getvalue()}')
      

      RESULTS:

      Date: 2016-06-30, JSWSTEEL, Close: 146.44, Pos: 0
      Date: 2016-06-30, NAME: JSWSTEEL, BUY CREATED: 146.44
      Date: 2016-06-30, MARUTI, Close: 4187.2, Pos: 0
      Date: 2016-06-30, NAME: MARUTI, BUY CREATED: 4187.2
      Date: 2016-06-30, ITC, Close: 245.6, Pos: 0
      Date: 2016-06-30, NAME: ITC, BUY CREATED: 245.6
      Date: 2016-06-30, ULTRACEMCO, Close: 3411.0, Pos: 0
      Date: 2016-06-30, NAME: ULTRACEMCO, BUY CREATED: 3411.0
      Date: 2016-06-30, SHREECEM, Close: 14546.5, Pos: 0
      Date: 2016-06-30, NAME: SHREECEM, BUY CREATED: 14546.5
      Date: 2016-06-30, TATASTEEL, Close: 303.19, Pos: 0
      Date: 2016-06-30, NAME: TATASTEEL, BUY CREATED: 303.19
      Date: 2016-06-30, HINDUNILVR, Close: 898.55, Pos: 0
      Date: 2016-06-30, NAME: HINDUNILVR, BUY CREATED: 898.55
      Date: 2016-06-30, BAJAJFINSV, Close: 2321.6, Pos: 0
      Date: 2016-06-30, NAME: BAJAJFINSV, BUY CREATED: 2321.6
      Date: 2016-06-30, NTPC, Close: 130.25, Pos: 0
      Date: 2016-06-30, NAME: NTPC, BUY CREATED: 130.25
      Date: 2016-06-30, ICICIBANK, Close: 218.68, Pos: 0
      Date: 2016-06-30, NAME: ICICIBANK, BUY CREATED: 218.68
      Date: 2016-07-01, Order Canceled/Margin/Rejected
      Date: 2016-07-01, -- No longer alive main Ref
      Date: 2016-07-01, Account Balance: 19334.399999999983
      Date: 2016-07-01, Order Canceled/Margin/Rejected
      Date: 2016-07-01, -- No longer alive main Ref
      Date: 2016-07-01, Account Balance: 19334.399999999983
      Date: 2016-07-01, Order Canceled/Margin/Rejected
      Date: 2016-07-01, -- No longer alive main Ref
      Date: 2016-07-01, Account Balance: 19334.399999999983
      Date: 2016-07-01, BUY EXECUTED: 147.51, Cost: 1475.1
      Date: 2016-07-01, -- No longer alive main Ref
      Date: 2016-07-01, Account Balance: 19334.399999999983
      Date: 2016-07-01, BUY EXECUTED: 4188.6, Cost: 41886.0
      Date: 2016-07-01, -- No longer alive main Ref
      Date: 2016-07-01, Account Balance: 19334.399999999983
      Date: 2016-07-01, BUY EXECUTED: 243.3, Cost: 2433.0
      Date: 2016-07-01, -- No longer alive main Ref
      Date: 2016-07-01, Account Balance: 19334.399999999983
      Date: 2016-07-01, BUY EXECUTED: 3410.0, Cost: 34100.0
      Date: 2016-07-01, -- No longer alive main Ref
      Date: 2016-07-01, Account Balance: 19334.399999999983
      Date: 2016-07-01, BUY EXECUTED: 14555.0, Cost: 145550.0
      Date: 2016-07-01, -- No longer alive main Ref
      Date: 2016-07-01, Account Balance: 19334.399999999983
      Date: 2016-07-01, BUY EXECUTED: 307.48, Cost: 3074.8
      Date: 2016-07-01, -- No longer alive main Ref
      Date: 2016-07-01, Account Balance: 19334.399999999983
      Date: 2016-07-01, BUY EXECUTED: 898.6, Cost: 8986.0
      Date: 2016-07-01, -- No longer alive main Ref
      Date: 2016-07-01, Account Balance: 19334.399999999983
      
      1 Reply Last reply Reply Quote 0
      • 1 / 1
      • First post
        Last post
      Copyright © 2016, 2017, 2018, 2019, 2020, 2021 NodeBB Forums | Contributors