# HG changeset patch
# User cmlenz
# Date 1236936890 0
# Node ID 8ebccfa9a9fe3f69f61609748c58a3df02d16238
# Parent abb1f1d2f4f31b0e13d581704d4e75acbf4841a9
inline branch: Add code block support to the template inliner, and some tweaks/cleanup.
diff --git a/examples/bench/bigtable.py b/examples/bench/bigtable.py
--- a/examples/bench/bigtable.py
+++ b/examples/bench/bigtable.py
@@ -9,8 +9,10 @@
import sys
import timeit
from StringIO import StringIO
+
from genshi.builder import tag
-from genshi.template import MarkupTemplate, NewTextTemplate
+from genshi.core import Stream
+from genshi.template import Context, MarkupTemplate, NewTextTemplate
try:
from elementtree import ElementTree as et
@@ -55,6 +57,7 @@
""")
+genshi_tmpl_compiled = genshi_tmpl.compile()
genshi_tmpl2 = MarkupTemplate("""
@@ -103,6 +106,11 @@
stream = genshi_tmpl.generate(table=table)
stream.render('html', strip_whitespace=False)
+def test_genshi_compiled():
+ """Genshi template, compiled to Python"""
+ stream = Stream(genshi_tmpl_compiled.generate(Context(table=table)))
+ stream.render('html', strip_whitespace=False)
+
def test_genshi_text():
"""Genshi text template"""
stream = genshi_text_tmpl.generate(table=table)
@@ -196,9 +204,10 @@
def run(which=None, number=10):
- tests = ['test_builder', 'test_genshi', 'test_genshi_text',
- 'test_genshi_builder', 'test_mako', 'test_kid', 'test_kid_et',
- 'test_et', 'test_cet', 'test_clearsilver', 'test_django']
+ tests = ['test_builder', 'test_genshi', 'test_genshi_compiled',
+ 'test_genshi_text', 'test_genshi_builder', 'test_mako',
+ 'test_kid', 'test_kid_et', 'test_et', 'test_cet',
+ 'test_clearsilver', 'test_django']
if which:
tests = filter(lambda n: n[5:] in which, tests)
diff --git a/genshi/template/inline.py b/genshi/template/inline.py
--- a/genshi/template/inline.py
+++ b/genshi/template/inline.py
@@ -15,7 +15,7 @@
from genshi.core import Attrs, Stream, _ensure, START, END, TEXT
from genshi.template.astutil import _ast
-from genshi.template.base import EXPR, SUB
+from genshi.template.base import EXEC, EXPR, SUB
from genshi.template.directives import *
@@ -45,22 +45,28 @@
# characters
if isinstance(obj, basestring):
yield TEXT, obj, pos
+ elif isinstance(obj, (int, float, long)):
+ yield TEXT, unicode(obj), pos
elif hasattr(obj, '__iter__'):
for event in _ensure(obj):
yield event
else:
yield TEXT, unicode(obj), pos
+
def _expand_text(obj):
if obj is not None:
if isinstance(obj, basestring):
return [obj]
+ elif isinstance(obj, (int, float, long)):
+ return [unicode(result)]
elif hasattr(obj, '__iter__'):
return [e[1] for e in _ensure(obj) if e[0] is TEXT]
else:
return [unicode(obj)]
return []
+
def _assign(ast):
buf = []
def _build(node, indices):
@@ -72,17 +78,19 @@
_build(ast, ())
return '{%s}' % ', '.join(buf)
+
def inline(template):
w = CodeWriter()
yield w('from genshi.core import Attrs, QName')
- yield w('from genshi.core import START, START_NS, END, END_NS, DOCTYPE, TEXT')
+ yield w('from genshi.core import START, START_CDATA, START_NS, END, '
+ 'END_CDATA, END_NS, DOCTYPE, TEXT')
yield w('from genshi.path import Path')
- yield w('from genshi.template.eval import Expression')
+ yield w('from genshi.template.eval import Expression, Suite')
yield w('from genshi.template.inline import _expand, _expand_text')
yield w()
- def _predecl_vars(stream):
+ def _declare_vars(stream):
for kind, data, pos in stream:
if kind is START:
@@ -103,6 +111,9 @@
elif kind is EXPR:
yield 'E', data, data
+ elif kind is EXEC:
+ yield 'S', data, data
+
elif kind is SUB:
directives, substream = data
for directive in directives:
@@ -117,24 +128,24 @@
elif hasattr(directive, 'path') and directive.path:
yield 'P', directive.path, directive.path
- for line in _predecl_vars(substream):
+ for line in _declare_vars(substream):
yield line
- def _predecl_defs(stream):
+ def _declare_functions(stream, names):
for kind, data, pos in stream:
if kind is SUB:
directives, substream = data
for idx, directive in enumerate(directives):
if isinstance(directive, DefDirective):
- defs.append(directive.name)
+ names.append(directive.name)
yield w('def %s:', directive.signature)
w.shift()
args = ['%r: %s' % (name, name) for name
in directive.args]
- yield w('ctxt.push({%s})', ', '.join(args))
+ yield w('push({%s})', ', '.join(args))
for line in _apply(directives[idx + 1:], substream):
yield line
- yield w('ctxt.pop()')
+ yield w('pop()')
w.unshift()
# Recursively apply directives
@@ -156,10 +167,10 @@
if isinstance(d, ForDirective):
yield w('for v in e[%d].evaluate(ctxt):', index['E'][d.expr])
w.shift()
- yield w('ctxt.push(%s)', _assign(d.target))
+ yield w('push(%s)', _assign(d.target))
for line in _apply(rest, stream):
yield line
- yield w('ctxt.pop()')
+ yield w('pop()')
w.unshift()
elif isinstance(d, IfDirective):
@@ -182,6 +193,9 @@
yield w('for evt in _expand(e[%d].evaluate(ctxt), (f, %d, %d)): yield evt',
index['E'][data], *pos[1:])
+ elif kind is EXEC:
+ yield w('s[%d].execute(ctxt)', index['S'][data])
+
elif kind is START:
tagname, attrs = data
qn = index['Q'][tagname]
@@ -225,9 +239,9 @@
yield w('_F = %r', template.filename)
yield w()
- yield '# predeclare qnames, attributes, and expressions'
+ yield '# Create qnames, attributes, expressions, and suite objects'
index, counter, values = {}, {}, {}
- for prefix, key, value in _predecl_vars(template.stream):
+ for prefix, key, value in _declare_vars(template.stream):
if not prefix in counter:
counter[prefix] = 0
if key not in index.get(prefix, ()):
@@ -243,16 +257,17 @@
yield w('def generate(ctxt, %s):',
', '.join(['f=_F'] + ['%s=_%s' % (n.lower(), n) for n in index]))
+ w.shift()
+ yield w('push = ctxt.push; pop = ctxt.pop')
yield w()
- w.shift()
# Define macro functions
defs = []
- for line in _predecl_defs(template.stream):
+ for line in _declare_functions(template.stream, names=defs):
yield line
if defs:
yield w()
- yield w('ctxt.push({%s})', ', '.join(['%r: %s' % (n, n) for n in defs]))
+ yield w('push({%s})', ', '.join('%r: %s' % (n, n) for n in defs))
yield w()
ei, pi = [0], [0]
@@ -264,12 +279,13 @@
import timeit
from genshi.template import Context, MarkupTemplate
- text = """
-
+
Hello, $name!
@@ -293,12 +309,12 @@
print
print 'Interpreted template:'
- print tmpl.generate(ctxt)
+ print tmpl.generate(ctxt).render('html')
print
print 'Executed module:'
module = tmpl.compile()
- print Stream(module.generate(ctxt))
+ print Stream(module.generate(ctxt)).render('html')
print
print