~tieong/notjinja2

fdd2e4ea89dc48eaa777dbbd0bd0132afb080fa9 — Thomas Ieong 1 year, 7 months ago b11390b
Get rid of inside_loop flag
1 files changed, 14 insertions(+), 41 deletions(-)

M notjinja2.py
M notjinja2.py => notjinja2.py +14 -41
@@ 1,12 1,12 @@
#!/usr/bin/env python3
# -*- coding: utf-8 -*-


"""
Simple template engine with a jinja syntax.
"""

import re
import pdb
from keyword import iskeyword

TOKENS = re.compile(r"(?s)({%.*?%}|{#.*?#}|{{.*?}})")


@@ 18,7 18,6 @@ class Template:
    def __init__(self, code, globs):
        self.code = ""
        self.globs = globs
        self.inside_loop = False

        self.add_line("def template_render(data=None):")
        self.indent()


@@ 38,13 37,11 @@ class Template:
                elif is_loop:
                    self.parse_loop(split_token)
                else:
                    pass
                    raise ValueError("Unknown control structure!")
                if self.buffer and (is_conditional or is_loop):
                    self.add_line(" ".join(self.buffer) + ":")
                    self.indent()
                    self.buffer.clear()
                    if is_loop:
                        self.inside_loop = True
            elif token.startswith("{{"):
                item = str(self.do_dots(str(split_token[1]).replace("\n", "")))
                self.add_line("output += {}".format(item))


@@ 61,12 58,7 @@ class Template:
    def do_dots(self, token):
        data = ""

        if "." in token and not self.inside_loop:
            split_token = token.split(".")
            data = "data['{}'].{}".format(split_token[0], split_token[1])
        elif token.isidentifier() and not self.inside_loop:
            data = "data['{}']".format(token)
        elif "|" in token:
        if "|" in token:
            split_token = token.split("|")
            name = self.globs["format_price"].__qualname__
            dot_split = token.split(".")


@@ 76,6 68,17 @@ class Template:
                )
            else:
                data = "data['{}']({})".format(split_token[1], split_token[0])
        elif "." in token:
            split_token = token.split(".")
            if split_token[0] in self.globs:
                data = "data['{}'].{}".format(split_token[0], split_token[1])
            else:
                data = token
        elif token.isidentifier():
            if token in self.globs:
                data = "data['{}']".format(token)
            else:
                data = token
        else:
            data = token



@@ 89,7 92,6 @@ class Template:
                self.buffer.append(token)
            elif token == "endfor":
                self.dedent()
                self.inside_loop = False
            elif token == tokens[-2]:
                self.buffer.append("data['{}']".format(token))
            else:


@@ 121,32 123,3 @@ class Template:
    def render(self):
        exec(self.code)
        return eval("template_render")(self.globs)


if __name__ == "__main__":
    class User:
        def __init__(self, is_logged_in, name):
            self.is_logged_in = is_logged_in
            self.name = name

    class Product:
        def __init__(self, name, price):
            self.name = name
            self.price = price

        def format_price(self, price):
            return str(price) + "0"

    with open("templates/depth.html", encoding="utf-8") as f:
        template = Template(
            f.read(),
            {
                "user": User(True, "Donald"),
                "product_list": [Product("foo", 10), Product("boo", 20)],
                "format_price": Product.format_price,
                "priority": "HIGH",
                "priority_low": "LOW",
                "data": {"HIGH": 1, "MID": 2, "LOW": 3},
            },
        )
        result = template.render()