Blame template.py

Ivan Mahonin ae689c
Ivan Mahonin ae689c
import os
Ivan Mahonin ae689c
import html
Ivan Mahonin ae689c
#import markdown
Ivan Mahonin ae689c
#os.path.dirname(os.path.abspath(__file__))
Ivan Mahonin ae689c
Ivan Mahonin ae689c
Ivan Mahonin ae689c
def dictGet(d, path):
Ivan Mahonin ae689c
    for k in str(path).split('.'):
Ivan Mahonin ae689c
        if type(d) is list or type(d) is tuple:
Ivan Mahonin ae689c
            d = d[int(k)]
Ivan Mahonin ae689c
            continue
Ivan Mahonin ae689c
        elif type(d) is dict:
Ivan Mahonin ae689c
            if (not k in d) and ('ex' in d):
Ivan Mahonin ae689c
                print("query ex for field: %s (%s)" % (path, k))
Ivan Mahonin ae689c
                d = d['ex'](d)
Ivan Mahonin ae689c
            if k in d:
Ivan Mahonin ae689c
                d = d[k]
Ivan Mahonin ae689c
                continue
Ivan Mahonin ae689c
        print("variable not found: %s (%s)" % (path, k))
Ivan Mahonin ae689c
        return None
Ivan Mahonin ae689c
    return d
Ivan Mahonin ae689c
Ivan Mahonin ae689c
def tostr(s):
Ivan Mahonin ae689c
    return '' if s is None else str(s) 
Ivan Mahonin ae689c
def text2html(t):
Ivan Mahonin ae689c
    return html.escape(tostr(t)).replace("\n", "
")
Ivan Mahonin ae689c
def md2html(t):
Ivan Mahonin ae689c
    return markdown.markdown(tostr(t))
Ivan Mahonin ae689c
Ivan Mahonin ae689c
Ivan Mahonin ae689c
tabsym = ' -- '
Ivan Mahonin ae689c
Ivan Mahonin ae689c
Ivan Mahonin ae689c
class TemplateText:
Ivan Mahonin ae689c
    def __init__(self, text = ''):
Ivan Mahonin ae689c
        self.text = text
Ivan Mahonin ae689c
    def write(self, writer, context):
Ivan Mahonin ae689c
        writer.write(self.text)
Ivan Mahonin ae689c
    def optimize(self):
Ivan Mahonin ae689c
        return self if self.text else None
Ivan Mahonin ae689c
    def dbgPrint(self, tab):
Ivan Mahonin ae689c
        print("%stext(%s)" % (tab, self.text.replace("\n", "\\n")))
Ivan Mahonin ae689c
Ivan Mahonin ae689c
class TemplateVarHtml:
Ivan Mahonin ae689c
    def __init__(self, varpath = None):
Ivan Mahonin ae689c
        self.varpath = varpath
Ivan Mahonin ae689c
    def write(self, writer, context):
Ivan Mahonin ae689c
        writer.write(tostr(dictGet( context, self.varpath )))
Ivan Mahonin ae689c
    def optimize(self):
Ivan Mahonin ae689c
        return self
Ivan Mahonin ae689c
    def dbgPrint(self, tab):
Ivan Mahonin ae689c
        print("%svarHtml(%s)" % (tab, self.varpath))
Ivan Mahonin ae689c
Ivan Mahonin ae689c
class TemplateVarMd:
Ivan Mahonin ae689c
    def __init__(self, varpath = None):
Ivan Mahonin ae689c
        self.varpath = varpath
Ivan Mahonin ae689c
    def write(self, writer, context):
Ivan Mahonin ae689c
        writer.write(md2html(dictGet( context, self.varpath )))
Ivan Mahonin ae689c
    def optimize(self):
Ivan Mahonin ae689c
        return self
Ivan Mahonin ae689c
    def dbgPrint(self, tab):
Ivan Mahonin ae689c
        print("%svarMd(%s)" % (tab, self.varpath))
Ivan Mahonin ae689c
Ivan Mahonin ae689c
class TemplateVarText:
Ivan Mahonin ae689c
    def __init__(self, varpath = None):
Ivan Mahonin ae689c
        self.varpath = varpath
Ivan Mahonin ae689c
    def write(self, writer, context):
Ivan Mahonin ae689c
        writer.write(text2html(dictGet( context, self.varpath )))
Ivan Mahonin ae689c
    def optimize(self):
Ivan Mahonin ae689c
        return self
Ivan Mahonin ae689c
    def dbgPrint(self, tab):
Ivan Mahonin ae689c
        print("%svarText(%s)" % (tab, self.varpath))
Ivan Mahonin ae689c
Ivan Mahonin ae689c
class TemplateVarTextMultiline:
Ivan Mahonin ae689c
    def __init__(self, varpath = None):
Ivan Mahonin ae689c
        self.varpath = varpath
Ivan Mahonin ae689c
    def write(self, writer, context):
Ivan Mahonin ae689c
        writer.write(text2html(dictGet( context, self.varpath )).replace("\n", "
"))
Ivan Mahonin ae689c
    def optimize(self):
Ivan Mahonin ae689c
        return self
Ivan Mahonin ae689c
    def dbgPrint(self, tab):
Ivan Mahonin ae689c
        print("%svarTextMultiline(%s)" % (tab, self.varpath))
Ivan Mahonin ae689c
Ivan Mahonin ae689c
class TemplateVarCount:
Ivan Mahonin ae689c
    def __init__(self, varpath = None):
Ivan Mahonin ae689c
        self.varpath = varpath
Ivan Mahonin ae689c
    def write(self, writer, context):
Ivan Mahonin ae689c
        v = dictGet( context, self.varpath )
Ivan Mahonin ae689c
        writer.write(str(len(v) if hasattr(v, '__len__') else 0))
Ivan Mahonin ae689c
    def optimize(self):
Ivan Mahonin ae689c
        return self
Ivan Mahonin ae689c
    def dbgPrint(self, tab):
Ivan Mahonin ae689c
        print("%svarCount(%s)" % (tab, self.varpath))
Ivan Mahonin ae689c
Ivan Mahonin ae689c
class TemplateVarField:
Ivan Mahonin ae689c
    def __init__(self, varpath = None):
Ivan Mahonin ae689c
        self.varpath = varpath
Ivan Mahonin ae689c
    def write(self, writer, context):
Ivan Mahonin ae689c
        f = self.varpath.split('.')[-1]
Ivan Mahonin ae689c
        writer.write("

%s: %s

" % (
Ivan Mahonin ae689c
            text2html( f ),
Ivan Mahonin ae689c
            text2html( dictGet(context, self.varpath) ) ))
Ivan Mahonin ae689c
    def optimize(self):
Ivan Mahonin ae689c
        return self
Ivan Mahonin ae689c
    def dbgPrint(self, tab):
Ivan Mahonin ae689c
        print("%svarField(%s)" % (tab, self.varpath))
Ivan Mahonin ae689c
Ivan Mahonin ae689c
class TemplateIf:
Ivan Mahonin ae689c
    def __init__(self, varpath = None, sub = None, alt = None):
Ivan Mahonin ae689c
        self.varpath = varpath
Ivan Mahonin ae689c
        self.sub = sub
Ivan Mahonin ae689c
        self.alt = alt
Ivan Mahonin ae689c
    def write(self, writer, context):
Ivan Mahonin ae689c
        if dictGet(context, self.varpath):
Ivan Mahonin ae689c
            if self.sub: self.sub.write(writer, context)
Ivan Mahonin ae689c
        else:
Ivan Mahonin ae689c
            if self.alt: self.alt.write(writer, context)
Ivan Mahonin ae689c
    def optimize(self):
Ivan Mahonin ae689c
        self.sub = self.sub.optimize() if self.sub else None
Ivan Mahonin ae689c
        self.alt = self.alt.optimize() if self.alt else None
Ivan Mahonin ae689c
        return self if self.sub or self.alt else None
Ivan Mahonin ae689c
    def dbgPrint(self, tab):
Ivan Mahonin ae689c
        print("%sif(%s):" % (tab, self.varpath))
Ivan Mahonin ae689c
        if self.sub:
Ivan Mahonin ae689c
            self.sub.dbgPrint(tab + tabsym)
Ivan Mahonin ae689c
        if self.alt:
Ivan Mahonin ae689c
            print("%selse:" % tab)
Ivan Mahonin ae689c
            self.alt.dbgPrint(tab + tabsym)
Ivan Mahonin ae689c
Ivan Mahonin ae689c
Ivan Mahonin ae689c
class TemplateWith:
Ivan Mahonin ae689c
    def __init__(self, varpath = None, varname = None, sub = None):
Ivan Mahonin ae689c
        self.varpath = varpath
Ivan Mahonin ae689c
        self.varname = varname
Ivan Mahonin ae689c
        self.sub = sub
Ivan Mahonin ae689c
    def write(self, writer, context):
Ivan Mahonin ae689c
        if self.sub:
Ivan Mahonin ae689c
            context = dict(context)
Ivan Mahonin ae689c
            context[self.varname] = dictGet(context, self.varpath)
Ivan Mahonin ae689c
            self.sub.write(writer, context)
Ivan Mahonin ae689c
    def optimize(self):
Ivan Mahonin ae689c
        self.sub = self.sub.optimize() if self.sub else None
Ivan Mahonin ae689c
        return self if self.sub else None
Ivan Mahonin ae689c
    def dbgPrint(self, tab):
Ivan Mahonin ae689c
        print("%swith(%s:%s):" % (tab, self.varpath, self.varname))
Ivan Mahonin ae689c
        if self.sub: self.sub.dbgPrint(tab + tabsym)
Ivan Mahonin ae689c
Ivan Mahonin ae689c
Ivan Mahonin ae689c
class TemplateComment:
Ivan Mahonin ae689c
    def __init__(self, text = None):
Ivan Mahonin ae689c
        self.text = text
Ivan Mahonin ae689c
    def write(self, writer, context):
Ivan Mahonin ae689c
        pass
Ivan Mahonin ae689c
    def optimize(self):
Ivan Mahonin ae689c
        return None
Ivan Mahonin ae689c
    def dbgPrint(self, tab):
Ivan Mahonin ae689c
        print("%scomment(%s)" % (texttab, self.text))
Ivan Mahonin ae689c
Ivan Mahonin ae689c
Ivan Mahonin ae689c
class TemplateLoop:
Ivan Mahonin ae689c
    def __init__(self, varpath = None, keyvarname = None, varname = None, sub = None, sep = None):
Ivan Mahonin ae689c
        self.varpath = varpath
Ivan Mahonin ae689c
        self.keyvarname = keyvarname
Ivan Mahonin ae689c
        self.varname = varname
Ivan Mahonin ae689c
        self.sub = sub
Ivan Mahonin ae689c
        self.sep = sep
Ivan Mahonin ae689c
    def writeItem(self, writer, context, first, k, v):
Ivan Mahonin ae689c
        if self.sep and not first:
Ivan Mahonin ae689c
            self.sep.write(writer, context)
Ivan Mahonin ae689c
        if self.sub:
Ivan Mahonin ae689c
            ctx = dict(context)
Ivan Mahonin ae689c
            ctx[self.keyvarname] = k
Ivan Mahonin ae689c
            ctx[self.varname] = v
Ivan Mahonin ae689c
            self.sub.write(writer, ctx)
Ivan Mahonin ae689c
    def write(self, writer, context):
Ivan Mahonin ae689c
        if self.sep or self.sub:
Ivan Mahonin ae689c
            vv = dictGet(context, self.varpath)
Ivan Mahonin ae689c
            if type(vv) is dict:
Ivan Mahonin ae689c
                f = True
Ivan Mahonin ae689c
                keys = list(vv.keys())
Ivan Mahonin ae689c
                keys.sort()
Ivan Mahonin ae689c
                for k in keys:
Ivan Mahonin ae689c
                    self.writeItem(writer, context, f, k, vv[k])
Ivan Mahonin ae689c
                    f = False
Ivan Mahonin ae689c
            elif hasattr(vv, '__iter__'):
Ivan Mahonin ae689c
                idx = 0
Ivan Mahonin ae689c
                for v in vv:
Ivan Mahonin ae689c
                    self.writeItem(writer, context, not idx, idx, v)
Ivan Mahonin ae689c
                    idx = idx + 1
Ivan Mahonin ae689c
    def optimize(self):
Ivan Mahonin ae689c
        self.sub = self.sub.optimize() if self.sub else None
Ivan Mahonin ae689c
        self.sep = self.sep.optimize() if self.sep else None
Ivan Mahonin ae689c
        return self if self.sub or self.sep else None
Ivan Mahonin ae689c
    def dbgPrint(self, tab):
Ivan Mahonin ae689c
        print("%sloop(%s:%s:%s):" % (tab, self.varpath, self.keyvarname, self.varname))
Ivan Mahonin ae689c
        if self.sub:
Ivan Mahonin ae689c
            self.sub.dbgPrint(tab + tabsym)
Ivan Mahonin ae689c
        if self.sep:
Ivan Mahonin ae689c
            print("%ssep:" % tab)
Ivan Mahonin ae689c
            self.sep.dbgPrint(tab + tabsym)
Ivan Mahonin ae689c
Ivan Mahonin ae689c
class Template:
Ivan Mahonin ae689c
    def __init__(self):
Ivan Mahonin ae689c
        self.items = []
Ivan Mahonin ae689c
    def write(self, writer, context):
Ivan Mahonin ae689c
        for i in self.items:
Ivan Mahonin ae689c
            i.write(writer, context)
Ivan Mahonin ae689c
    def optimize(self):
Ivan Mahonin ae689c
        it = []
Ivan Mahonin ae689c
        for i in self.items:
Ivan Mahonin ae689c
            ii = i.optimize()
Ivan Mahonin ae689c
            if ii:
Ivan Mahonin ae689c
                if it and type(ii) is TemplateText and type(it[-1]) is TemplateText:
Ivan Mahonin ae689c
                    it[-1].text = it[-1].text + ii.text
Ivan Mahonin ae689c
                else:
Ivan Mahonin ae689c
                    it.append(ii)
Ivan Mahonin ae689c
        self.items = it
Ivan Mahonin ae689c
        if len(self.items) == 1: return self.items[0]
Ivan Mahonin ae689c
        return self if self.items else None
Ivan Mahonin ae689c
    def dbgPrint(self, tab):
Ivan Mahonin ae689c
        print("%stemplate:" % tab)
Ivan Mahonin ae689c
        for i in self.items:
Ivan Mahonin ae689c
            i.dbgPrint(tab + tabsym)
Ivan Mahonin ae689c
Ivan Mahonin ae689c
Ivan Mahonin ae689c
class TplLoader:
Ivan Mahonin ae689c
    @staticmethod
Ivan Mahonin ae689c
    def loadtext(filename):
Ivan Mahonin ae689c
        filename = os.path.abspath(filename)
Ivan Mahonin ae689c
        path = os.path.dirname(filename)
Ivan Mahonin ae689c
        res = ''
Ivan Mahonin ae689c
        text = ''
Ivan Mahonin ae689c
        with open(filename, 'r') as f: text = f.read()
Ivan Mahonin ae689c
        ii = 0
Ivan Mahonin ae689c
        i = 0
Ivan Mahonin ae689c
        while i < len(text):
Ivan Mahonin ae689c
            if text[i:i+9] == '{include:':
Ivan Mahonin ae689c
                res = res + text[ii:i]
Ivan Mahonin ae689c
                a = i+9
Ivan Mahonin ae689c
                b = text.find('}', a)
Ivan Mahonin ae689c
                if b<0: raise Exception("include parse error: %s:%d" % (filename, a))
Ivan Mahonin ae689c
                fn = text[a:b]
Ivan Mahonin ae689c
                res = res + TplLoader.loadtext(path +'/' + fn)
Ivan Mahonin ae689c
                i = b+1
Ivan Mahonin ae689c
                ii = i
Ivan Mahonin ae689c
            else:
Ivan Mahonin ae689c
                i = i + 1
Ivan Mahonin ae689c
        return res + text[ii:i]
Ivan Mahonin ae689c
Ivan Mahonin ae689c
    def __init__(self, filename):
Ivan Mahonin ae689c
        self.filename = os.path.abspath(filename)
Ivan Mahonin ae689c
        self.text = TplLoader.loadtext(self.filename)
Ivan Mahonin ae689c
        self.ptr = 0
Ivan Mahonin ae689c
Ivan Mahonin ae689c
    def error(self):
Ivan Mahonin ae689c
        with open('tplerr.txt', 'w') as f: f.write(self.text)
Ivan Mahonin ae689c
        raise Exception("parse error: %s:%d" % (self.filename, self.ptr))
Ivan Mahonin ae689c
Ivan Mahonin ae689c
    def readKey(self, k):
Ivan Mahonin ae689c
        if self.text[self.ptr:self.ptr + len(k)] == k:
Ivan Mahonin ae689c
            self.ptr = self.ptr + len(k)
Ivan Mahonin ae689c
            return True
Ivan Mahonin ae689c
        return False
Ivan Mahonin ae689c
Ivan Mahonin ae689c
    def readVarname(self):
Ivan Mahonin ae689c
        i = self.ptr
Ivan Mahonin ae689c
        while i < len(self.text) and (self.text[i].isalnum() or self.text[i] in '_'):
Ivan Mahonin ae689c
            i = i + 1
Ivan Mahonin ae689c
        if i == self.ptr: return None
Ivan Mahonin ae689c
        i, self.ptr = self.ptr, i
Ivan Mahonin ae689c
        return self.text[i:self.ptr]
Ivan Mahonin ae689c
Ivan Mahonin ae689c
    def readVarpath(self):
Ivan Mahonin ae689c
        i = self.ptr
Ivan Mahonin ae689c
        varpath = None
Ivan Mahonin ae689c
        while True:
Ivan Mahonin ae689c
            varname = self.readVarname()
Ivan Mahonin ae689c
            if not varname:
Ivan Mahonin ae689c
                if varpath: self.error()
Ivan Mahonin ae689c
                break
Ivan Mahonin ae689c
            varpath = varpath + '.' + varname if varpath else varname
Ivan Mahonin ae689c
            if not self.readKey('.'): break
Ivan Mahonin ae689c
        if not varpath:
Ivan Mahonin ae689c
            self.ptr = i
Ivan Mahonin ae689c
        return varpath
Ivan Mahonin ae689c
Ivan Mahonin ae689c
    def loadVarText(self):
Ivan Mahonin ae689c
        if not self.readKey("{:"): return None
Ivan Mahonin ae689c
        varpath = self.readVarpath()
Ivan Mahonin ae689c
        if not varpath or not self.readKey("}"): self.error()
Ivan Mahonin ae689c
        return TemplateVarText(varpath)
Ivan Mahonin ae689c
Ivan Mahonin ae689c
    def loadVarTextMultiline(self):
Ivan Mahonin ae689c
        if not self.readKey("{t:"): return None
Ivan Mahonin ae689c
        varpath = self.readVarpath()
Ivan Mahonin ae689c
        if not varpath or not self.readKey("}"): self.error()
Ivan Mahonin ae689c
        return TemplateVarTextMultiline(varpath)
Ivan Mahonin ae689c
Ivan Mahonin ae689c
    def loadVarHtml(self):
Ivan Mahonin ae689c
        if not self.readKey("{html:"): return None
Ivan Mahonin ae689c
        varpath = self.readVarpath()
Ivan Mahonin ae689c
        if not varpath or not self.readKey("}"): self.error()
Ivan Mahonin ae689c
        return TemplateVarHtml(varpath)
Ivan Mahonin ae689c
Ivan Mahonin ae689c
    def loadVarMd(self):
Ivan Mahonin ae689c
        return None # disabled
Ivan Mahonin ae689c
        if not self.readKey("{md:"): return None
Ivan Mahonin ae689c
        varpath = self.readVarpath()
Ivan Mahonin ae689c
        if not varpath or not self.readKey("}"): self.error()
Ivan Mahonin ae689c
        return TemplateVarMd(varpath)
Ivan Mahonin ae689c
Ivan Mahonin ae689c
    def loadVarCount(self):
Ivan Mahonin ae689c
        if not self.readKey("{count:"): return None
Ivan Mahonin ae689c
        varpath = self.readVarpath()
Ivan Mahonin ae689c
        if not varpath or not self.readKey("}"): self.error()
Ivan Mahonin ae689c
        return TemplateVarCount(varpath)
Ivan Mahonin ae689c
Ivan Mahonin ae689c
    def loadVarField(self):
Ivan Mahonin ae689c
        if not self.readKey("{f:"): return None
Ivan Mahonin ae689c
        varpath = self.readVarpath()
Ivan Mahonin ae689c
        if not varpath or not self.readKey("}"): self.error()
Ivan Mahonin ae689c
        return TemplateVarField(varpath)
Ivan Mahonin ae689c
Ivan Mahonin ae689c
    def loadIf(self):
Ivan Mahonin ae689c
        if not self.readKey("{if:"): return None
Ivan Mahonin ae689c
        varpath = self.readVarpath()
Ivan Mahonin ae689c
        if not varpath or not self.readKey("}"): self.error()
Ivan Mahonin ae689c
        res = TemplateIf(varpath, Template(), Template())
Ivan Mahonin ae689c
        e = False
Ivan Mahonin ae689c
        while True:
Ivan Mahonin ae689c
            if self.readKey("{endif}"): break
Ivan Mahonin ae689c
            if self.readKey("{else}"):
Ivan Mahonin ae689c
                if e: self.error()
Ivan Mahonin ae689c
                e = True
Ivan Mahonin ae689c
                continue
Ivan Mahonin ae689c
            item = self.loadTemplate()
Ivan Mahonin ae689c
            if not item: self.error()
Ivan Mahonin ae689c
            if e:
Ivan Mahonin ae689c
                res.alt.items.append(item)
Ivan Mahonin ae689c
            else:
Ivan Mahonin ae689c
                res.sub.items.append(item)
Ivan Mahonin ae689c
        return res
Ivan Mahonin ae689c
Ivan Mahonin ae689c
    def loadWith(self):
Ivan Mahonin ae689c
        if not self.readKey("{with:"): return None
Ivan Mahonin ae689c
        varpath = self.readVarpath()
Ivan Mahonin ae689c
        if not varpath or not self.readKey(":"): self.error()
Ivan Mahonin ae689c
        varname = self.readVarname()
Ivan Mahonin ae689c
        if not varname or not self.readKey("}"): self.error()
Ivan Mahonin ae689c
        res = TemplateWith(varpath, varname, Template())
Ivan Mahonin ae689c
        while True:
Ivan Mahonin ae689c
            if self.readKey("{endwith}"): break
Ivan Mahonin ae689c
            item = self.loadTemplate()
Ivan Mahonin ae689c
            if not item: self.error()
Ivan Mahonin ae689c
            res.sub.items.append(item)
Ivan Mahonin ae689c
        return res
Ivan Mahonin ae689c
Ivan Mahonin ae689c
    def loadComment(self):
Ivan Mahonin ae689c
        if not self.readKey("{comment}"): return None
Ivan Mahonin ae689c
        res = TemplateComment()
Ivan Mahonin ae689c
        i = self.text.find('{endcomment}', self.ptr)
Ivan Mahonin ae689c
        if i < 0:
Ivan Mahonin ae689c
            i = len(self.text)
Ivan Mahonin ae689c
        res = TemplateComment(self.text[self.ptr:i])
Ivan Mahonin ae689c
        self.ptr = i
Ivan Mahonin ae689c
        if not self.readKey("{endcomment}"): self.error()
Ivan Mahonin ae689c
        return res
Ivan Mahonin ae689c
Ivan Mahonin ae689c
    def loadLoop(self):
Ivan Mahonin ae689c
        if not self.readKey("{loop:"): return None
Ivan Mahonin ae689c
        varpath = self.readVarpath()
Ivan Mahonin ae689c
        if not varpath or not self.readKey(":"): self.error()
Ivan Mahonin ae689c
        keyvarname = self.readVarname()
Ivan Mahonin ae689c
        if not self.readKey(":"): self.error()
Ivan Mahonin ae689c
        varname = self.readVarname()
Ivan Mahonin ae689c
        if not varname or not self.readKey("}"): self.error()
Ivan Mahonin ae689c
        res = TemplateLoop(varpath, keyvarname, varname, Template(), Template())
Ivan Mahonin ae689c
        s = False
Ivan Mahonin ae689c
        while True:
Ivan Mahonin ae689c
            if self.readKey("{endloop}"): break
Ivan Mahonin ae689c
            if self.readKey("{sep}"):
Ivan Mahonin ae689c
                if s: self.error()
Ivan Mahonin ae689c
                s = True
Ivan Mahonin ae689c
                continue
Ivan Mahonin ae689c
            item = self.loadTemplate()
Ivan Mahonin ae689c
            if not item: self.error()
Ivan Mahonin ae689c
            if s:
Ivan Mahonin ae689c
                res.sep.items.append(item)
Ivan Mahonin ae689c
            else:
Ivan Mahonin ae689c
                res.sub.items.append(item)
Ivan Mahonin ae689c
        return res
Ivan Mahonin ae689c
Ivan Mahonin ae689c
    def loadTemplate(self):
Ivan Mahonin ae689c
        t = self.loadVarText()
Ivan Mahonin ae689c
        if t: return t
Ivan Mahonin ae689c
        t = self.loadVarTextMultiline()
Ivan Mahonin ae689c
        if t: return t
Ivan Mahonin ae689c
        t = self.loadVarHtml()
Ivan Mahonin ae689c
        if t: return t
Ivan Mahonin ae689c
        t = self.loadVarMd()
Ivan Mahonin ae689c
        if t: return t
Ivan Mahonin ae689c
        t = self.loadVarCount()
Ivan Mahonin ae689c
        if t: return t
Ivan Mahonin ae689c
        t = self.loadVarField()
Ivan Mahonin ae689c
        if t: return t
Ivan Mahonin ae689c
        t = self.loadIf()
Ivan Mahonin ae689c
        if t: return t
Ivan Mahonin ae689c
        t = self.loadWith()
Ivan Mahonin ae689c
        if t: return t
Ivan Mahonin ae689c
        t = self.loadComment()
Ivan Mahonin ae689c
        if t: return t
Ivan Mahonin ae689c
        t = self.loadLoop()
Ivan Mahonin ae689c
        if t: return t
Ivan Mahonin ae689c
Ivan Mahonin ae689c
        i = self.text.find('{', self.ptr)
Ivan Mahonin ae689c
        if i == self.ptr:
Ivan Mahonin ae689c
            i = self.text.find('{', self.ptr+1)
Ivan Mahonin ae689c
        if i < 0:
Ivan Mahonin ae689c
            i = len(self.text)
Ivan Mahonin ae689c
        if i <= self.ptr:
Ivan Mahonin ae689c
            return None
Ivan Mahonin ae689c
        i, self.ptr = self.ptr, i
Ivan Mahonin ae689c
        return TemplateText(self.text[i:self.ptr])
Ivan Mahonin ae689c
Ivan Mahonin ae689c
    @staticmethod
Ivan Mahonin ae689c
    def load(filename):
Ivan Mahonin ae689c
        l = TplLoader(filename)
Ivan Mahonin ae689c
        t = Template()
Ivan Mahonin ae689c
        while True:
Ivan Mahonin ae689c
            tt = l.loadTemplate()
Ivan Mahonin ae689c
            if not tt: break
Ivan Mahonin ae689c
            t.items.append(tt)
Ivan Mahonin ae689c
        if l.ptr < len(l.text): l.error()
Ivan Mahonin ae689c
        t = t.optimize()
Ivan Mahonin ae689c
        return t if t else TemplateText()