Python Script To Import List of Trades into TradeStation’s EasyLanguage – Sort of

Converting A List of Trades, Dates and Prices Into EasyLanguage Arrays:

As the old saying goes “a picture is worth a thousand words!”  Have you ever been given a list of trades like this:

Sell Short,20010622,1178.50 
Buy to Cover,20010626,1159.75 
Sell Short,20010801,1150.00 
Buy to Cover,20010807,1139.75 
Sell Short,20010814,1129.00 
Buy to Cover,20010816,1117.25 
Sell Short,20011001,976.75 
Buy to Cover,20011004,1016.75 
Sell Short,20011107,1053.00 
Buy to Cover,20011123,1069.50 
Sell Short,20011219,1076.25 
Buy to Cover,20020102,1075.00 
Sell Short,20020129,1067.25 
Buy to Cover,20020131,1046.75 
Sell Short,20020131,1046.75 
Buy to Cover,20020205,1026.75 
Sell Short,20020520,1033.25 
Buy to Cover,20020522,1011.50 
Sell Short,20020731,832.00 
Buy to Cover,20020805,792.50 
Sell Short,20020812,834.00 
Buy to Cover,20020814,811.75 
Sell Short,20020911,838.50 
Buy to Cover,20020913,816.75 
List of Trades : Order, Date, Price

But really wanted to see this:

I have created a small Python script that will take a list of trades like those listed in table above and create the following EasyLanguage:

arrays: DateArr[500](0),TradeArr[500](""),PriceArr[500](0);
DateArr[0]=1010622;TradeArr[0]="SS";PriceArr[0]=1178.5;
DateArr[1]=1010626;TradeArr[1]="SX";PriceArr[1]=1159.75;
DateArr[2]=1010801;TradeArr[2]="SS";PriceArr[2]=1150.0;
DateArr[3]=1010807;TradeArr[3]="SX";PriceArr[3]=1139.75;
DateArr[4]=1010814;TradeArr[4]="SS";PriceArr[4]=1129.0;
DateArr[5]=1010816;TradeArr[5]="SX";PriceArr[5]=1117.25;
DateArr[6]=1011001;TradeArr[6]="SS";PriceArr[6]=976.75;
DateArr[7]=1011004;TradeArr[7]="SX";PriceArr[7]=1016.75;
DateArr[8]=1011107;TradeArr[8]="SS";PriceArr[8]=1053.0;
DateArr[9]=1011123;TradeArr[9]="SX";PriceArr[9]=1069.5;
DateArr[10]=1011219;TradeArr[10]="SS";PriceArr[10]=1076.25;
DateArr[11]=1020102;TradeArr[11]="SX";PriceArr[11]=1075.0;
DateArr[12]=1020129;TradeArr[12]="SS";PriceArr[12]=1067.25;
DateArr[13]=1020131;TradeArr[13]="SX";PriceArr[13]=1046.75;
DateArr[14]=1020131;TradeArr[14]="SS";PriceArr[14]=1046.75;
DateArr[15]=1020205;TradeArr[15]="SX";PriceArr[15]=1026.75;
DateArr[16]=1020520;TradeArr[16]="SS";PriceArr[16]=1033.25;
DateArr[17]=1020522;TradeArr[17]="SX";PriceArr[17]=1011.5;
Converting list of trades to EasyLanguage

This just creates the arrays that you can use to graph the trades on a chart.  If you are using exact prices you got to make sure your data aligns with the prices in the list of trades.  If you are only entering on the open or the close of the bar then the price array isn’t necessary.

The following Python script will also be helpful if you want to learn how to open a file in csv format, read it into lists, convert it and then save the output to a file.

#-------------------------------------------------------------------------------
# Name:        Read csv file via askOpen and save txt file via askSave
# Purpose:     Read the trade metrics from a TradeStation csv format
#              and build arrays from the information to display on charts in
#              TradeStation
# Author:      georg
#
# Created:     29/08/2018
# Copyright:   (c) georg 2018
#-------------------------------------------------------------------------------
import csv
import tkinter as tk
import os.path
from tkinter.filedialog import askopenfilenames
from tkinter.filedialog import asksaveasfilename

tradeType = list()
tradeDate = list()
tradePrice = list()

def main():
    root = tk.Tk()
    root.withdraw()
    files = askopenfilenames(filetypes=(('CSV files', '*.csv'),
                                       ('TXT files', '*.txt')),
                                       title='Select CSV format only!')
    fileList = root.tk.splitlist(files)
    fileListLen = len(fileList)


# make sure you know the format ahead of time
# I know "Buy",20180828,2745.75
#
    cnt = 0
    for files in range(0,fileListLen):
        head,tail = os.path.split(fileList[files])
        with open(fileList[files]) as f:
            f_csv = csv.reader(f)
            for row in f_csv:
                numCols = len(row)
                tradeType.append(row[0])
                tradeDate.append(int(row[1]))
                tradePrice.append(float(row[2]))
                cnt += 1
        f.close


    filename = asksaveasfilename(title="Will Save File with '.txt'",defaultextension=".txt")
#    filename = filename + '.txt'
    target1 = open(filename,'w')
    outString = 'arrays: DateArr[500](0),TradeArr[500](0),PriceArr[500](0);\n'
    target1.write(outString)
    for x in range(0,cnt):
        if tradeType[x] == "Sell Short": tradeType[x] = "SS"
        if tradeType[x] == "Buy": tradeType[x] = "B"
        if tradeType[x] == "Buy to Cover": tradeType[x] = "SX"
        if tradeType[x] == "Sell": tradeType[x] = "LX"
        outString = 'DateArr['+str(x)+']='+str(tradeDate[x]-19000000)+';TradeArr['+str(x)+']="'+tradeType[x]+'";PriceArr['+str(x)+']='+str(tradePrice[x])+';\n'
        target1.write(outString)
    target1.close


if __name__ == '__main__':
    main()
Python Script Open, Read, Convert and Write A File Using TK Dialogs

And here is the EasyLanguage code that will step through the arrays and place the trades accordingly.  I noticed that sometimes two trades could occur on the same bar, but only two and you will notice in the code where I programmed this occurrence.

vars: cnt(0);

If date of tomorrow = DateArr[cnt] then
Begin
	print("Inside: ",d," ",dateArr[cnt]);
	If tradeArr[cnt] = "B" then
	begin
		buy next bar at PriceArr[cnt] stop;
	end;
	If tradeArr[cnt] = "LX" then
	begin
		sell next bar at PriceArr[cnt] stop;
	end;
		If tradeArr[cnt] = "SS" then
	begin
		sellShort next bar at PriceArr[cnt] stop;
	end;
	If tradeArr[cnt] = "SX" then
	begin
		buyToCover next bar at PriceArr[cnt] stop;
	end;
	cnt = cnt + 1;
	If DateArr[cnt] = DateArr[cnt-1] then
	Begin
		print("two trades same day ",d," ",dateArr[cnt]);
		If tradeArr[cnt] = "B" then
		begin
			buy next bar at PriceArr[cnt] stop;
		end;
		If tradeArr[cnt] = "LX" then
		begin
			sell next bar at PriceArr[cnt] stop;
		end;
		If tradeArr[cnt] = "SS" then
		begin
	    	print("looking to go short at ",PriceArr[cnt]);
			sellShort next bar at PriceArr[cnt] stop;
		end;
		If tradeArr[cnt] = "SX" then
		begin
			buyToCover next bar at PriceArr[cnt] stop;
		end;
		cnt = cnt + 1;
	end;	
end;
EasyLanguage Snippet To Execute Trades Stored in Arrays

 

 

Using TradeStation’s COT Indicator to Develop a Trading System

TradeStation’s COT (Commitment of Traders) Indicator:

TradeStation COT Indicator

TradeStation now includes the historic COT (Commitment of Traders) report in the form of an indicator.

If you can plot it then you can use it in a Strategy.  The following code listing takes the Indicator code and with very few modifications turns it into a trading system.

{
Net positions of various groups of traders from the CFTC's weekly Commitments of
Traders report.  "Net" positions are calculated by taking the number of contracts
that a group of traders is long and subtracting the number of contracts that that
group of traders is short.

The user input "FuturesOnly_Or_FuturesAndOptions_1_or_2" determines whether the
CFTC's "Futures Only" report is used, or the "Futures and Options" report is
used to determine the positions of the various groups of traders.  By default, the
"Futures Only" report is used.

Plot1:  Commercial traders' net position
Plot2:  Non-commercial traders' net position
Plot3:  Speculators' net positions, for speculators not of reportable size
Plot4:  Zero line

If an error occurs retrieving one of the values used by this study, or if the value
is not applicable or non-meaningful, a blank cell will be displayed in RadarScreen or
in the OptionStation assets pane.  In a chart, no value will be plotted until a value
is obtained without generating an error when retrieved.
}

input:  FuturesOnly_Or_FuturesAndOptions_1_or_2( 1 ) ; { set to 1 to use the CFTC's
 "Futures Only" report, set to 2 (or to any value other than 1) to use the "Futures
 and Options" report }

variables:
	Initialized( false ),
	FieldNamePrefix( "" ),
	CommLongFieldNme( "" ),
	CommShortFieldNme( "" ),
	NonCommLongFieldNme( "" ),
	NonCommShortFieldNme( "" ),
	SpecLongFieldNme( "" ),
 	SpecShortFieldNme( "" ),
    CommLong( 0 ),
	oCommLongErr( 0 ),
	CommShort( 0 ),
	oCommShortErr( 0 ),
	NonCommLong( 0 ),
	oNonCommLongErr( 0 ),
	NonCommShort( 0 ),
	oNonCommShortErr( 0 ),
	SpecLong( 0 ),
	oSpecLongErr( 0 ),
	SpecShort( 0 ),
	oSpecShortErr( 0 ),
	CommNet( 0 ),
	NonCommNet( 0 ),
	SpecNet( 0 ) ;

if Initialized = false then
	begin
	if Category > 0 then
		RaiseRuntimeError( "Commitments of Traders studies can be applied only to" +
		 " futures symbols." ) ;
	Initialized = true ;
	FieldNamePrefix = IffString( FuturesOnly_Or_FuturesAndOptions_1_or_2 = 1,
	 "COTF-", "COTC-" ) ;
	CommLongFieldNme = FieldNamePrefix + "12" ;
	CommShortFieldNme = FieldNamePrefix + "13" ;
	NonCommLongFieldNme = FieldNamePrefix + "9" ;
	NonCommShortFieldNme = FieldNamePrefix + "10" ;
	SpecLongFieldNme = FieldNamePrefix + "16" ;
 	SpecShortFieldNme = FieldNamePrefix + "17" ;	
	end ;

CommLong = FundValue( CommLongFieldNme, 0, oCommLongErr ) ;
CommShort = FundValue( CommShortFieldNme, 0, oCommShortErr) ;
NonCommLong = FundValue( NonCommLongFieldNme, 0, oNonCommLongErr ) ;
NonCommShort = FundValue( NonCommShortFieldNme, 0, oNonCommShortErr );
SpecLong = FundValue( SpecLongFieldNme, 0, oSpecLongErr ) ; 
SpecShort = FundValue( SpecShortFieldNme, 0, oSpecShortErr ) ;

if oCommLongErr = fdrOk and oCommShortErr = fdrOk then
	begin
	CommNet = CommLong - CommShort ;
	Print ("CommNet ",commNet);
	end ;

if oNonCommLongErr = fdrOk and oNonCommShortErr = fdrOk then
	begin
	NonCommNet = NonCommLong - NonCommShort ;
	end ;

if oSpecLongErr = fdrOk and oSpecShortErr = fdrOk then
	begin
	SpecNet = SpecLong - SpecShort ;
	end ;
If CommNet < 0  then sellShort tomorrow at open;
If CommNet > 0 then buy tomorrow at open;


{ ** Copyright (c) 2001 - 2010 TradeStation Technologies, Inc. All rights reserved. ** 
  ** TradeStation reserves the right to modify or overwrite this analysis technique 
     with each release. ** }
COT Indicator Converted To Strategy

Line numbers 90 and 91 informs TS to take a long position if the Net Commercial Interests are positive and a short position if the Commercials are negative.  I kept the original comments in place in  case you wanted to see how the indicator and its associated function calls work.  The linchpin of this code lies in the function call FundValue.  This function call pulls fundamental data from the data servers and provides it in an easy to use format.  Once you have the data you can play all sorts of games with it.  This is just a simple system to see if the commercial traders really do know which direction the market is heading.

if you test this strategy on the ES you will notice a downward sloping 45 degree equity curve.  This leads me to believe the commercials are trying their best to  use the ES futures to hedge other market positions.  If you go with the non Commercials you will see  a totally different picture.  To do this just substitute the following two lines:

If CommNet < 0 then sellShort tomorrow at open;
If CommNet > 0 then buy tomorrow at open;

With:

If NonCommNet < 0 then sellShort tomorrow at open;
If NonCommNet > 0 then buy tomorrow at open;

I said a totally different picture not a great one.  Check out if the speculators know better.