Announcement

Collapse

Looking for a User App or Add-On built by the NinjaTrader community?

Visit NinjaTrader EcoSystem and our free User App Share!

Have a question for the NinjaScript developer community? Open a new thread in our NinjaScript File Sharing Discussion Forum!
See more
See less

Partner 728x90

Collapse

Custom Class - Exit Manager

Collapse
X
 
  • Filter
  • Time
  • Show
Clear All
new posts

    Custom Class - Exit Manager

    Using the reference sample "SampleOnOrderUpdate", is it possible to refactor the management of an open position to a custom class (e.g. Exit Manager)?

    Please find attached a concept script "TestExitManagerOnOrderUpdate".
    The script appears to work on Playback101 State.Historical.
    It appears to fail at State.Realtime.
    Any guidance is appreciated.


    Alternatively, please advise why going down this path is simply ill-advised.
    Attached Files

    #2
    Originally posted by Shansen View Post
    It appears to fail at State.Realtime.
    Fail how?
    What benefit are you trying to achieve?

    I did something similar, but my 'OrderGroup' class acted more like a data container, a super 'struct' to contain all the myriad of details of a single position.

    Code:
    public class OrderGroup
    {
      public int OrderQuantity = 0;
      public Order EntryOrder = null;
      public Order StopOrder = null;
      public Order TargetOrder = null;
      public int EntryBar = 0;
      public string EntryName = null;
      ....
      public OrderGroup(int quantity)
      {
         OrderQuantity = quantity;
      }
      ....
      public void SetOrderQuantity(int NewQuantity)
      {
          ....
      }
      ....
    }
    I usually create an array of 1 or more OrderGroups, as needed,

    Code:
    private OrderGroup[] OrderGroups = new OrderGroup[]
    {
      new OrderGroup(1),
      ....
    }
    My properties directly update the class variables, like this, (although I made OrderQuantity a special case because I needed to perform other housekeeping, so it has a special SetOrderQuantity helper),

    Code:
    [Description("OrderGroup #1 quantity for order entry")]
    [GridCategory("Position Management")]
    [Gui.Design.DisplayName("OrderQuantity")]
    public int Group1_OrderQuantity
    {
        get { return OrderGroups[0].OrderQuantity; }
        set { OrderGroups[0].SetOrderQuantity(Math.Max(1, value)); }
    }
    Inside OnOrderUpdate/OnExecution, etc, I do things like,

    Code:
       int GroupIndex = 0;
       LookupOrder(order, out GroupIndex);  <-- in case I have multiple
       OrderGroup OG = OrderGroups[GroupIndex];
    
       if (order != null && order == OG.EntryOrder)
       ....
    Admittedly this is an NT7 example, but you get the idea. I designed my class around the goal of serving up a super 'container of data'. I was not too concerned with embedding much functionality into the class methods. I wanted a design metaphor in my code that helped organize all the various order data associated with one position, such as when I have multiple orders and multiple profit targets, these multiple data items are still parts of the same position. My goal of moving to Unmanaged mode was made simpler by using this design.

    What are the goals of your design?

    Comment


      #3
      hi bltdavid,

      I'm trying to get started on writing my own classes but I thought NT only allows/recommends to write own custom methods. Are you writing all the classes in the "main strategy page" or do you have different class files and call objects as needed in your main strategy page?

      Comment


        #4
        Hello Shansen,

        Thanks for the post.

        Support can not assist with any external data structures. The community should be able to help out with the testing.

        Please let me know if I may answer any questions on documented NinjaScript items.
        Chris L.NinjaTrader Customer Service

        Comment


          #5
          Originally posted by Boonfly8 View Post
          hi bltdavid,

          I'm trying to get started on writing my own classes but I thought NT only allows/recommends to write own custom methods. Are you writing all the classes in the "main strategy page" or do you have different class files and call objects as needed in your main strategy page?
          You can do anything you want -- this is .NET and C# is a big huge world. You have to remember, you are really just writing a 'plugin' for a .NET program called NinjaTrader.exe.

          A 'plugin' comes in two flavors, Indicator and Strategy, ok, well, NT8 adds a 3rd plugin type for Addons, and technically, yeah, ok ok, BarTypes would be another plugin, but I digress...

          These plugins are just objects derived from certain base classes, which are provided to you by the 'NinjaScript framework' -- which is just their large closed source class library made 'public' to you via NinjaTrader.exe.

          I started by making my own abstract base class, so that I could stuff lots of small utility methods (and utility classes, such as OrderGroup) into one central place, and then all my strategies inherit from this new base class, rather than just 'Strategy'. Of course, my abstract base class must first inherit from 'Strategy'.

          Think of it like creating a middle man. I'm inserting a class in-between my strategy class and the 'Strategy' class and the sole purpose of my middle man class is to 'export' a bunch of common things to those who derive from it -- ie, I'm making the class hierarchy fatter (or wider, and deeper, I suppose, but I digress... )

          For example ....

          In NT7, I created bltBaseStrategy.cs, storing it in the bin/Custom/Strategies folder,

          Code:
          namespace NinjaTrader.Strategy
          {
              abstract public class bltBaseStrategy : Strategy
              {
              ....
              }
          }
          Every strategy I write inherits from bltBaseStrategy. For example, I could take the @SampleMACrossover.cs strategy and make one change,

          Code:
          ....
          namespace NinjaTrader.Strategy
          {
              /// <summary>
              /// Simple moving average cross over strategy.
              /// </summary>
              [Description("Simple moving average cross over strategy.")]
              public class SampleMACrossOver : [B][COLOR=Red]bltBaseStrategy[/COLOR][/B]
              {
                  #region Variables
                  private int        fast    = 10;
                  private int        slow    = 25;
                  #endregion
                  ....
          and now this code has access to my 'super data' OrderGroup class defined in bltBaseStrategy.cs.

          The class hierarchy used to be:
          SampleMACrossover <-- Strategy <-- ...

          But I added my middle man class:
          SampleMACrossover <-- bltBaseStrategy <-- Strategy <-- ...

          Now anything defined in the 'bltBaseStrategy' class (plus the 'Strategy' class, plus all base classes 'Strategy' inherited from) is made available inside SampleMACrossover.

          Does that make sense?

          Comment


            #6
            bltdavid , the goal is to group all logic for exiting a position, and not intersperse it among the required implementation methods (e.g. OnOrderUpdate, OnExecutionUpdate).

            I was mistaken. The script works under Playback (Market Replay), Playback (Historical), and Live (Sim101).

            My concern is, my (possibly) incomplete knowledge of NT Managed Order Methods. By taking this approach I am inadvertently opening myself up to issues by using Orders outside the Strategy Class?

            Comment


              #7
              Originally posted by Shansen View Post
              the goal is to group all logic for exiting a position, and not intersperse it among the required implementation methods (e.g. OnOrderUpdate, OnExecutionUpdate).
              That sounds good and bad, it still depends on what you really mean. The arguments passed into the methods you mention should be dealt with quickly. Relegating the order handling logic (including some exit logic) to inside these methods is why these methods exist in the first place. Granted, I have my own routines, such as SetStopLossOrder() and SetProfitTargetOrder() -- for me, once the order is identified inside one of these routines, I dispatch it to an appropriate handler for further processing.

              Logic for exiting a position?
              What 'logic' are you referring to, exactly?

              For example, my exit logic for EndOfTradeHours, BreakEvenStops, AutoTrailStops, as well as MaxDailyProfit/Loss, is actually dispatched from within the OnBarUpdate method, using a secondary 1-Tick data series. I have no 'exit logic' inside the methods you mentioned, the great bulk of it just doesn't go there. (Ok, sure, I submit the StopLoss and ProfitTarget orders from inside OnExecution, but actual details of my order management code to handle BreakEven or AutoTrail stops, etc, is dispatched from inside OnBarUpdate, using the granularity of a 1-Tick secondary data series.)

              Originally posted by Shansen View Post
              I was mistaken. The script works under Playback (Market Replay), Playback (Historical), and Live (Sim101).
              Good to hear.

              Originally posted by Shansen View Post
              My concern is, my (possibly) incomplete knowledge of NT Managed Order Methods. By taking this approach I am inadvertently opening myself up to issues by using Orders outside the Strategy Class?
              Outside the Strategy class? Well, that depends on what you mean. If your code compiles, I don't think you're really outside the class.

              [Edit: Ah, I think you mean outside the inheritance chain, such that 'scope' becomes a somewhat major coding issue. Well, yes, that issue will probably arise sooner or later (see below for my example on trying to using Print), but it's more of a major coding hassle, rather than a show-stopping issue.]

              If you see benefits from organizing your code in the direction you are proceeding (aka, using an ExitManager class) then by all means, continue on your journey.

              Some issues you may have involve scope. For example, let's say you'd like to call Print() from within your ExitManager class. Well, you can't do that directly. Print is not within the scope of the ExitManager class. Why? Print comes from the 'Strategy' class, but your separate ExitManager class is not part of that inheritance hierarchy and doesn't get to call Print() for free. To overcome that, you'd have to pass 'this' into your ExitManager constructor and do a couple extra sophisticated tricks to call Print() from inside your ExitManager objects.

              If you can solve issues like this, and you still see benefits in your ExitManager class, then proceed. No one will stop you.

              I know my choice of a relatively clean 'data only' style class to maintain all variables related to a position has served me very well. I have lots of methods that know how to operate on an OrderGroup, but few of these methods actually reside inside the OrderGroup class itself (because like the issue I just mentioned above, doing it that way seemed to complicate certain things unnecessarily.)

              Good luck!
              Last edited by bltdavid; 07-03-2018, 06:28 PM.

              Comment


                #8
                I just studied your ExitManager code in detail.

                It appears you have the 'scope' issue well understood, since you're already passing 'this' into your ExitManager class constructor. Sorry, didn't exactly register that. My bad.

                It looks like the direction you're taking should work. I don't like it personally, but that's only because I have so much experience and success with my own 'data only' class.

                My only other point is to say this: look deeply into how your UpdateStop() method turned out. I personally find your requirement to prefix everything in the NinjaScript universe with your "_strat." extremely soul crushing.

                Why? Think of filling out your ExitManager class, with lots of new code (perhaps hundreds and hundreds of additional lines of code) for Breakeven and AutoTrail support, EndOfTradeHours, etc.

                Do you really think typing _strat.Low[0] and _strat.Close[0] and then continuing to type this prefix for every single NinjaScript method and variable, ad infinitum, is worth it?

                I don't. I think you're going down a path that produces some pretty awful looking code.

                It destroys readability and buys you some cheap encapsulation that you could have gotten differently.

                Yuck. Don't do that.
                Last edited by bltdavid; 07-03-2018, 09:32 PM.

                Comment


                  #9
                  I agree the concept script "TestExitManagerOnOrderUpdate" has elements with poor readability and generally some awful looking code.

                  I agree I am balancing readability against encapsulation.

                  Any suggestion for a different approach that achieves encapsulation without the drawbacks is very welcome.

                  Thanks again your insight.

                  Comment

                  Latest Posts

                  Collapse

                  Topics Statistics Last Post
                  Started by martin70, 03-24-2023, 04:58 AM
                  14 responses
                  105 views
                  0 likes
                  Last Post martin70  
                  Started by TraderBCL, Today, 04:38 AM
                  0 responses
                  2 views
                  0 likes
                  Last Post TraderBCL  
                  Started by Radano, 06-10-2021, 01:40 AM
                  19 responses
                  606 views
                  0 likes
                  Last Post Radano
                  by Radano
                   
                  Started by KenneGaray, Today, 03:48 AM
                  0 responses
                  4 views
                  0 likes
                  Last Post KenneGaray  
                  Started by thanajo, 05-04-2021, 02:11 AM
                  4 responses
                  470 views
                  0 likes
                  Last Post tradingnasdaqprueba  
                  Working...
                  X