def setupForTheTradeObject(self, getMax=False, infile="trades.8.csv"):
        '''Set up the DataFrames'''
        jf = JournalFiles(mydevel=True,
                          infile=infile,
                          indir="data/",
                          outdir="out/")

        tkt = Statement_DAS(jf)
        trades, jf = tkt.getTrades()

        idf = InputDataFrame()
        trades, success = idf.processInputFile(trades)

        tu = DefineTrades()
        (dummy_len, dummy_df, ldf) = tu.processOutputDframe(trades)
        srf = SumReqFields()
        maxlen = 0
        maxindex = -1  #The index that yieds the maximumbal from ldf[i]
        for i in range(len(ldf)):
            if len(ldf[i]) > maxlen:
                maxlen = len(ldf[i])
                maxindex = i
        index = randint(0, len(ldf) - 1)
        if getMax:
            index = maxindex
        self.atrade = ldf[index]
        self.tto = TheTradeObject(self.atrade, True, srf)
        return self.tto
Example #2
0
    def test_addTradeDuration(self):
        '''
        Test the method DefineTrades.addStartTime. Send some randomly generated trades excluding
        the start field and then test the results for the start field. Specifically 
        Test that Duration val is placed only when the trade has 0 Shares
        Test that the the original is the same dur as that created by addTradeDuration
        Test Duration is difference from each Last Trade - Start val
        '''
        NUMTRADES = 4
        trades = list()
        start = pd.Timestamp('2018-06-06 09:30:00')
        df = pd.DataFrame()
        exclude = []
        for i in range(NUMTRADES):
            tdf, start = randomTradeGenerator2(i + 1,
                                               earliest=start,
                                               pdbool=True,
                                               exclude=exclude)
            df = df.append(tdf)
            exclude.append(tdf.Symb.unique()[0])

        df.reset_index(drop=True, inplace=True)

        frc = FinReqCol()
        df2 = df.copy()
        df2[frc.dur] = None
        df3 = df2.copy()

        df3 = df3.sort_values(['Symb', 'Account', 'Time'])
        dtrades = DefineTrades()
        df3 = dtrades.addTradeDuration(df3)

        for i in range(NUMTRADES):
            tnum = 'Trade ' + str(i + 1)
            tdf = df3[df3.Tindex == tnum]
            tdf_gen = df[df.Tindex == tnum]
            xl = tdf.index[-1]
            xl_gen = tdf_gen.index[-1]

            assert len(tdf.Tindex.unique()) == 1

            for i, row in tdf.iterrows():
                if row.Balance:
                    assert not row.Duration
                else:
                    if not row.Duration:
                        assert len(tdf) == 2
                        assert tdf.loc[tdf.index[0]].Side.startswith('HOLD')
                    # assert row.Duration
                    diff = row.Time - row.Start
                    assert diff == row.Duration
                    assert row.Duration == tdf_gen.loc[xl_gen].Duration
Example #3
0
    def test_addTradePL(self):
        '''
        Test the method DefineTrades.addTradePL. Create random trade and remove the sum val
        
        Call addtradePL and compare the origianl generation with the new one. 
        Specifically Test that Sum val is placed only when the trade has 0 Shares
        Test that the the original is the same PL as that created by addTradeDuration
        Test Sum is sum or the PL values from the trade.
        '''
        NUMTRADES = 4
        trades = list()
        start = pd.Timestamp('2018-06-06 09:30:00')
        df = pd.DataFrame()
        exclude = []
        for i in range(4):
            tdf, start = randomTradeGenerator2(i + 1,
                                               earliest=start,
                                               pdbool=True,
                                               exclude=exclude)
            df = df.append(tdf)
            exclude.append(tdf.Symb.unique()[0])

        df.reset_index(drop=True, inplace=True)

        frc = FinReqCol()
        df2 = df.copy()

        df2[frc.sum] = None

        df3 = df2.copy()

        df3 = df3.sort_values(['Symb', 'Account', 'Time'])
        dtrades = DefineTrades()
        df3 = dtrades.addTradePL(df3)

        for i in range(NUMTRADES):
            tnum = 'Trade ' + str(i + 1)
            tdf = df3[df3.Tindex == tnum]
            tdf_gen = df[df.Tindex == tnum]

            for i, row in tdf.iterrows():
                if row.Balance:
                    assert not row.Sum
                else:

                    assert isclose(tdf['P / L'].sum(), row.Sum, abs_tol=1e-7)
                    assert isclose(row.Sum,
                                   tdf_gen.loc[tdf_gen.index[-1]].Sum,
                                   abs_tol=1e-7)
Example #4
0
    def test_addFinReqCol(self):
        '''
        Test the method journal.definetrades.TestDefineTrades.addFinReqCol
        '''
        rc = ReqCol()
        frc = FinReqCol()

        df = pd.DataFrame(np.random.randint(0,
                                            1000,
                                            size=(10, len(rc.columns))),
                          columns=rc.columns)
        dtrades = DefineTrades()
        df = dtrades.addFinReqCol(df)
        for x in frc.columns:
            self.assertIn(x, df.columns)
        self.assertGreaterEqual(len(df.columns), len(frc.columns))
Example #5
0
    def test_addSummaryPL(self):
        '''
        Test the method DefineTrades.addStartTime. Send some randomly generated trades excluding
        the start field and then test the results for the start field.
        '''
        NUMTRADES = 4
        trades = list()
        start = pd.Timestamp('2018-06-06 09:30:00')
        df = pd.DataFrame()
        exclude = []
        for i in range(4):
            tdf, start = randomTradeGenerator2(i + 1,
                                               earliest=start,
                                               pdbool=True,
                                               exclude=exclude)
            df = df.append(tdf)
            exclude.append(tdf.Symb.unique()[0])

        df.reset_index(drop=True, inplace=True)

        frc = FinReqCol()
        df2 = df.copy()

        df2[frc.sum] = None

        df3 = df2.copy()

        df3 = df3.sort_values(['Symb', 'Account', 'Time'])
        dtrades = DefineTrades()
        df3 = dtrades.addTradePL(df3)

        for i in range(NUMTRADES):
            tnum = 'Trade ' + str(i + 1)
            tdf = df3[df3.Tindex == tnum]
            tdf_gen = df[df.Tindex == tnum]

            for i, row in tdf.iterrows():
                if row.Balance:
                    assert not row.Sum
                else:

                    assert isclose(tdf['P / L'].sum(), row.Sum, abs_tol=1e-7)
                    assert isclose(row.Sum,
                                   tdf_gen.loc[tdf_gen.index[-1]].Sum,
                                   abs_tol=1e-7)
Example #6
0
    def test_addStartTime(self):
        '''
        Test the method DefineTrades.addStartTime. Send some randomly generated trades excluding
        the start field and then test the results for the start field.
        '''
        NUMTRADES = 4
        trades = list()
        start = pd.Timestamp('2019-01-01 09:30:00')
        exclude = []
        for i in range(4):
            t, start = randomTradeGenerator2(i + 1,
                                             earliest=start,
                                             exclude=exclude)
            trades.extend(t)
            # print(t[0][3])
            exclude.append(t[0][3])

        frc = FinReqCol()
        df = pd.DataFrame(data=trades,
                          columns=[
                              frc.tix, frc.start, frc.time, frc.ticker,
                              frc.side, frc.shares, frc.bal, frc.acct, frc.PL,
                              frc.sum, frc.dur
                          ])
        df2 = df.copy()
        df2[frc.start] = None

        dtrades = DefineTrades()
        df3 = df2.copy()
        df3.sort_values(['Symb', 'Account', 'Time'], inplace=True)
        df3 = dtrades.addStartTime(df3)
        for i in range(len(df3)):
            # Tests that addtradeIndex recreated the same index locations that rtg did after sorting the trades
            if df3.loc[i][frc.start] != df.loc[i][frc.start]:
                print('Found and error at index', i)
                print(df3.loc[i][frc.start], df.loc[i][frc.start])
            self.assertEqual(df3.loc[i][frc.start], df.loc[i][frc.start])
        for i in range(NUMTRADES):
            # Test all trades have a single start time
            tradeNum = 'Trade ' + str(i + 1)
            tdf = df3[df3.Tindex == tradeNum].copy()
            self.assertEqual(len(tdf.Start.unique()), 1)
Example #7
0
    def test_writeShareBalance(self):
        '''
        Test the method writeShareBalance. Send some randomly generated trades. Remove a bunch of
        columns and call writeShareBalance. Test that the share balance was recreated correctly
        test the share balance that returns. Sort both and compare the results using the place
        index iloc
        '''
        NUMTRADES = 4
        trades = list()
        start = pd.Timestamp('2018-06-06 09:30:00')
        df = pd.DataFrame()
        exclude = []
        for i in range(NUMTRADES):
            tdf, start = randomTradeGenerator2(i + 1,
                                               earliest=start,
                                               pdbool=True,
                                               exclude=exclude)
            df = df.append(tdf)
            exclude.append(tdf.Symb.unique()[0])

        df.reset_index(drop=True, inplace=True)

        frc = FinReqCol()
        df2 = df.copy()

        df2[frc.sum] = None
        df2[frc.start] = None
        df2[frc.tix] = None
        df2[frc.PL] = None
        df2[frc.dur] = None
        df2[frc.bal] = 0

        df3 = df2.copy()
        df3 = df3.sort_values(['Symb', 'Account', 'Time'])
        df3.reset_index(drop=True, inplace=True)
        df = df.sort_values(['Symb', 'Account', 'Time'])

        dtrades = DefineTrades()
        df3 = dtrades.writeShareBalance(df3)
        for i in range(len(df3)):
            assert df3.iloc[i][frc.bal] == df.iloc[i][frc.bal]
Example #8
0
    def runnit(self):
        print('gonna runnit gonna runnit')
        self.initialize()
        if not self.indir:
            print('What file is supposed to load?')
            return
        jf = JournalFiles(indir=self.indir, outdir=self.outdir,
                      theDate=self.theDate, infile=self.infile,
                      inputType = self.inputtype, infile2=self.positions,
                      mydevel=True)

        if self.inputtype == 'IB_HTML':
            jf.inputType = 'IB_HTML'
            statement = Statement_IBActivity(jf)
            df = statement.getTrades_IBActivity(jf.inpathfile)
        elif  self.inputtype == 'DAS':
            tkt = Ticket(jf)
            df, jf = tkt.getTrades()
        # trades = pd.read_csv(jf.inpathfile)
        else:
            #Temporary
            print('Opening a non standard file name in DAS')
            tkt = Ticket(jf)
            df, jf = tkt.getTrades()

        idf = InputDataFrame()
        trades,  success = idf.processInputFile(df, jf.theDate, jf)
        if not success:
            return

        tu = DefineTrades(self.inputtype)
        inputlen, dframe, ldf = tu.processOutputDframe(trades)

        # Process the openpyxl excel object using the output file DataFrame. Insert
        # images and Trade Summaries.
        margin = 25

        lf = LayoutForms(self.sc, jf, dframe)
        tradeSummaries = lf.runSummaries(ldf)
Example #9
0
    def test_createImageLocation(self, unusedstub):
        '''Run structjour'''
        #Assert the initial entry location in imageLocation is figured by these factors
         # Assert all entries are figured by summarySize and len of the minittrade
        # Assert the minitable locations are offset by length of the minitrade tables +
                # ls.spacing, and the first entry in the Leftmost column starts with 'Trade'
                 # Assert third entry of imageLocation begins with 'Trade' and contains
                #       ['Long', 'Short']
                # Assert the 4th entry is a timestamp
                # Assert the 5th entry is a time delta
        global D


        for tdata, infile in zip(self.dadata, self.infiles):
            # :::::::::  Setup   ::::::::
            D = deque(tdata)
            # infile = 'trades.8.csv'
            print(infile)
            indir = 'data/'
            mydevel = False
            jf = JournalFiles(indir=indir, infile=infile, mydevel=mydevel)

            trades, jf = Statement_DAS(jf).getTrades()
            trades, success = InputDataFrame().processInputFile(trades)
            inputlen, dframe, ldf = DefineTrades().processOutputDframe(trades)
            # ::::::::::: end setup :::::::::::::

            margin = 25
            spacing = 3
            ls = LayoutSheet(margin, inputlen, spacing=spacing)
            imageLocation, dframe = ls.imageData(dframe, ldf)


            for count, t in enumerate(imageLocation):
                if count == 0:
                    initialEntry = ls.inputlen + ls.topMargin + ls.spacing + len(ldf[0]) + 2
                    self.assertEqual(t[0], initialEntry)

                else:
                    nextloc = imageLocation[count-1][0] + len(ldf[count]) + ls.summarySize
                    self.assertEqual(t[0], nextloc)

                t_entry = t[0] - (spacing + len(ldf[count]))
                self.assertTrue(dframe.iloc[t_entry][0].startswith('Trade'))
                self.assertEqual(len(dframe.iloc[t_entry-1][0]), 0)
                self.assertTrue(t[2].startswith('Trade'))
                self.assertTrue(t[2].find('Long') > 0 or t[2].find('Short') > 0)
                self.assertTrue(isinstance(pd.Timestamp('2019-11-11 ' + t[3]), dt.datetime))
                self.assertTrue(isinstance(t[4], dt.timedelta))
Example #10
0
    def test_runSummaries(self, unusedstub1, unusedstub2, unusedstub3):
        '''
        Test the method prunSummaries. The setup here is alost the entire module trade.py
        We run the standard set of infiles
        '''

        # global D
        # infiles = ['trades.1116_messedUpTradeSummary10.csv', 'trades.8.WithHolds.csv',
        #         'trades.8.csv', 'trades.907.WithChangingHolds.csv',
        #         'trades_190117_HoldError.csv', 'trades.8.ExcelEdited.csv',
        #         'trades.910.tickets.csv', 'trades_tuesday_1121_DivBy0_bug.csv',
        #         'trades.8.WithBothHolds.csv', 'trades1105HoldShortEnd.csv',
        #         'trades190221.BHoldPreExit.csv']

        global D
        for tdata, infile in zip(self.dadata, self.infiles):
            # :::::::::  Setup   ::::::::

            D = deque(tdata)
            # :::::::::::::: SETUP ::::::::::::::
            # theDate = '2018-11-05'
            outdir = 'out/'
            indir = 'C:/python/E/structjour/src/data/'
            mydevel = False
            jf = JournalFiles(infile=infile, outdir=outdir, indir=indir, mydevel=mydevel)


            trades, jf = Statement_DAS(jf).getTrades()
            trades, success = InputDataFrame().processInputFile(trades)
            inputlen, dframe, ldf = DefineTrades().processOutputDframe(trades)

            # Process the openpyxl excel object using the output file DataFrame. Insert
            # images and Trade Summaries.
            margin = 25

            # Create the space in dframe to add the summary information for each trade.
            # Then create the Workbook.
            ls = LayoutSheet(margin, inputlen)
            imageLocation, dframe = ls.imageData(dframe, ldf)
            wb, ws, dummy = ls.createWorkbook(dframe)

            tf = TradeFormat(wb)

            mstkAnchor = (len(dframe.columns) + 2, 1)
            mistake = MistakeSummary(numTrades=len(ldf), anchor=mstkAnchor)
            mistake.mstkSumStyle(ws, tf, mstkAnchor)

            # :::::::::::::: END SETUP ::::::::::::::
            tradeSummaries = ls.runSummaries(imageLocation, ldf, jf, ws, tf)

            # Make sure the out dir exists
            if not os.path.exists("out/"):
                os.mkdir("out/")

            # Make sure the file we are about to create does not exist
            dispath = "out/SCHNOrK.xlsx"
            if os.path.exists(dispath):
                os.remove(dispath)
            wb.save(dispath)

            wb2 = load_workbook(dispath)
            ws2 = wb2.active


            srf = SumReqFields()
            for trade, loc in zip(tradeSummaries, imageLocation):
                anchor = (1, loc[0])
                # print(anchor)
                for col in trade:
                    if col in['clean']:
                        continue

                    # Get the cell
                    if isinstance(srf.tfcolumns[col][0], list):
                        cell = tcell(srf.tfcolumns[col][0][0], anchor=anchor)
                    else:
                        cell = tcell(srf.tfcolumns[col][0], anchor=anchor)

                    # Nicer to read
                    wsval = ws2[cell].value
                    tval = trade[col].unique()[0]

                    # Test Formulas (mostly skipping for now because its gnarly)
                    # Formulas in srf.tfformulas including the translation stuff

                    if col in srf.tfformulas.keys():
                        self.assertTrue(wsval.startswith('='))

                    # Test empty cells
                    elif not tval:
                        # print(wsval, '<------->', tval)
                        self.assertIs(wsval, None)

                    # Test floats
                    elif isinstance(tval, float):
                        # print(wsval, '<------->', tval)
                        self.assertAlmostEqual(wsval, tval)

                    # Time vals
                    elif isinstance(tval, (pd.Timestamp, dt.datetime, np.datetime64)):
                        wsval = pd.Timestamp(wsval)
                        tval = pd.Timestamp(tval)
                        self.assertGreaterEqual((wsval-tval).total_seconds(), -.01)
                        self.assertLessEqual((wsval-tval).total_seconds(), .01)


                    # Test everything else
                    else:
                        # print(wsval, '<------->', tval)
                        self.assertEqual(wsval, tval)
Example #11
0
    def test_populateDailySummaryForm(self, unusedstub1, unusedstub2, unusedstub3):
        '''
        Test the method populateMistakeForm. The setup here is alost the entire module trade.py
        The tested method puts in the trade PL and notes
        '''

        global D


        for tdata, infile in zip(self.dadata, self.infiles):
            # :::::::::  Setup   ::::::::
            D = deque(tdata)
            # :::::::::::::: SETUP ::::::::::::::
            # theDate = '2018-11-05'
            outdir = 'out/'
            indir = 'data/'
            mydevel = False
            jf = JournalFiles(infile=infile, outdir=outdir, indir=indir, mydevel=mydevel)
            print(jf.inpathfile)

            trades, jf = Statement_DAS(jf).getTrades()
            trades, success = InputDataFrame().processInputFile(trades)
            inputlen, dframe, ldf = DefineTrades().processOutputDframe(trades)

            # Process the openpyxl excel object using the output file DataFrame. Insert
            # images and Trade Summaries.
            margin = 25

            # Create the space in dframe to add the summary information for each trade.
            # Then create the Workbook.
            ls = LayoutSheet(margin, inputlen)
            imageLocation, dframe = ls.imageData(dframe, ldf)
            wb, ws, dummy = ls.createWorkbook(dframe)

            tf = TradeFormat(wb)

            mstkAnchor = (len(dframe.columns) + 2, 1)
            mistake = MistakeSummary(numTrades=len(ldf), anchor=mstkAnchor)
            # mistake.mstkSumStyle(ws, tf, mstkAnchor)
            mistake.dailySumStyle(ws, tf, mstkAnchor)
            tradeSummaries = ls.runSummaries(imageLocation, ldf, jf, ws, tf)

            # :::::::::::::: END SETUP ::::::::::::::
            # ls.populateMistakeForm(tradeSummaries, mistake, ws, imageLocation)
            ls.populateDailySummaryForm(tradeSummaries, mistake, ws, mstkAnchor)

            # Make sure the out dir exists
            if not os.path.exists("out/"):
                os.mkdir("out/")

            # Make sure the file we are about to create does not exist
            dispath = "out/SCHNOrK.xlsx"
            if os.path.exists(dispath):
                os.remove(dispath)

            wb.save(dispath)
            # print(infile, 'saved as', dispath)

            wb2 = load_workbook(dispath)
            ws2 = wb2.active

            # Live Total
            frc = FinReqCol()
            livetot = 0
            simtot = 0
            highest = 0
            lowest = 0
            numwins = 0
            numlosses = 0
            totwins = 0
            totloss = 0

            for trade in tradeSummaries:
                acct = trade[frc.acct].unique()[0]
                pl = trade[frc.PL].unique()[0]
                highest = pl if pl > highest else highest
                lowest = pl if pl < lowest else lowest
                if pl > 0:
                    numwins += 1
                    totwins += pl
                # Trades == 0 are figured in the loss column-- comissions and all
                else:
                    numlosses += 1
                    totloss += pl


                if acct == 'Live':
                    livetot += pl
                elif acct == 'SIM':
                    simtot += pl

            # print(livetot)
            # livetotcell = tcell(mistake.dailySummaryFields['livetot'][0], anchor=ls.DSFAnchor)
            # print(simtot)

            avgwin = 0 if numwins == 0 else totwins/numwins
            avgloss = 0 if numlosses == 0 else totloss/numlosses

            data = [['livetot', livetot], ['simtot', simtot], ['highest', highest],
                    ['lowest', lowest], ['avgwin', avgwin], ['avgloss', avgloss]]

            for s, d in data:
                cell = tcell(mistake.dailySummaryFields[s][0], anchor=ls.DSFAnchor)
                # msg = '{} {} {}'.format(s, d, ws2[cell].value)
                # print(msg)
                self.assertAlmostEqual(d, ws2[cell].value)  #, abs_tol=1e-7)


            data = ['livetotnote', 'simtotnote', 'highestnote', 'lowestnote',
                    'avgwinnote', 'avglossnote']
            for s in data:
                cell = tcell(mistake.dailySummaryFields[s][0][0], anchor=ls.DSFAnchor)
                val = ws2[cell].value
                self.assertIsInstance(val, str)

                self.assertGreater(len(val), 1)
Example #12
0
    def test_populateMistakeForm(self, unusedstub1, unusedstub2, unusedstub3):
        '''
        Test the method populateMistakeForm. The setup here is alost the entire module trade.py
        '''

        global D
        for tdata, infile in zip(self.dadata, self.infiles):
            # :::::::::  Setup   ::::::::
            D = deque(tdata)
            # :::::::::::::: SETUP ::::::::::::::
            # theDate = '2018-11-05'
            outdir = 'out/'
            indir = 'data/'
            mydevel = False
            jf = JournalFiles(infile=infile, outdir=outdir, indir=indir, mydevel=mydevel)

            trades, jf = Statement_DAS(jf).getTrades()
            trades, success = InputDataFrame().processInputFile(trades)
            inputlen, dframe, ldf = DefineTrades().processOutputDframe(trades)

            # Process the openpyxl excel object using the output file DataFrame. Insert
            # images and Trade Summaries.
            margin = 25

            # Create the space in dframe to add the summary information for each trade.
            # Then create the Workbook.
            ls = LayoutSheet(margin, inputlen)
            imageLocation, dframe = ls.imageData(dframe, ldf)
            wb, ws, dummy = ls.createWorkbook(dframe)

            tf = TradeFormat(wb)

            mstkAnchor = (len(dframe.columns) + 2, 1)
            mistake = MistakeSummary(numTrades=len(ldf), anchor=mstkAnchor)
            mistake.mstkSumStyle(ws, tf, mstkAnchor)

            tradeSummaries = ls.runSummaries(imageLocation, ldf, jf, ws, tf)

            # :::::::::::::: END SETUP ::::::::::::::
            ls.populateMistakeForm(tradeSummaries, mistake, ws, imageLocation)

            # Make sure the out dir exists
            if not os.path.exists("out/"):
                os.mkdir("out/")

            # Make sure the file we are about to create does not exist
            dispath = "out/SCHNOrK.xlsx"
            if os.path.exists(dispath):
                os.remove(dispath)
            wb.save(dispath)

            wb2 = load_workbook(dispath)
            ws2 = wb2.active

            frc = FinReqCol()

            # ragged iteration over mistakeFields and tradeSummaries.
            count = 0   # ragged iterator for tradeSummaries
            for key in mistake.mistakeFields:

                entry = mistake.mistakeFields[key]
                cell = entry[0][0] if isinstance(entry[0], list) else entry[0]
                cell = tcell(cell, anchor=mistake.anchor)
                if key.startswith('name'):
                    # Get the hyperlink target in mistakeform , parse the target and verify the
                    # hyperlinks point to each other
                    tsName = tradeSummaries[count][frc.name].unique()[0]
                    tsAcct = tradeSummaries[count][frc.acct].unique()[0]
                    targetcell = ws2[cell].hyperlink.target.split('!')[1]
                    originalcell = ws2[targetcell].hyperlink.target.split('!')[1]

                    # print(ws2[cell].value, '<--------', tsumName)
                    # print(ws2[cell].value, '<-------', tsumAccount)
                    # print(cell, '<------->', originalcell)
                    self.assertGreater(ws2[cell].value.find(tsName), -1)
                    self.assertGreater(ws2[cell].value.find(tsAcct), -1)
                    self.assertEqual(cell, originalcell)
                    count = count + 1


            # ::::::: tpl fields :::::::
            count = 0
            for key in mistake.mistakeFields:

                entry = mistake.mistakeFields[key]
                cell = entry[0][0] if isinstance(entry[0], list) else entry[0]
                cell = tcell(cell, anchor=mistake.anchor)
                if key.startswith('tpl'):
                    targetcell = ws2[cell].value[1:]
                    origval = tradeSummaries[count][frc.PL].unique()[0]
                    # print(ws2[targetcell].value, '<------->', origval )
                    if origval == 0:
                        self.assertIs(ws2[targetcell].value, None)
                    else:
                        self.assertAlmostEqual(ws2[targetcell].value, origval)
                    count = count + 1

                # These next two tests (for plx and mistakex) have no unique entries (without user
                # input or mock) Test for the static values and that plx entry is next to its header
                if key.startswith('pl'):
                    headval = 'Proceeds Lost'
                    targetcell = ws2[cell].value[1:]
                    headercell = 'A' + targetcell[1:]
                    # print(ws2[targetcell].value, '<------->', None)
                    # print(headercell, '------->', ws2[headercell].value)
                    self.assertTrue(ws2[targetcell].value is None)
                    self.assertEqual(ws2[headercell].value, headval)

                if key.startswith('mistake'):
                    noteval = 'Final note'
                    targetcell = ws2[cell].value[1:]
                    # print(ws2[targetcell].value, '<------->', noteval)
                    self.assertEqual(ws2[targetcell].value, noteval)
Example #13
0
def run(infile='trades.csv',
        outdir=None,
        theDate=None,
        indir=None,
        infile2=None,
        mydevel=True):
    '''
    Run structjour. Temporary picker for input type based on filename. If infile has 'activity' in
    it and ends in .html, then its IB Activity Statement web page (as a file on this system)
    :params infile: Name of the input file. Default trades.csv--a DAS export from the trades window.
                    If infile contains the string 'trades', input type is set to DAS.
                    If infile contains the string 'activity', input type is set to IB Activity.
                    Default will try DAS
    :params outdir: Location to write the output file.
    :params theDate: The date of this input file. If trades lack a Date, this date be the trade date.
    :params indir: Location of the input file.
    :parmas infile2: Name of the DAS positions file. Will default to indir/positions.csv  
    :params mydevel: If True, use a specific file structure and let structjour create it. All can 
                     be overriden by using the specific parameters above.
    '''
    settings = QSettings('zero_substance', 'structjour')
    settings.setValue('runType', 'CONSOLE')
    #  indir=None, outdir=None, theDate=None, infile='trades.csv', mydevel=False
    jf = JournalFiles(indir=indir,
                      outdir=outdir,
                      theDate=theDate,
                      infile=infile,
                      infile2=infile2,
                      mydevel=mydevel)

    name, ext = os.path.splitext(jf.infile.lower())
    if name.find('activity') > -1 and ext == '.html':
        jf.inputType = 'IB_HTML'
        statement = Statement_IBActivity(jf)
        df = statement.getTrades_IBActivity(jf.inpathfile)
    elif name.find('trades') > -1 and ext == '.csv':
        # This could be an IB CSV--so this is temporary-- when I enable some sort of IB CSV, will
        # probably do some kind of class heirarchy here for statements.
        tkt = Ticket(jf)
        df, jf = tkt.getTrades()
    # trades = pd.read_csv(jf.inpathfile)
    else:
        #Temporary
        print('Opening a non standard file name in DAS')
        tkt = Ticket(jf)
        df, jf = tkt.getTrades()

    idf = InputDataFrame()
    trades, success = idf.processInputFile(df, jf.theDate, jf)
    if not success:
        print('Failed. Between you and me, I think its a programming error')
        return jf

    tu = DefineTrades()
    inputlen, dframe, ldf = tu.processOutputDframe(trades)

    # Process the openpyxl excel object using the output file DataFrame. Insert
    # images and Trade Summaries.
    margin = 25

    # Create the space in dframe to add the summary information for each trade.
    # Then create the Workbook.
    ls = LayoutSheet(margin, inputlen)
    imageLocation, dframe = ls.imageData(dframe, ldf)
    wb, ws, nt = ls.createWorkbook(dframe)

    tf = TradeFormat(wb)
    ls.styleTop(ws, len(nt.columns), tf)
    assert len(ldf) == len(imageLocation)

    mstkAnchor = (len(dframe.columns) + 2, 1)
    mistake = MistakeSummary(numTrades=len(ldf), anchor=mstkAnchor)
    mistake.mstkSumStyle(ws, tf, mstkAnchor)
    mistake.dailySumStyle(ws, tf, mstkAnchor)

    tradeSummaries = ls.runSummaries(imageLocation, ldf, jf, ws, tf)
    # app = QApplication(sys.argv)
    # qtf = QtForm()
    # qtf.fillForm(tradeSummaries[1])
    # app.exec_()

    ls.populateMistakeForm(tradeSummaries, mistake, ws, imageLocation)
    ls.populateDailySummaryForm(tradeSummaries, mistake, ws, mstkAnchor)

    ls.save(wb, jf)
    print("Processing complete. Saved {}".format(jf.outpathfile))
    return jf
Example #14
0
    def test_addTradeIndex(self):
        '''
        Test addTradeIndex
        '''
        NUMRUNS = 10
        NUMTRADES = 10  # Number of trades to aggregate into single statement
        for i in range(NUMRUNS):
            # if not i % 20:
            #     print(f'{i}/{NUMRUNS} ', end='')
            earliest = pd.Timestamp('2018-06-06 09:30:00')
            delt = pd.Timedelta(minutes=1)
            df = pd.DataFrame()
            exclude = []
            for j in range(NUMTRADES):
                tdf, earliest = randomTradeGenerator2(j + 1,
                                                      earliest=earliest,
                                                      pdbool=True,
                                                      exclude=exclude)
                exclude.append(tdf.iloc[0].Symb)
                df = df.append(tdf)
                earliest = earliest + delt

                df.reset_index(drop=True, inplace=True)
                df = df.sort_values(['Symb', 'Account', 'Time'])
            frc = FinReqCol()
            df2 = df.copy()
            df2[frc.tix] = ''
            df2.sort_values(['Symb', 'Account', 'Time'], inplace=True)

            dtrades = DefineTrades()
            ddf = dtrades.addTradeIndex(df2)

            for k in range(4):
                tnum = 'Trade ' + str(k + 1)
                tdf = ddf[ddf.Tindex == tnum].copy()
                xl = tdf.index[-1]
                lastd = None
                thisd = None
                for j, row in tdf.iterrows():
                    if j != xl:
                        if tdf.at[j, 'Balance'] == 0:
                            print('Found an error at index', j,
                                  'The Balance should not be 0')
                            print(tdf[[
                                'Symb', 'Tindex', 'Account', 'Time', 'Side',
                                'Qty', 'Balance'
                            ]])
                        self.assertNotEqual(tdf.at[j, 'Balance'], 0)
                    else:
                        if tdf.at[j, 'Balance'] != 0:
                            print('Found an error at index', xl,
                                  'The balance should be 0')
                            print(df[[
                                'Symb', 'Tindex', 'Account', 'Time', 'Side',
                                'Qty', 'Balance'
                            ]])
                        self.assertEqual(tdf.at[j, 'Balance'], 0)
                    if lastd:
                        if lastd > thisd:
                            print('Found an error in the Time sequencing of',
                                  tnum)
                            print(thisd, ' > ', lastd, ' = ', thisd > lastd)
                            print(df[[
                                'Symb', 'Tindex', 'Account', 'Time', 'Side',
                                'Qty', 'Balance'
                            ]])
                            self.assertGreater(thisd, lastd)