changeset 313:d72d842e1083 trunk

Handle expressions containing non-ASCII strings as arguments for `py:with`, `py:def`, and `py:for`.
author cmlenz
date Tue, 24 Oct 2006 14:16:22 +0000
parents cb7326367f91
children 06a25d0962af
files genshi/eval.py genshi/template.py genshi/tests/output.py genshi/tests/template.py
diffstat 4 files changed, 59 insertions(+), 8 deletions(-) [+]
line wrap: on
line diff
--- a/genshi/eval.py
+++ b/genshi/eval.py
@@ -75,10 +75,8 @@
         """
         if isinstance(source, basestring):
             self.source = source
-            if isinstance(source, unicode):
-                source = '\xef\xbb\xbf' + source.encode('utf-8')
-            self.code = _compile(parse(source, 'eval'), self.source,
-                                 filename=filename, lineno=lineno)
+            self.code = _compile(_parse(source), self.source, filename=filename,
+                                 lineno=lineno)
         else:
             assert isinstance(source, ast.Node)
             self.source = '?'
@@ -163,6 +161,11 @@
         raise NameError('Variable "%s" is not defined' % self._name)
 
 
+def _parse(source, mode='eval'):
+    if isinstance(source, unicode):
+        source = '\xef\xbb\xbf' + source.encode('utf-8')
+    return parse(source, mode)
+
 def _compile(node, source=None, filename=None, lineno=-1):
     tree = ExpressionASTTransformer().visit(node)
     if isinstance(filename, unicode):
--- a/genshi/template.py
+++ b/genshi/template.py
@@ -31,7 +31,7 @@
 
 from genshi.core import Attrs, Namespace, Stream, StreamEventKind, _ensure
 from genshi.core import START, END, START_NS, END_NS, TEXT, COMMENT
-from genshi.eval import Expression
+from genshi.eval import Expression, _parse
 from genshi.input import XMLParser
 from genshi.path import Path
 from genshi.util import LRUCache
@@ -359,7 +359,7 @@
     def __init__(self, args, namespaces=None, filename=None, lineno=-1,
                  offset=-1):
         Directive.__init__(self, None, namespaces, filename, lineno, offset)
-        ast = compiler.parse(args, 'eval').node
+        ast = _parse(args).node
         self.args = []
         self.defaults = {}
         if isinstance(ast, compiler.ast.CallFunc):
@@ -432,7 +432,7 @@
             raise TemplateSyntaxError('"in" keyword missing in "for" directive',
                                       filename, lineno, offset)
         assign, value = value.split(' in ', 1)
-        ast = compiler.parse(assign, 'exec')
+        ast = _parse(assign, 'exec')
         self.assign = _assignment(ast.node.nodes[0].expr)
         self.filename = filename
         Directive.__init__(self, value.strip(), namespaces, filename, lineno,
@@ -744,7 +744,7 @@
         self.vars = []
         value = value.strip()
         try:
-            ast = compiler.parse(value, 'exec').node
+            ast = _parse(value, 'exec').node
             for node in ast.nodes:
                 if isinstance(node, compiler.ast.Discard):
                     continue
--- a/genshi/tests/output.py
+++ b/genshi/tests/output.py
@@ -80,6 +80,24 @@
         output = stream.render(XMLSerializer)
         self.assertEqual('<?python x = 2?>', output)
 
+    def test_nested_default_namespaces(self):
+        xml = XML("""<div xmlns="http://www.w3.org/1999/xhtml">
+          <p xmlns="http://www.w3.org/1999/xhtml" />
+        </div>""")
+        output = xml.render(XMLSerializer)
+        self.assertEqual("""<div xmlns="http://www.w3.org/1999/xhtml">
+          <p/>
+        </div>""", output)
+
+    def test_nested_bound_namespaces(self):
+        xml = XML("""<div xmlns:x="http://example.org/">
+          <p xmlns:x="http://example.org/" />
+        </div>""")
+        output = xml.render(XMLSerializer)
+        self.assertEqual("""<div xmlns:x="http://example.org/">
+          <p/>
+        </div>""", output)
+
 
 class XHTMLSerializerTestCase(unittest.TestCase):
 
@@ -151,6 +169,24 @@
         output = XML(text).render(XHTMLSerializer)
         self.assertEqual(text, output)
 
+    def test_nested_default_namespaces(self):
+        xml = XML("""<div xmlns="http://www.w3.org/1999/xhtml">
+          <p xmlns="http://www.w3.org/1999/xhtml" />
+        </div>""")
+        output = xml.render(XHTMLSerializer)
+        self.assertEqual("""<div xmlns="http://www.w3.org/1999/xhtml">
+          <p></p>
+        </div>""", output)
+
+    def test_nested_bound_namespaces(self):
+        xml = XML("""<div xmlns:x="http://example.org/">
+          <x:p xmlns:x="http://example.org/" />
+        </div>""")
+        output = xml.render(XHTMLSerializer)
+        self.assertEqual("""<div xmlns:x="http://example.org/">
+          <x:p />
+        </div>""", output)
+
 
 class HTMLSerializerTestCase(unittest.TestCase):
 
--- a/genshi/tests/template.py
+++ b/genshi/tests/template.py
@@ -887,6 +887,18 @@
             here are two semicolons: ;;
         </div>""", str(tmpl.generate()))
 
+    def test_unicode_expr(self):
+        tmpl = MarkupTemplate("""<div xmlns:py="http://genshi.edgewall.org/">
+          <span py:with="weeks=(u'一', u'二', u'三', u'四', u'五', u'六', u'日')">
+            $weeks
+          </span>
+        </div>""")
+        self.assertEqual("""<div>
+          <span>
+            一二三四五六日
+          </span>
+        </div>""", str(tmpl.generate()))
+
 
 class TemplateTestCase(unittest.TestCase):
     """Tests for basic template processing, expression evaluation and error
Copyright (C) 2012-2017 Edgewall Software