Example #1
0
class dr3080(object):
    def __init__(self, **opts):
        self.opts = opts
        if self.setVariables():
            self.mainProcess()
            self.opts["mf"].startLoop()

    def setVariables(self):
        self.sql = Sql(
            self.opts["mf"].dbm,
            ["ctlmes", "ctlmst", "drschn", "drsmst", "drstrn", "tplmst"],
            prog=self.__class__.__name__)
        if self.sql.error:
            return
        gc = GetCtl(self.opts["mf"])
        drsctl = gc.getCtl("drsctl", self.opts["conum"])
        if not drsctl:
            return
        self.chains = drsctl["ctd_chain"]
        self.stpl = drsctl["ctd_tplnam"]
        self.ageing = drsctl["ctd_ageing"]
        self.fromad = drsctl["ctd_emadd"]
        t = time.localtime()
        self.sysdtw = (t[0] * 10000) + (t[1] * 100) + t[2]
        if self.chains == "N":
            self.schn = 0
            self.echn = 0
        return True

    def mainProcess(self):
        tpm = {
            "stype":
            "R",
            "tables": ("tplmst", ),
            "cols": (("tpm_tname", "", 0, "Template"), ("tpm_title", "", 0,
                                                        "Title", "Y")),
            "where": [("tpm_type", "=", "S"), ("tpm_system", "=", "DRS")],
            "order":
            "tpm_tname"
        }
        drc = {
            "stype": "R",
            "tables": ("drschn", ),
            "cols":
            (("chm_chain", "", 0, "Num"), ("chm_name", "", 0, "Name", "Y")),
            "where": [("chm_cono", "=", self.opts["conum"])]
        }
        drm = {
            "stype":
            "R",
            "tables": ("drsmst", ),
            "cols":
            (("drm_acno", "", 0, "Acc-Num"), ("drm_name", "", 0, "Name", "Y"),
             ("drm_add1", "", 0, "Address Line 1"))
        }
        if self.chains == "Y":
            drm["where"] = [("drm_cono", "=", self.opts["conum"])]
            drm["whera"] = [["C", "drm_chain", 0, 1]]
        else:
            drm["where"] = [("drm_cono", "=", self.opts["conum"]),
                            ("drm_chain", "=", 0)]
        mss = {
            "stype":
            "R",
            "tables": ("ctlmes", ),
            "cols": (("mss_message", "", 0, "Num"), ("mss_detail", "NA", 50,
                                                     "Details")),
            "where": [("mss_system", "=", "STA")]
        }
        r1s = (("Yes", "Y"), ("No", "N"))
        r2s = (("Yes", "Y"), ("Range", "R"), ("Singles", "S"))
        r3s = (("Number", "N"), ("Name", "M"), ("Postal Code", "P"))
        fld = [[["T", 0, 0, 0], "INA", 20, "Template Name", "", self.stpl, "Y",
                self.doTplNam, tpm, None, None],
               [["T", 0, 1, 0], ("IRB", r1s), 0, "Open Item", "", "Y", "Y",
                self.doOItem, None, None, None],
               [["T", 0, 2, 0], "IUI", 2, "Maximum Pages", "", 1, "Y",
                self.doPages, None, None, None],
               [["T", 0, 3, 0], ("IRB", r2s), 0, "Whole File", "", "S", "Y",
                self.doWhole, None, None, None],
               [["T", 0, 4, 0], "IUI", 3, "From Chain", "", "", "Y",
                self.doChn, drc, None, None],
               [["T", 0, 5, 0], "INA", 7, "From Account", "", "", "Y",
                self.doAcc, drm, None, None],
               [["T", 0, 6, 0], "INA", 3, "To Chain", "", "", "Y", self.doChn,
                drc, None, None],
               [["T", 0, 7, 0], "INA", 7, "To Account", "", "", "Y",
                self.doAcc, drm, None, None],
               [["T", 0, 8, 0], ("IRB", r3s), 0, "Sort Order", "", "N", "Y",
                self.doSort, None, None, None],
               [["T", 0, 9, 0], ("IRB", r1s), 0, "Include Zero Balances", "",
                "N", "Y", self.doZeros, None, None, None],
               [["T", 0, 10, 0], ("IRB", r1s), 0, "Include Negative Balances",
                "", "N", "Y", self.doMinus, None, None, None],
               [["T", 0, 11, 0], ("IRB", r1s), 0, "Include Stopped Accounts",
                "", "N", "Y", self.doStops, None, None, None],
               [["T", 0, 12, 0], ("IRB", r1s), 0, "Include Redundant Accounts",
                "", "N", "Y", self.doRedu, None, None, None],
               [["T", 0, 13,
                 0], ("IRB", r1s), 0, "Include Allocated Transactions", "",
                "N", "Y", self.doAlloc, None, None, None],
               [["T", 0, 14, 0], "ID1", 10, "Statement Date", "", self.sysdtw,
                "Y", self.doDat, None, None, ("efld", )],
               [["T", 0, 15, 0], "IUI", 3, "Message Number", "", "", "Y",
                self.doMessno, mss, None, ("efld", )]]
        if self.chains != "Y":
            del fld[6]
            del fld[4]
            for n, f in enumerate(fld):
                fld[n][0][2] = n
        tnd = ((self.doEnd, "Y"), )
        txt = (self.doExit, )
        self.df = TartanDialog(self.opts["mf"],
                               eflds=fld,
                               tend=tnd,
                               txit=txt,
                               view=("N", "V"),
                               mail=("B", "Y"))

    def doTplNam(self, frt, pag, r, c, p, i, w):
        acc = self.sql.getRec("tplmst",
                              where=[("tpm_tname", "=", w),
                                     ("tpm_type", "=", "S"),
                                     ("tpm_system", "=", "DRS")],
                              limit=1)
        if not acc:
            return "Invalid Template Name"
        self.tname = w
        self.sttyp = acc[self.sql.tplmst_col.index("tpm_sttp")]
        if self.sttyp == "N":
            self.oitem = "Y"
            self.pages = 0
            self.df.loadEntry(frt, pag, p + 1, data=self.oitem)
            self.df.loadEntry(frt, pag, p + 2, data=self.pages)
            return "sk2"

    def doOItem(self, frt, pag, r, c, p, i, w):
        self.oitem = w
        if self.oitem == "N":
            self.pages = 0
            self.df.loadEntry(frt, pag, p + 1, data=self.pages)
            return "sk1"

    def doPages(self, frt, pag, r, c, p, i, w):
        self.pages = w

    def doWhole(self, frt, pag, r, c, p, i, w):
        self.whole = w
        if self.whole in ("Y", "S"):
            self.schn = 0
            self.echn = 0
            self.sacc = ""
            self.eacc = ""
            if self.chains == "Y":
                self.df.loadEntry("T", 0, p + 1, data=self.schn)
                self.df.loadEntry("T", 0, p + 2, data=self.sacc)
                self.df.loadEntry("T", 0, p + 3, data=self.echn)
                self.df.loadEntry("T", 0, p + 4, data=self.eacc)
                return "sk4"
            else:
                self.df.loadEntry("T", 0, p + 1, data=self.sacc)
                self.df.loadEntry("T", 0, p + 2, data=self.eacc)
                return "sk2"

    def doChn(self, frt, pag, r, c, p, i, w):
        chk = self.sql.getRec("drschn",
                              cols=["chm_name"],
                              where=[("chm_chain", "=", w)],
                              limit=1)
        if not chk:
            return "Invalid Chain Store"
        if c == 5:
            self.schn = w
        else:
            self.echn = w

    def doAcc(self, frt, pag, r, c, p, i, w):
        if self.chains == "Y" and c == 6:
            chk = self.schn
            self.sacc = w
        elif self.chains == "Y" and c == 8:
            chk = self.echn
            self.eacc = w
        elif c == 5:
            chk = self.schn
            self.sacc = w
        else:
            chk = self.echn
            self.eacc = w
        chk = self.sql.getRec("drsmst",
                              cols=["drm_name"],
                              where=[("drm_cono", "=", self.opts["conum"]),
                                     ("drm_chain", "=", chk),
                                     ("drm_acno", "=", w)],
                              limit=1)
        if not chk:
            return "Invalid Debtors Account"

    def doSort(self, frt, pag, r, c, p, i, w):
        self.sort = w

    def doZeros(self, frt, pag, r, c, p, i, w):
        self.zeros = w

    def doMinus(self, frt, pag, r, c, p, i, w):
        self.minus = w

    def doStops(self, frt, pag, r, c, p, i, w):
        self.stops = w

    def doRedu(self, frt, pag, r, c, p, i, w):
        self.redu = w
        if self.sttyp == "O":
            self.alloc = "Y"
            self.df.loadEntry(frt, pag, p + 1, data=self.alloc)
            return "sk1"

    def doAlloc(self, frt, pag, r, c, p, i, w):
        self.alloc = w

    def doMessno(self, frt, pag, r, c, p, i, w):
        if w:
            acc = self.sql.getRec("ctlmes",
                                  cols=["mss_detail"],
                                  where=[("mss_system", "=", "STA"),
                                         ("mss_message", "=", w)],
                                  limit=1)
            if not acc:
                return "Invalid Message Number"
        self.mess = w

    def doDat(self, frt, pag, r, c, p, i, w):
        self.datew = w
        self.dated = self.df.t_disp[pag][0][p]
        self.curdt = int(w / 100)

    def doEnd(self):
        self.df.closeProcess()
        self.emadd = self.df.repeml[2]
        if not self.echn:
            self.echn = 999
        if not self.eacc:
            self.eacc = "zzzzzzz"
        whr = [("drm_cono", "=", self.opts["conum"]),
               ("drm_chain", ">=", self.schn), ("drm_acno", ">=", self.sacc),
               ("drm_chain", "<=", self.echn), ("drm_acno", "<=", self.eacc)]
        if self.stops == "N":
            whr.append(("drm_stop", "<>", "Y"))
        if self.redu == "N":
            whr.append(("drm_stat", "<>", "X"))
        if self.whole == "S":
            recs = getSingleRecords(self.opts["mf"],
                                    "drsmst",
                                    ("drm_chain", "drm_acno", "drm_name"),
                                    where=whr)
        else:
            if self.sort == "N":
                odr = "drm_chain, drm_acno"
            elif self.sort == "M":
                odr = "drm_name"
            else:
                odr = "drm_pcod"
            recs = self.sql.getRec("drsmst", where=whr, order=odr)
        if not recs:
            showError(self.opts["mf"].body, "Error", "No Accounts Selected")
        else:
            self.form = DrawForm(self.opts["mf"].dbm,
                                 self.tname,
                                 wrkdir=self.opts["mf"].rcdic["wrkdir"])
            self.doLoadStatic()
            self.form.doNewDetail()
            p = ProgressBar(self.opts["mf"].body, mxs=len(recs), esc=True)
            for num, rec in enumerate(recs):
                p.displayProgress(num)
                if p.quit:
                    break
                self.doProcess(rec)
            p.closeProgress()
            if p.quit or not self.form.page:
                pass
            elif self.df.repeml[1] == "N" or self.emadd:
                self.df.repeml[2] = self.emadd
                self.doPrint()
        self.opts["mf"].closeLoop()

    def doLoadStatic(self):
        cmc = self.sql.ctlmst_col
        ctm = self.sql.getRec("ctlmst",
                              where=[("ctm_cono", "=", self.opts["conum"])],
                              limit=1)
        for fld in cmc:
            dat = ctm[cmc.index(fld)]
            if fld in self.form.tptp:
                if fld == "ctm_logo":
                    self.form.letterhead(cmc, ctm, fld, dat)
                    continue
                self.form.tptp[fld][1] = dat
        if "letterhead" in self.form.tptp:
            self.form.letterhead(cmc, ctm, "letterhead", None)
        self.form.document_date(self.dated)
        self.form.bank_details(cmc, ctm, 0)

    def doProcess(self, drm):
        dmc = self.sql.drsmst_col
        dtc = self.sql.drstrn_col
        tdc = self.form.sql.tpldet_col
        self.chn = drm[dmc.index("drm_chain")]
        self.acc = drm[dmc.index("drm_acno")]
        eml = drm[dmc.index("drm_acc_email")]
        self.form.account_details("drm", dmc, drm, 1)
        if drm[dmc.index("drm_stames")]:
            self.mesno = drm[dmc.index("drm_stames")]
        else:
            self.mesno = self.mess
        for col in dmc:
            d = "%s_C00" % col
            if d in self.form.newdic:
                dat = drm[dmc.index(col)]
                self.form.newdic[d][tdc.index("tpd_text")] = dat
        bals = Balances(self.opts["mf"], "DRS", self.opts["conum"], self.curdt,
                        (self.chn, self.acc))
        if self.alloc == "Y":
            tt = "A"
        else:
            tt = "Y"
        obal, self.tbal, self.ages, trns = bals.doAllBals(trans=tt)
        if not trns[1]:
            return
        if self.sttyp == "O":
            self.tots = [0.0, 0.0, 0.0]
            cmth = False
            tran = copyList(trns[1])
            for t in tran:
                if t[dtc.index("drt_type")] not in (2, 6) and \
                        t[dtc.index("drt_curdt")] == self.curdt:
                    self.tots[1] = float(ASD(self.tots[1]) + \
                        ASD(t[dtc.index("drt_tramt")]))
                    if t[dtc.index("drt_taxamt")]:
                        self.tots[1] = float(ASD(self.tots[1]) - \
                            ASD(t[dtc.index("drt_taxamt")]))
                        self.tots[2] = float(ASD(self.tots[2]) + \
                            ASD(t[dtc.index("drt_taxamt")]))
                else:
                    self.tots[0] = float(ASD(self.tots[0]) + \
                        ASD(t[dtc.index("drt_tramt")]))
                if t[dtc.index("drt_curdt")] == self.curdt:
                    cmth = True
                elif self.oitem == "N":
                    trns[1].remove(t)
            if self.zeros == "N" and not self.tbal and not cmth:
                return
            if self.minus == "N" and self.tbal < 0:
                return
            if self.oitem == "N" and obal:
                t[trns[0].index("drt_type")] = 3
                t[trns[0].index("drt_ref1")] = "O/Bal"
                t[trns[0].index("drt_batch")] = ""
                t[trns[0].index("drt_trdt")] = (self.curdt * 100) + 1
                t[trns[0].index("drt_ref2")] = ""
                t[trns[0].index("drt_tramt")] = obal
                t[trns[0].index("drt_taxamt")] = 0
                t[trns[0].index("drt_desc")] = "Opening Balance"
                t[trns[0].index("drt_taxind")] = ""
                t[trns[0].index("drt_batind")] = ""
                trns[1].insert(0, t)
            if len(trns[1]) <= self.form.maxlines:
                self.doBody(trns[0], trns[1], tdc)
            else:
                pages = int(len(trns[1]) / self.form.maxlines)
                if len(trns[1]) % self.form.maxlines:
                    pages += 1
                if pages <= self.pages:
                    self.doBody(trns[0], trns[1], tdc)
                else:
                    bal = 0
                    lines = len(
                        trns[1]) - (self.pages * self.form.maxlines) + 1
                    for _ in range(lines):
                        trn = trns[1].pop(0)
                        bal = float(
                            ASD(bal) + ASD(trn[dtc.index("drt_tramt")]))
                    trn[trns[0].index("drt_type")] = 3
                    trn[trns[0].index("drt_ref1")] = "B/FWD"
                    trn[trns[0].index("drt_batch")] = ""
                    trn[trns[0].index("drt_ref2")] = ""
                    trn[trns[0].index("drt_tramt")] = bal
                    trn[trns[0].index("drt_taxamt")] = 0
                    trn[trns[0].index("drt_desc")] = "Balance Brought Forward"
                    trn[trns[0].index("drt_taxind")] = ""
                    trn[trns[0].index("drt_batind")] = ""
                    trns[1].insert(0, trn)
                    self.doBody(trns[0], trns[1], tdc)
        else:
            if self.zeros == "N" and not self.tbal:
                return
            if self.minus == "N" and self.tbal < 0:
                return
            self.doBody(trns[0], trns[1], tdc)
        self.doTotal(tdc)
        self.doTail(tdc)
        if self.df.repeml[1] == "Y" and not self.emadd:
            self.df.repeml[2] = eml
            self.doPrint()

    def doPrint(self):
        if self.df.repeml[1] == "Y" and not self.emadd:
            key = "%s_%s_%s" % (self.opts["conum"], self.chn, self.acc)
        else:
            key = "%s_all_all" % self.opts["conum"]
        pdfnam = getModName(self.opts["mf"].rcdic["wrkdir"],
                            self.__class__.__name__,
                            key,
                            ext="pdf")
        self.form.output(pdfnam, "F")
        doPrinter(mf=self.opts["mf"],
                  conum=self.opts["conum"],
                  pdfnam=pdfnam,
                  header="%s Statement for %s as at %s" %
                  (self.opts["conam"], self.acc, self.dated),
                  repprt=self.df.repprt,
                  fromad=self.fromad,
                  repeml=self.df.repeml)
        if self.df.repeml[1] == "Y":
            self.form = DrawForm(self.opts["mf"].dbm,
                                 self.tname,
                                 wrkdir=self.opts["mf"].rcdic["wrkdir"])
            self.doLoadStatic()
            self.form.doNewDetail()

    def doBody(self, dtc, drt, tdc):
        page = 0
        count = 0
        rbal = 0
        text = tdc.index("tpd_text")
        for trans in drt:
            if not count:
                page += 1
                count = self.doHeader(page)
            if count == self.form.maxlines:
                page = self.doCfwd(page)
                count = self.doHeader(page)
            for cod in self.form.body:
                if cod == "type_code":
                    c = "drt_type"
                elif cod == "line_paid":
                    c = "paid"
                elif cod == "line_balance":
                    c = "balance"
                else:
                    c = cod
                d = "%s_C%02i" % (cod, count)
                if cod == "type_code":
                    ttyp = trans[dtc.index(c)]
                    self.form.newdic[d][text] = drtrtp[ttyp - 1][0]
                elif self.sttyp == "O" and cod == "running_balance":
                    self.form.newdic[d][text] = rbal
                else:
                    self.form.newdic[d][text] = trans[dtc.index(c)]
                    if self.sttyp == "O" and cod == "drt_tramt":
                        rbal = float(ASD(rbal) + ASD(trans[dtc.index(c)]))
                self.form.doDrawDetail(self.form.newdic[d])
            count += 1
        for x in range(count, self.form.maxlines):
            for cod in self.form.body:
                d = "%s_C%02i" % (cod, x)
                self.form.newdic[d][tdc.index("tpd_text")] = "BLANK"
                self.form.doDrawDetail(self.form.newdic[d])

    def doHeader(self, page):
        self.form.add_page()
        tdc = self.form.sql.tpldet_col
        for key in self.form.newkey:
            nl = copyList(self.form.newdic[key])
            if nl[tdc.index("tpd_place")] != "A":
                continue
            if nl[tdc.index("tpd_detseq")] == "drm_acno_C00":
                nl[tdc.index("tpd_text")] = self.acc
            elif nl[tdc.index("tpd_detseq")] == "page_number_C00":
                nl[tdc.index("tpd_text")] = str(page)
            self.form.doDrawDetail(nl)
        return 0

    def doCfwd(self, page):
        if "carried_forward" in self.form.tptp:
            tdc = self.form.sql.tpldet_col
            line = copyList(self.form.cfwd)
            line[tdc.index("tpd_text")] = "Continued on Page %i" % (page + 1)
            self.form.doDrawDetail(line)
        return page + 1

    def doTotal(self, tdc):
        for c in self.form.total:
            if self.ageing == "N" and c != "total_balance":
                continue
            t = "%s_T00" % c
            if c in self.form.newdic:
                self.form.doDrawDetail(self.form.newdic[c])
            elif t in self.form.newdic:
                self.form.doDrawDetail(self.form.newdic[t])
            d = "%s_C00" % c
            if d in self.form.newdic:
                line = self.form.newdic[d]
                if c == "120_day_balance":
                    line[tdc.index("tpd_text")] = self.ages[4]
                elif c == "90_day_balance":
                    line[tdc.index("tpd_text")] = self.ages[3]
                elif c == "60_day_balance":
                    line[tdc.index("tpd_text")] = self.ages[2]
                elif c == "30_day_balance":
                    line[tdc.index("tpd_text")] = self.ages[1]
                elif c == "current_balance":
                    line[tdc.index("tpd_text")] = self.ages[0]
                elif c == "total_arrears":
                    line[tdc.index("tpd_text")] = self.tots[0]
                elif c == "month_exclusive":
                    line[tdc.index("tpd_text")] = self.tots[1]
                elif c == "month_tax":
                    line[tdc.index("tpd_text")] = self.tots[2]
                elif c == "total_balance":
                    line[tdc.index("tpd_text")] = self.tbal
                self.form.doDrawDetail(line)

    def doTail(self, tdc):
        for c in self.form.tail:
            if c == "message" and not self.mesno:
                continue
            t = "%s_T00" % c
            if c in self.form.newdic:
                self.form.doDrawDetail(self.form.newdic[c])
            elif t in self.form.newdic:
                self.form.doDrawDetail(self.form.newdic[t])
            d = "%s_C00" % c
            if d in self.form.newdic:
                if d == "message_C00" and self.mesno:
                    mes = self.sql.getRec("ctlmes",
                                          cols=["mss_detail"],
                                          where=[("mss_system", "=", "STA"),
                                                 ("mss_message", "=",
                                                  self.mesno)],
                                          limit=1)
                    self.form.newdic[d][tdc.index("tpd_text")] = mes[0]
                self.form.doDrawDetail(self.form.newdic[d])

    def doExit(self):
        self.df.closeProcess()
        self.opts["mf"].closeLoop()
Example #2
0
class cr3080(object):
    def __init__(self, **opts):
        self.opts = opts
        if self.setVariables():
            self.mainProcess()
            if "wait" in self.opts:
                self.df.mstFrame.wait_window()
            else:
                self.opts["mf"].startLoop()

    def setVariables(self):
        gc = GetCtl(self.opts["mf"])
        crsctl = gc.getCtl("crsctl", self.opts["conum"])
        if not crsctl:
            return
        t = time.localtime()
        self.sysdtw = (t[0] * 10000) + (t[1] * 100) + t[2]
        self.sql = Sql(self.opts["mf"].dbm, [
            "ctlctl", "ctlmst", "crsctl", "crsmst", "crstrn", "crsage",
            "gentrn", "tplmst"
        ],
                       prog=self.__class__.__name__)
        if self.sql.error:
            return
        self.glint = crsctl["ctc_glint"]
        self.bestac = crsctl["ctc_bestac"]
        self.besttp = crsctl["ctc_besttp"]
        self.bankac = crsctl["ctc_bankac"]
        self.tplnam = crsctl["ctc_tplnam"]
        self.fromad = crsctl["ctc_emadd"]
        if self.glint == "Y":
            ctlctl = gc.getCtl("ctlctl", self.opts["conum"])
            if not ctlctl:
                return
            if gc.chkRec(self.opts["conum"], ctlctl, ["crs_ctl"]):
                return
            self.crsctl = ctlctl["crs_ctl"]
        acc = self.sql.getRec("crstrn",
                              cols=["max(crt_ref1)"],
                              where=[("crt_cono", "=", self.opts["conum"]),
                                     ("crt_type", "=", 5),
                                     ("crt_ref1", "like", "EFT______")],
                              limit=1)
        try:
            self.cats = int(acc[0][3:])
            self.refs = int(acc[0][3:]) + 1
        except:
            self.cats = 0
            self.refs = 1
        self.etotal = 0
        return True

    def mainProcess(self):
        tpm = {
            "stype":
            "R",
            "tables": ("tplmst", ),
            "cols": (("tpm_tname", "", 0, "Template"), ("tpm_title", "", 0,
                                                        "Title", "Y")),
            "where": [("tpm_type", "=", "R"), ("tpm_system", "=", "CRS")],
            "order":
            "tpm_tname"
        }
        crm = {
            "stype":
            "R",
            "tables": ("crsmst", ),
            "cols":
            (("crm_acno", "", 0, "Acc-Num"), ("crm_name", "", 0, "Name", "Y")),
            "where": [("crm_cono", "=", self.opts["conum"]),
                      ("crm_stat", "<>", "X")]
        }
        r1s = (("Yes", "Y"), ("Range", "R"), ("Singles", "S"))
        r2s = (("Yes", "Y"), ("No", "N"))
        r3s = (("Number", "N"), ("Name", "M"), ("Postal Code", "P"))
        r4s = (("Monthly", "M"), ("Daily", "D"))
        fld = ((("T", 0, 0, 0), "INA", 20, "Template Name", "", self.tplnam,
                "Y", self.doTplNam, tpm, None, None),
               (("T", 0, 1, 0), ("IRB", r1s), 0, "Whole File", "", "S", "Y",
                self.doWhole, None, None, None), [["T", 0, 2, 0], "INA", 7,
                                                  "From Account", "", "", "Y",
                                                  self.doAcc, crm, None, None],
               [["T", 0, 3, 0], "INA", 7, "To   Account", "", "", "Y",
                self.doAcc, crm, None,
                None], (("T", 0, 4, 0), ("IRB", r3s), 0, "Sort Order", "", "N",
                        "Y", self.doSort, None, None, None),
               (("T", 0, 5, 0), ("IRB", r4s), 0, "Terms Base", "", "M", "Y",
                self.doFrequency, None, None,
                None), (("T", 0, 6, 0), ("IRB", r2s), 0, "Exceptions", "", "N",
                        "Y", self.doExcepts, None, None, None),
               (("T", 0, 7, 0), "ID1", 10, "Due Date", "", self.sysdtw, "Y",
                self.doDuedat, None, None, ("efld", )),
               (("T", 0, 8, 0), "ID1", 10, "Payment Date", "", self.sysdtw,
                "Y", self.doPaydat, None, None, ("efld", )))
        tnd = ((self.doEnd, "Y"), )
        txt = (self.doExit, )
        self.df = TartanDialog(self.opts["mf"],
                               eflds=fld,
                               tend=tnd,
                               txit=txt,
                               view=("N", "V"),
                               mail=("B", "Y"))

    def doTplNam(self, frt, pag, r, c, p, i, w):
        acc = self.sql.getRec("tplmst",
                              where=[("tpm_tname", "=", w),
                                     ("tpm_type", "=", "R"),
                                     ("tpm_system", "=", "CRS")],
                              limit=1)
        if not acc:
            return "Invalid Template Name"
        self.tname = w

    def doWhole(self, frt, pag, r, c, p, i, w):
        self.whole = w
        if self.whole in ("Y", "S"):
            self.sacc = ""
            self.eacc = ""
            self.df.loadEntry("T", 0, p + 1, data=self.sacc)
            self.df.loadEntry("T", 0, p + 2, data=self.eacc)
            return "sk2"

    def doAcc(self, frt, pag, r, c, p, i, w):
        chk = self.sql.getRec("crsmst",
                              cols=["crm_name", "crm_stat"],
                              where=[("crm_cono", "=", self.opts["conum"]),
                                     ("crm_acno", "=", w)],
                              limit=1)
        if not chk:
            return "Invalid Creditors Account"
        if not chk[1] == "X":
            return "Invalid Account, Redundant"
        if c == 3:
            self.sacc = w
        else:
            self.eacc = w

    def doSort(self, frt, pag, r, c, p, i, w):
        self.sort = w

    def doFrequency(self, frt, pag, r, c, p, i, w):
        self.freq = w

    def doExcepts(self, frt, pag, r, c, p, i, w):
        self.excepts = w

    def doDuedat(self, frt, pag, r, c, p, i, w):
        self.duedtw = w
        self.duedtd = self.df.t_disp[pag][0][p]

    def doPaydat(self, frt, pag, r, c, p, i, w):
        self.paydtw = w
        self.paydtd = self.df.t_disp[pag][0][p]
        self.curdt = int(self.paydtw / 100)
        self.batno = "E%s" % self.curdt

    def doEnd(self):
        self.df.closeProcess()
        if self.excepts == "Y":
            self.doExceptions()
        self.emadd = self.df.repeml[2]
        if self.bestac:
            self.export = open(
                os.path.join(
                    self.opts["mf"].rcdic["wrkdir"],
                    "best%03d_%s.txt" % (self.opts["conum"], self.paydtw)),
                "w")
            # Header for BEST
            self.export.write("%1s%4s%-40s%8s%1s%8s%-15s%1s%2s%1s%9s%2s%4s"\
                "\r\n" % ("*", self.bestac, self.opts["conam"], self.paydtw,
                "Y", "", "CREDITORS EFT", "+", self.besttp, 0, "", "01",
                "LIVE"))
        else:
            self.export = None
        if self.whole == "S":
            recs = getSingleRecords(self.opts["mf"],
                                    "crsmst", ("crm_acno", "crm_name"),
                                    where=[("crm_cono", "=",
                                            self.opts["conum"]),
                                           ("crm_termsb", "=", self.freq),
                                           ("crm_pyind", "<>", "N"),
                                           ("crm_stat", "<>", "X")])
        else:
            if not self.eacc:
                self.eacc = "zzzzzzz"
            whr = [("crm_cono", "=", self.opts["conum"]),
                   ("crm_acno", "between", self.sacc, self.eacc),
                   ("crm_termsb", "=", self.freq), ("crm_pyind", "<>", "N"),
                   ("crm_stat", "<>", "X")]
            if self.sort == "N":
                odr = "crm_acno"
            elif self.sort == "M":
                odr = "crm_name"
            else:
                odr = "crm_pcod"
            recs = self.sql.getRec("crsmst", where=whr, order=odr)
            if not recs:
                showError(self.opts["mf"].body, "Error",
                          "No Accounts Selected")
        if recs:
            self.form = DrawForm(self.opts["mf"].dbm,
                                 self.tname,
                                 wrkdir=self.opts["mf"].rcdic["wrkdir"])
            self.doLoadStatic()
            self.form.doNewDetail()
            p = ProgressBar(self.opts["mf"].body, mxs=len(recs), esc=True)
            for num, rec in enumerate(recs):
                p.displayProgress(num)
                if p.quit:
                    self.opts["mf"].dbm.rollbackDbase()
                    break
                self.doProcess(rec)
            p.closeProgress()
            if p.quit or not self.form.page:
                pass
            elif self.df.repeml[1] == "N" or self.emadd:
                self.df.repeml[2] = self.emadd
                self.doPrint()
            if self.bestac:
                # Trailer for BEST
                value = int(round((self.etotal * 100), 0))
                self.export.write("%1s%4s%1s%30s%013u%47s\r\n" % \
                    (2, self.bestac, "T", "", value, ""))
                self.export.close()
                if self.glint == "Y" and self.etotal:
                    # Create total transactions in GL
                    data = [
                        self.opts["conum"], self.crsctl, self.curdt,
                        self.paydtw, 2, self.refno, self.batno, self.etotal,
                        0.0,
                        "Payment EFT%06i to EFT%06i" % (self.refs, self.cats),
                        "", "", 0, self.opts["capnm"], self.sysdtw, 0
                    ]
                    self.sql.insRec("gentrn", data=data)
                    data[1] = self.bankac
                    data[7] = float(ASD(0) - ASD(self.etotal))
                    self.sql.insRec("gentrn", data=data)
                self.opts["mf"].dbm.commitDbase(
                    ask=True,
                    mess="""Would you like to commit all elecronic payments?

If you decide to do this, you must remember to upload the BEST file to the Bank otherwise you are NOT going to Reconcile!""",
                    default="no")
        if "wait" not in self.opts:
            self.opts["mf"].closeLoop()

    def doExceptions(self):
        crm = {
            "stype":
            "R",
            "tables": ("crsmst", ),
            "cols":
            (("crm_acno", "", 0, "Acc-Num"), ("crm_name", "", 0, "Name", "Y")),
            "where": [("crm_cono", "=", self.opts["conum"]),
                      ("crm_termsb", "=", self.freq), ("crm_stat", "<>", "X")]
        }
        crt = {
            "stype":
            "R",
            "tables": ("crstrn", ),
            "cols":
            (("crt_ref1", "", 0, "Reference", "Y"), ("crt_type",
                                                     ("XX", crtrtp), 3, "Typ"),
             ("crt_trdt", "", 0, "Date"), ("crt_tramt", "", 0, "    Amount"),
             ("paid", "SD", 13.2,
              "      Paid"), ("balance", "SD", 13.2,
                              "   Balance"), ("crt_paydt", "", 0, "Pay-Date"),
             ("crt_payind", "", 0, "I"), ("crt_payamt", "", 0, "  Pay-Amnt")),
            "wtype":
            "D",
            "where": [],
            "order":
            "crt_ref1"
        }
        types = []
        for x in range(1, len(crtrtp) + 1):
            types.append((x, crtrtp[x - 1][1]))
        typ = {
            "stype": "C",
            "titl": "Select the Required Type",
            "head": ("C", "Type"),
            "data": types
        }
        fld = ((("T", 0, 0,
                 0), "I@crm_acno", 0, "", "", "", "N", self.doExAcNo, crm,
                None, ("notblank", )), (("T", 0, 0, 0), "O@crm_name", 0, ""),
               (("C", 0, 0, 1), "I@crt_type", 0, "", "", "", "N",
                self.doExTrnTyp, typ, None, ("in", (1, 2, 3, 4, 5))),
               (("C", 0, 0, 0), "I@crt_ref1", 0, "", "", "", "N",
                self.doExTrnRef, crt, None, ("notblank", )),
               (("C", 0, 0, 2), "O@crt_trdt", 0, ""), (("C", 0, 0, 3), "OSD",
                                                       13.2, "Balance"),
               (("C", 0, 0, 4), "I@crt_payind", 0, "", "", "", "N",
                self.doExInd, None, None, ("in", ("Y", "N"))),
               (("C", 0, 0, 5), "I@crt_paydt", 0, "", "", "", "N",
                self.doExDte, None, None,
                ("efld", )), (("C", 0, 0, 6), "I@crt_payamt", 0, "", "", "",
                              "N", self.doExAmt, None, None, ("efld", )))
        tnd = ((self.doExEndTop, "n"), )
        txt = (self.doExExitTop, )
        cnd = ((self.doExEndCol, "y"), )
        cxt = (self.doExExitCol, )
        self.ex = TartanDialog(self.opts["mf"],
                               eflds=fld,
                               tend=tnd,
                               txit=txt,
                               cend=cnd,
                               cxit=cxt)
        self.ex.mstFrame.wait_window()

    def doExAcNo(self, frt, pag, r, c, p, i, w):
        acc = self.sql.getRec(
            "crsmst",
            cols=["crm_name", "crm_termsb", "crm_pyind", "crm_stat"],
            where=[("crm_cono", "=", self.opts["conum"]),
                   ("crm_acno", "=", w)],
            limit=1)
        if not acc:
            return "Invalid Account Number"
        if acc[1] != self.freq:
            return "Invalid Terms Base"
        if acc[2] == "N":
            return "Invalid Payment Indicator"
        if acc[3] == "X":
            return "Invalid Account, Redundant"
        self.exacc = w
        self.ex.loadEntry(frt, pag, p + 1, data=acc[0])

    def doExEndTop(self):
        self.ex.focusField("C", 0, 1)

    def doExExitTop(self):
        self.opts["mf"].dbm.commitDbase(
            ask=True, mess="Would you like to commit these exceptions?")
        self.ex.closeProcess()

    def doExTrnTyp(self, frt, pag, r, c, p, i, w):
        self.extyp = w
        data = []
        # Build the data for the F1 choice selection
        col, dat = getTrn(self.opts["mf"].dbm,
                          "crs",
                          whr=[("crt_cono", "=", self.opts["conum"]),
                               ("crt_acno", "=", self.exacc),
                               ("crt_type", "=", w)],
                          zer="N")
        if dat:
            cols = ("crt_ref1", "crt_type", "crt_trdt", "crt_tramt", "paid",
                    "balance", "crt_paydt", "crt_payind", "crt_payamt")
            for d in dat:
                rec = []
                for cc in cols:
                    rec.append(d[col.index(cc)])
                data.append(rec)
        self.ex.colf[0][1][8]["where"] = data

    def doExTrnRef(self, frt, pag, r, c, p, i, w):
        col = ["crt_trdt", "balance", "crt_payind", "crt_paydt", "crt_payamt"]
        whr = [("crt_cono", "=", self.opts["conum"]),
               ("crt_acno", "=", self.exacc), ("crt_type", "=", self.extyp),
               ("crt_ref1", "=", w)]
        c, d = getTrn(self.opts["mf"].dbm, "crs", whr=whr, lim=1)
        if not d:
            return "Invalid Transaction Number"
        if not d[0][c.index("balance")]:
            return "Transaction Has No Balance"
        self.exref = w
        self.exdte = d[0][c.index("crt_paydt")]
        self.examt = d[0][c.index("crt_payamt")]
        for pos, fld in enumerate(col):
            self.ex.loadEntry(frt, pag, p + 1 + pos, data=d[0][c.index(fld)])

    def doExInd(self, frt, pag, r, c, p, i, w):
        self.exind = w
        if self.exind == "N":
            return "nd"

    def doExDte(self, frt, pag, r, c, p, i, w):
        self.exdte = w

    def doExAmt(self, frt, pag, r, c, p, i, w):
        self.examt = w

    def doExEndCol(self):
        # Update Transaction"
        self.sql.updRec("crstrn",
                        cols=["crt_payind", "crt_paydt", "crt_payamt"],
                        data=[self.exind, self.exdte, self.examt],
                        where=[("crt_cono", "=", self.opts["conum"]),
                               ("crt_acno", "=", self.exacc),
                               ("crt_type", "=", self.extyp),
                               ("crt_ref1", "=", self.exref)])
        self.ex.advanceLine(0)

    def doExExitCol(self):
        self.ex.focusField("T", 0, 1)

    def doLoadStatic(self):
        cmc = self.sql.ctlmst_col
        ctm = self.sql.getRec("ctlmst",
                              where=[("ctm_cono", "=", self.opts["conum"])],
                              limit=1)
        for fld in cmc:
            dat = ctm[cmc.index(fld)]
            if fld in self.form.tptp:
                if fld == "ctm_logo":
                    self.form.letterhead(cmc, ctm, fld, dat)
                    continue
                self.form.tptp[fld][1] = dat
        if "letterhead" in self.form.tptp:
            self.form.letterhead(cmc, ctm, "letterhead", None)
        self.form.document_date(self.duedtd)

    def doProcess(self, crm):
        cmc = self.sql.crsmst_col
        tdc = self.form.sql.tpldet_col
        self.acno = crm[cmc.index("crm_acno")]
        eml = crm[cmc.index("crm_acc_email")]
        self.form.account_details("crm", cmc, crm, 1)
        for col in cmc:
            d = "%s_C00" % col
            if d in self.form.newdic:
                dat = crm[cmc.index(col)]
                self.form.newdic[d][tdc.index("tpd_text")] = dat
        jon = "cra_curdt <= %s" % self.curdt
        whr = [("crt_cono", "=", self.opts["conum"]),
               ("crt_acno", "=", self.acno), ("crt_payind", "=", "Y"),
               ("crt_paydt", "<=", self.duedtw)]
        ctc, crt = getTrn(self.opts["mf"].dbm,
                          "crs",
                          jon=jon,
                          whr=whr,
                          zer="N")
        if not crt:
            return
        bal = 0
        self.pay = 0
        for d in crt:
            if d[ctc.index("balance")] < 0:
                d[ctc.index("crt_payamt")] = d[ctc.index("balance")]
            bal = float(ASD(bal) + ASD(d[ctc.index("balance")]))
            self.pay = float(ASD(self.pay) + ASD(d[ctc.index("crt_payamt")]))
        if self.pay > bal:
            self.pay = bal
        if self.pay > 0:
            self.bname = crm[cmc.index("crm_bname")]
            self.bibt = crm[cmc.index("crm_bibt")]
            self.bacc = crm[cmc.index("crm_bacc")]
            if self.bname and self.bibt and self.bacc:
                self.ptype = "E"  # Electronic
                test = False
                while not test:
                    self.cats += 1
                    self.refno = "EFT%06i" % self.cats
                    # Check if Reference Number Already Exists
                    chk = self.sql.getRec("crstrn",
                                          where=[("crt_cono", "=",
                                                  self.opts["conum"]),
                                                 ("crt_acno", "=", self.acno),
                                                 ("crt_type", "=", 5),
                                                 ("crt_ref1", "=", self.refno)
                                                 ])
                    if not chk:
                        test = True
            else:
                self.ptype = "C"  # Cheque
            self.doBody(ctc, crt, tdc)
            self.doTotal(tdc)
            self.doTail(tdc)
            if self.df.repeml[1] == "Y" and not self.emadd:
                self.df.repeml[2] = eml
                self.doPrint()

    def doPrint(self):
        if self.df.repeml[1] == "Y" and not self.emadd:
            key = "%s_%s" % (self.opts["conum"], self.acno)
        else:
            key = "%s_all" % self.opts["conum"]
        pdfnam = getModName(self.opts["mf"].rcdic["wrkdir"],
                            self.__class__.__name__,
                            key,
                            ext="pdf")
        self.form.output(pdfnam, "F")
        doPrinter(mf=self.opts["mf"],
                  conum=self.opts["conum"],
                  pdfnam=pdfnam,
                  header="%s Remittance Advice" % self.opts["conam"],
                  repprt=self.df.repprt,
                  fromad=self.fromad,
                  repeml=self.df.repeml)
        if self.df.repeml[1] == "Y":
            self.form = DrawForm(self.opts["mf"].dbm,
                                 self.tname,
                                 wrkdir=self.opts["mf"].rcdic["wrkdir"])
            self.doLoadStatic()
            self.form.doNewDetail()

    def doBody(self, ctc, crt, tdc):
        page = 0
        count = 0
        text = self.form.sql.tpldet_col.index("tpd_text")
        for trans in crt:
            trbal = trans[ctc.index("balance")]
            payamt = trans[ctc.index("crt_payamt")]
            if payamt > trbal:
                payamt = trbal
            trans[ctc.index("balance")] = payamt
            if not count:
                page += 1
                count = self.doHeader(page)
            if count == self.form.maxlines:
                page = self.doCfwd(page)
                count = self.doHeader(page)
            for cod in self.form.body:
                if cod == "type_code":
                    c = "crt_type"
                elif cod == "line_paid":
                    c = "paid"
                elif cod == "line_balance":
                    c = "balance"
                else:
                    c = cod
                d = "%s_C%02i" % (cod, count)
                if cod == "type_code":
                    ttyp = trans[ctc.index(c)]
                    self.form.newdic[d][text] = crtrtp[ttyp - 1][0]
                else:
                    self.form.newdic[d][text] = trans[ctc.index(c)]
                self.form.doDrawDetail(self.form.newdic[d])
            if self.ptype == "E" and self.bestac:
                trtp = trans[ctc.index("crt_type")]
                ref1 = trans[ctc.index("crt_ref1")]
                # Create Ageing Transaction
                self.sql.insRec("crsage",
                                data=[
                                    self.opts["conum"], self.acno, trtp, ref1,
                                    self.curdt, 5, self.refno, payamt, 0
                                ])
            count += 1
        for x in range(count, self.form.maxlines):
            for cod in self.form.body:
                d = "%s_C%02i" % (cod, x)
                self.form.newdic[d][tdc.index("tpd_text")] = "BLANK"
                self.form.doDrawDetail(self.form.newdic[d])

    def doHeader(self, page):
        tdc = self.form.sql.tpldet_col
        self.form.add_page()
        for key in self.form.newkey:
            nl = copyList(self.form.newdic[key])
            if nl[tdc.index("tpd_place")] != "A":
                continue
            if nl[tdc.index("tpd_detseq")] == "crm_acno_C00":
                nl[tdc.index("tpd_text")] = self.acno
            elif nl[tdc.index("tpd_detseq")] == "page_number_C00":
                nl[tdc.index("tpd_text")] = str(page)
            self.form.doDrawDetail(nl)
        return 0

    def doCfwd(self, page):
        if "carried_forward" in self.form.tptp:
            tdc = self.form.sql.tpldet_col
            line = copyList(self.form.cfwd)
            line[tdc.index("tpd_text")] = "Continued on Page %i" % (page + 1)
            self.form.doDrawDetail(line)
        return page + 1

    def doTotal(self, tdc):
        for c in self.form.total:
            t = "%s_T00" % c
            if c in self.form.newdic:
                self.form.doDrawDetail(self.form.newdic[c])
            elif t in self.form.newdic:
                self.form.doDrawDetail(self.form.newdic[t])
            d = "%s_C00" % c
            if d in self.form.newdic:
                line = self.form.newdic[d]
                if c == "total_payment":
                    line[tdc.index("tpd_text")] = self.pay
                self.form.doDrawDetail(line)
        if self.ptype == "E" and self.bestac:
            value = int(round((self.pay * 100), 0))
            self.export.write("%1s%4s%06u%-7s%019u%1s%1s%011u%-20s%10s"\
                "%-15s%1s\r\n" % (2, self.bestac, self.bibt, self.acno,
                int(self.bacc), "", "1", value, self.bname, "",
                self.opts["conam"][:15], ""))
            self.etotal = float(ASD(self.etotal) + ASD(self.pay))
            # Create Payment and Ageing Transaction
            p = float(ASD(0) - ASD(self.pay))
            self.sql.insRec("crstrn",
                            data=[
                                self.opts["conum"], self.acno, 5, self.refno,
                                self.batno, self.paydtw, "", p, 0.0, 0.0,
                                self.curdt, 0, "", 0.0, "Electronic Payment",
                                "", "", self.opts["capnm"], self.sysdtw, 0
                            ])
            self.sql.insRec("crsage",
                            data=[
                                self.opts["conum"], self.acno, 5, self.refno,
                                self.curdt, 5, self.refno, p, 0
                            ])

    def doTail(self, tdc):
        for c in self.form.tail:
            t = "%s_T00" % c
            if c in self.form.newdic:
                self.form.doDrawDetail(self.form.newdic[c])
            elif t in self.form.newdic:
                self.form.doDrawDetail(self.form.newdic[t])
            d = "%s_C00" % c
            if d in self.form.newdic:
                line = self.form.newdic[d]
                if c == "eft_message" and self.ptype == "E" and self.bestac:
                    line[tdc.index("tpd_text")] = "ELECTRONIC TRANSFER AT %s "\
                        "REFERENCE %s" % (self.paydtd, self.refno)
                self.form.doDrawDetail(line)

    def doExit(self):
        self.df.closeProcess()
        if "wait" not in self.opts:
            self.opts["mf"].closeLoop()
Example #3
0
class ln3040(object):
    def __init__(self, **opts):
        self.opts = opts
        if self.setVariables():
            self.mainProcess()
            self.opts["mf"].startLoop()

    def setVariables(self):
        gc = GetCtl(self.opts["mf"])
        lonctl = gc.getCtl("lonctl", self.opts["conum"])
        if not lonctl:
            return
        self.capb = lonctl["cln_capb"]
        self.capf = lonctl["cln_capf"]
        self.lint = lonctl["cln_last"]
        self.stpl = lonctl["cln_tplnam"]
        self.fromad = lonctl["cln_emadd"]
        t = time.localtime()
        self.sysdtw = (t[0] * 10000) + (t[1] * 100) + t[2]
        self.curdt = int(self.sysdtw / 100)
        self.sper = int(self.opts["period"][1][0] / 100)
        self.eper = int(self.opts["period"][2][0] / 100)
        self.sql = Sql(self.opts["mf"].dbm, [
            "ctlmes", "ctlmst", "ctlynd", "lonmf1", "lonmf2", "lontrn",
            "tplmst"
        ],
                       prog=self.__class__.__name__)
        if self.sql.error:
            return
        return True

    def mainProcess(self):
        tpm = {
            "stype":
            "R",
            "tables": ("tplmst", ),
            "cols": (("tpm_tname", "", 0, "Template"), ("tpm_title", "", 0,
                                                        "Title", "Y")),
            "where": [("tpm_type", "=", "S"), ("tpm_system", "=", "LON")],
            "order":
            "tpm_tname"
        }
        r1s = (("Yes", "Y"), ("No", "N"))
        r2s = (("Number", "A"), ("Name", "N"))
        fld = ((("T", 0, 0, 0), "INA", 20, "Template Name", "", self.stpl, "Y",
                self.doTplNam, tpm, None, None),
               (("T", 0, 1, 0), "Id2", 7, "Start Period", "", self.sper, "N",
                self.doSPer, None, None,
                None), (("T", 0, 2, 0), "ID2", 7, "End Period", "", self.eper,
                        "N", self.doEPer, None, None,
                        None), (("T", 0, 3, 0), ("IRB", r1s), 0, "Whole File",
                                "", "N", "N", self.doWhole, None, None, None),
               (("T", 0, 4, 0), ("IRB", r2s), 0, "Sort Order", "", "A", "N",
                self.doSort, None, None, None),
               (("T", 0, 5, 0), ("IRB", r1s), 0, "Include Zero Balances", "",
                "N", "N", self.doZeros, None, None, None),
               (("T", 0, 6, 0), ("IRB", r1s), 0, "Include Pending Interest",
                "", "N", "N", self.doPend, None, None, None),
               (("T", 0, 7, 0), ("IRB", r1s), 0, "Interest Totals Only", "",
                "Y", "N", self.doITots, None, None, None))
        tnd = ((self.doEnd, "Y"), )
        txt = (self.doExit, )
        self.df = TartanDialog(self.opts["mf"],
                               eflds=fld,
                               tend=tnd,
                               txit=txt,
                               view=("N", "V"),
                               mail=("B", "Y"))

    def doTplNam(self, frt, pag, r, c, p, i, w):
        acc = self.sql.getRec("tplmst",
                              where=[("tpm_tname", "=", w),
                                     ("tpm_type", "=", "S"),
                                     ("tpm_system", "=", "LON")],
                              limit=1)
        if not acc:
            return "Invalid Template Name"
        self.tname = w

    def doSPer(self, frt, pag, r, c, p, i, w):
        self.sperw = w
        self.sperd = self.df.t_disp[pag][0][p]

    def doEPer(self, frt, pag, r, c, p, i, w):
        self.eperw = w
        self.eperd = self.df.t_disp[pag][0][p]
        self.date = CCD(mthendDate((w * 100) + 1), "D1", 10)

    def doWhole(self, frt, pag, r, c, p, i, w):
        self.whole = w

    def doSort(self, frt, pag, r, c, p, i, w):
        self.sort = w

    def doZeros(self, frt, pag, r, c, p, i, w):
        self.zeros = w

    def doPend(self, frt, pag, r, c, p, i, w):
        self.pend = w

    def doITots(self, frt, pag, r, c, p, i, w):
        self.itot = w

    def doEnd(self):
        self.df.closeProcess()
        self.emadd = self.df.repeml[2]
        if self.whole == "N":
            recs = getSingleRecords(self.opts["mf"],
                                    "lonmf1", ("lm1_acno", "lm1_name"),
                                    where=[("lm1_cono", "=",
                                            self.opts["conum"])])
        else:
            whr = [("lm1_cono", "=", self.opts["conum"])]
            if self.sort == "A":
                odr = "lm1_acno"
            else:
                odr = "lm1_name"
            recs = self.sql.getRec("lonmf1", where=whr, order=odr)
        if not recs:
            showError(self.opts["mf"].body, "Error", "No Accounts Selected")
        else:
            self.form = DrawForm(self.opts["mf"].dbm,
                                 self.tname,
                                 wrkdir=self.opts["mf"].rcdic["wrkdir"])
            self.doLoadStatic()
            self.form.doNewDetail()
            p = ProgressBar(self.opts["mf"].body, mxs=len(recs), esc=True)
            for num, rec in enumerate(recs):
                p.displayProgress(num)
                if p.quit:
                    break
                self.doProcess(rec)
            p.closeProgress()
            if p.quit or not self.form.page:
                pass
            elif self.df.repeml[1] == "N" or self.emadd:
                self.df.repeml[2] = self.emadd
                self.doPrint()
        self.opts["mf"].closeLoop()

    def doLoadStatic(self):
        cmc = self.sql.ctlmst_col
        ctm = self.sql.getRec("ctlmst",
                              where=[("ctm_cono", "=", self.opts["conum"])],
                              limit=1)
        for fld in cmc:
            dat = ctm[cmc.index(fld)]
            if fld in self.form.tptp:
                if fld == "ctm_logo":
                    self.form.letterhead(cmc, ctm, fld, dat)
                    continue
                self.form.tptp[fld][1] = dat
        if "letterhead" in self.form.tptp:
            self.form.letterhead(cmc, ctm, "letterhead", None)
        self.form.document_date(self.date.disp)
        self.form.bank_details(cmc, ctm, 0)

    def doProcess(self, lm1):
        l1c = self.sql.lonmf1_col
        tdc = self.form.sql.tpldet_col
        self.acno = lm1[l1c.index("lm1_acno")]
        self.emlto = lm1[l1c.index("lm1_email")]
        self.form.account_details("lm1", l1c, lm1, 1)
        for col in l1c:
            d = "%s_C00" % col
            if d in self.form.newdic:
                dat = lm1[l1c.index(col)]
                self.form.newdic[d][tdc.index("tpd_text")] = dat
        lonmf2 = self.sql.getRec("lonmf2",
                                 where=[("lm2_cono", "=", self.opts["conum"]),
                                        ("lm2_acno", "=", self.acno)],
                                 order="lm2_loan")
        for loan in lonmf2:
            self.doStatement(tdc, loan)

    def doStatement(self, tdc, lm2):
        l2c = self.sql.lonmf2_col
        ltc = copyList(self.sql.lontrn_col)
        self.loan = lm2[l2c.index("lm2_loan")]
        for col in l2c:
            d = "%s_C00" % col
            if d in self.form.newdic:
                dat = lm2[l2c.index(col)]
                self.form.newdic[d][tdc.index("tpd_text")] = dat
        if self.pend == "Y":
            # Raise Pending Interest
            LoanInterest("L",
                         self.opts["mf"].dbm,
                         lm2,
                         update="Y",
                         tdate=self.date.work,
                         batch="Pending",
                         curdt=self.curdt,
                         capnm="")
        # Get Transactions
        whr = [("lnt_cono", "=", self.opts["conum"]),
               ("lnt_acno", "=", self.acno), ("lnt_loan", "=", self.loan),
               ("lnt_curdt", "<=", self.eperw)]
        odr = "lnt_curdt, lnt_trdt, lnt_type, lnt_refno"
        if self.itot == "Y":
            w = whr[:]
            w.append(("lnt_type", "<>", 4))
            trns = self.sql.getRec("lontrn", where=w, order=odr)
            if self.capb == "A":  # Anniversary
                fcap = [lm2[l2c.index("lm2_start")], 0]
                if self.capf == "A":
                    fcap[1] = projectDate(fcap[0], 1, typ="years")
                else:
                    fcap[1] = projectDate(fcap[0], 6, typ="months")
            else:  # Financial
                periods = self.sql.getRec(
                    "ctlynd",
                    cols=["cye_period", "cye_start", "cye_end"],
                    where=[("cye_cono", "=", self.opts["conum"])],
                    order="cye_period")
                fcap = [periods[0][1], periods[0][2]]
                if self.capf == "B":  # Bi-Annual
                    fcap[1] = projectDate(fcap[1], -6, typ="months")
            capdt = [copyList(fcap)]
            while fcap[1] < self.date.work:
                if self.capf == "A":
                    fcap[0] = projectDate(fcap[0], 1, typ="years")
                    fcap[1] = projectDate(fcap[1], 1, typ="years")
                else:
                    fcap[0] = projectDate(fcap[0], 6, typ="months")
                    fcap[1] = projectDate(fcap[1], 6, typ="months")
                if fcap[1] <= self.date.work:
                    capdt.append(copyList(fcap))
            for capd in capdt:
                w = whr[:]
                w.append(("lnt_type", "=", 4))
                w.append(("lnt_trdt", "between", capd[0], capd[1]))
                ints = self.sql.getRec("lontrn", where=w, order=odr)
                if not ints:
                    continue
                ddes = "Dr Int %s to %s"
                cdes = "Cr Int %s to %s"
                dbal = 0
                cbal = 0
                for trn in ints:
                    amt = trn[ltc.index("lnt_tramt")]
                    if amt < 0:
                        cbal = float(ASD(cbal) + ASD(amt))
                    else:
                        dbal = float(ASD(dbal) + ASD(amt))
                if dbal:
                    trn[ltc.index("lnt_tramt")] = dbal
                    trn[ltc.index("lnt_desc")] = ddes % (CCD(
                        int(capd[0] / 100), "D2",
                        7).disp, CCD(int(capd[1] / 100), "D2", 7).disp)
                    trns.append(copyList(trn))
                if cbal:
                    trn[ltc.index("lnt_tramt")] = cbal
                    trn[ltc.index("lnt_desc")] = cdes % (CCD(
                        int(capd[0] / 100), "D2",
                        7).disp, CCD(int(capd[1] / 100), "D2", 7).disp)
                    trns.append(copyList(trn))
            trns = sorted(trns, key=itemgetter(5))
        else:
            trns = self.sql.getRec("lontrn", where=whr, order=odr)
        if not trns:
            return
        self.bal = 0
        self.tots = 0
        if self.sperw:
            obal = 0
            trans = copyList(trns)
            for trn in trans:
                tramt = trn[self.sql.lontrn_col.index("lnt_tramt")]
                if trn[self.sql.lontrn_col.index("lnt_curdt")] < self.sperw:
                    obal = float(ASD(obal) + ASD(tramt))
                    trns.remove(trn)
            trn[ltc.index("lnt_type")] = 3
            trn[ltc.index("lnt_trdt")] = (self.sperw * 100) + 1
            trn[ltc.index("lnt_refno")] = "O/Bal"
            trn[ltc.index("lnt_batch")] = ""
            trn[ltc.index("lnt_tramt")] = obal
            trn[ltc.index("lnt_desc")] = "Opening Balance"
            trn[ltc.index("lnt_batind")] = ""
            trns.insert(0, trn)
        trans = []
        for trn in trns:
            tramt = trn[ltc.index("lnt_tramt")]
            self.tots = float(ASD(self.tots) + ASD(tramt))
            if tramt < 0:
                trn.extend([0, tramt])
            else:
                trn.extend([tramt, 0])
            trans.append(trn)
        ltc.extend(["line_debit", "line_credit"])
        if self.zeros == "N" and not self.tots:
            return
        self.doBody(ltc, trans, tdc)
        self.doTotal(tdc)
        self.doTail(tdc)
        if self.pend == "Y":
            self.opts["mf"].dbm.rollbackDbase()
        if self.df.repeml[1] == "Y" and not self.emadd:
            self.df.repeml[2] = self.emlto
            self.doPrint()

    def doPrint(self):
        if self.df.repeml[1] == "Y" and not self.emadd:
            key = "%s_%s_%s" % (self.opts["conum"], self.acno, self.loan)
        else:
            key = "%s_all_all" % self.opts["conum"]
        pdfnam = getModName(self.opts["mf"].rcdic["wrkdir"],
                            self.__class__.__name__,
                            key,
                            ext="pdf")
        self.form.output(pdfnam, "F")
        doPrinter(mf=self.opts["mf"],
                  conum=self.opts["conum"],
                  pdfnam=pdfnam,
                  header="%s Statement at %s" %
                  (self.opts["conam"], self.date.disp),
                  repprt=self.df.repprt,
                  fromad=self.fromad,
                  repeml=self.df.repeml)
        if self.df.repeml[1] == "Y":
            self.form = DrawForm(self.opts["mf"].dbm,
                                 self.tname,
                                 wrkdir=self.opts["mf"].rcdic["wrkdir"])
            self.doLoadStatic()
            self.form.doNewDetail()

    def doBody(self, ltc, lnt, tdc):
        page = 0
        count = 0
        text = tdc.index("tpd_text")
        for trans in lnt:
            if not count:
                page += 1
                count = self.doHeader(page)
            if count == self.form.maxlines:
                page = self.doCfwd(page)
                count = self.doHeader(page)
            for cod in self.form.body:
                if cod == "type_code":
                    c = "lnt_type"
                elif cod == "line_paid":
                    c = "paid"
                else:
                    c = cod
                d = "%s_C%02i" % (cod, count)
                if cod == "type_code":
                    ttyp = trans[ltc.index(c)]
                    self.form.newdic[d][text] = lntrtp[ttyp - 1][0]
                elif c in ("line_debit", "line_credit"):
                    tramt = trans[ltc.index(c)]
                    self.bal = float(ASD(self.bal) + ASD(tramt))
                    self.form.newdic[d][text] = trans[ltc.index(c)]
                elif c == "line_balance":
                    self.form.newdic[d][text] = self.bal
                else:
                    self.form.newdic[d][text] = trans[ltc.index(c)]
                self.form.doDrawDetail(self.form.newdic[d])
            count += 1
        for x in range(count, self.form.maxlines):
            for cod in self.form.body:
                d = "%s_C%02i" % (cod, x)
                self.form.newdic[d][tdc.index("tpd_text")] = "BLANK"
                self.form.doDrawDetail(self.form.newdic[d])

    def doHeader(self, page):
        self.form.add_page()
        tdc = self.form.sql.tpldet_col
        for key in self.form.newkey:
            nl = copyList(self.form.newdic[key])
            if nl[tdc.index("tpd_place")] != "A":
                continue
            if nl[tdc.index("tpd_detseq")] == "lm1_acno_C00":
                nl[tdc.index("tpd_text")] = self.acno
            elif nl[tdc.index("tpd_detseq")] == "page_number_C00":
                nl[tdc.index("tpd_text")] = str(page)
            self.form.doDrawDetail(nl)
        return 0

    def doCfwd(self, page):
        if "carried_forward" in self.form.tptp:
            tdc = self.form.sql.tpldet_col
            line = copyList(self.form.cfwd)
            line[tdc.index("tpd_text")] = "Continued on Page %i" % (page + 1)
            self.form.doDrawDetail(line)
        return page + 1

    def doTotal(self, tdc):
        for c in self.form.total:
            t = "%s_T00" % c
            if c in self.form.newdic:
                self.form.doDrawDetail(self.form.newdic[c])
            elif t in self.form.newdic:
                self.form.doDrawDetail(self.form.newdic[t])
            d = "%s_C00" % c
            if d in self.form.newdic:
                line = self.form.newdic[d]
                if c == "total_balance":
                    line[tdc.index("tpd_text")] = self.tots
                self.form.doDrawDetail(line)

    def doTail(self, tdc):
        for c in self.form.tail:
            t = "%s_T00" % c
            if c in self.form.newdic:
                self.form.doDrawDetail(self.form.newdic[c])
            elif t in self.form.newdic:
                self.form.doDrawDetail(self.form.newdic[t])
            d = "%s_C00" % c
            if d in self.form.newdic:
                self.form.doDrawDetail(self.form.newdic[d])

    def doExit(self):
        self.df.closeProcess()
        self.opts["mf"].closeLoop()