User Tools

Site Tools


the_unlimited_power_of_modules

The Unlimited Power of Python Modules

Disclaimer: this is a fairly advanced tutorial which you do not need to understand in order to use SystemTrader. Unless you are a seasoned programmer, this will probably not help you.

If not familiar with the TSL language yet, you should start with this introduction instead.

Why Use Python Modules

Modules provide programmers with the unlimited power of Python, in a way that integrates well with SystemTrader. They can be used to assist the creation of technical indicators and trading systems, typically to perform complex operations using functions, classes, and variables in a way that would not be practical within a TSL script.

Modules can also be used to literally extend SystemTrader. Such an extension (albeit a modest one) is described in this tutorial.

Creating a new Module

In the sidebar, under UTILITIES, click TSL Modules.

In the list-view, click [Click here to add a new module…]. Give a name to the new module then press ENTER.

Programming the Module

Modules are coded in the Python language. Unlike in technical indicators and trading systems, SystemTrader does not provide any additional language feature in modules: they are made in plain Python.

Here is the example of a module which allows one to import transaction data into SystemTrader:

MakePortfolio
import struct
import os
import os.path
 
PACK_TRADE  = "<HHIHHdHHddddd"
 
FILE_PARAM  = "parameters.xml"
FILE_TICKER = "tickers.txt"
FILE_TRADE  = "trades"
 
class CTrade:
    def __init__(self, Ticker, IsShort, NumShares, Date, Price, Commission, CurrencyRate):
        self.Ticker = Ticker       # string identifier corresponding to the path of the ticker in Workspace/Tickers (for example "yahoo_us/US/AAPL")
        self.IsShort = IsShort     # boolean value: True = selling, False = buying
        self.OrderType = 0         # integer value: 0 = MARKET, 1 = LIMIT, 2 = STOP, 3 = TRAILING-STOP
        self.NumShares = NumShares # number of shares in this trade
        self.CreationDate = Date   # date of order creation
        self.FillDate = Date       # date of order fill
        self.Price1 = Price        # limit/market price
        self.FillPrice = Price     # fill price
        self.Commission = Commission # trade commission
        self.CurrencyRate = CurrencyRate # currency rate
        self.Spread = 0            # spread
 
class CParameters:
    pass # no parameter for now
 
class CTradeTickers:
    def __init__(self):
        self.Tickers = []
 
    def GetTickerNum(self, Ticker):
        if Ticker in self.Tickers:
            return self.Tickers.index(Ticker)
        else:
            self.Tickers.append(Ticker)
            return len(self.Tickers) - 1
 
def GetCompressedDate(Date):
    D = Date % 100
    M = (Date - D) % 10000
    Y = (Date - D - M) / 10000
    M /= 100
    assert D<32 and M<13 and Y>1900 and Y<2150
    return ((Y-1900)<<9) + (M<<5) + D
 
def WriteParameters(PortfolioDir, Parameters):
    File = open(os.path.join(PortfolioDir, FILE_PARAM), 'w')
    File.write('''<?xml version="1.0" encoding="iso-8859-15"?>
<root>
</root>''')
    File.close()
 
def PackTrades(PortfolioDir, Trades):
    TradeTickers = CTradeTickers()
    TradeData = [struct.pack(PACK_TRADE,
                             TradeTickers.GetTickerNum(T.Ticker),
                             ((T.IsShort) | (T.OrderType<<1)),
                             T.NumShares,
                             GetCompressedDate(T.CreationDate), 0,
                             T.Price1,
                             GetCompressedDate(T.FillDate), 0,
                             T.FillPrice,
                             T.Spread,
                             T.Commission,
                             T.CurrencyRate, 0)
                     for T in Trades]
    File = open(os.path.join(PortfolioDir, FILE_TRADE), "wb")
    File.write("".join(TradeData))
    File.close()
 
    File = open(os.path.join(PortfolioDir, FILE_TICKER), "w")
    File.write("\n".join(TradeTickers.Tickers))
    File.close()
 
def CreatePortfolio(PortfolioDir, Trades, Parameters=CParameters()):
    if os.path.isdir(PortfolioDir):
        raise Exception("This directory already exists.")
    os.mkdir(PortfolioDir)
    WriteParameters(PortfolioDir, Parameters)
    PackTrades(PortfolioDir, Trades)
    print 'Portfolio created:', PortfolioDir

Using a Module from the Interpreter

In the side-bar, under UTILITIES, click TSL Interpreter.

>>> import MakePortfolio
>>> Trade1 = MakePortfolio.CTrade("yahoo_us/US/AAPL", False, 10, 20110203, 343.44, 5.00, 1.0)
>>> Directory = '/SamplePortfolio'
>>> MakePortfolio.CreatePortfolio(Directory, [Trade1])

A new portfolio is created in the /SamplePortfolio directory. To use it, copy this directory into [Your SystemTrader Workspace]/Portfolios and re-launch SystemTrader.

The “MakePortfolio” module could be used, for example, to parse any kind of transaction data and import it into SystemTrader.

Using a Module from Indicators and Trading Systems

Modules can be used from TSL Indicators and Trading Systems without any “import” statement. Just use the module namespace from inside the indicator/system:

IndicatorXYZ
return ModuleXYZ.DoComplexComputation(Open, High, Low, Close, Volume)
the_unlimited_power_of_modules.txt · Last modified: 2014/08/02 06:29 (external edit)