# HG changeset patch # User hodgestar # Date 1356809501 0 # Node ID 2ed9827596a481e7f8ed6ce94de415efa5356f8a # Parent 19ac5d8fd96ce51c73f1e2b1cb4da70690d2e665 Update genshi.template AST handling to support Python 3.4 (see #537). diff --git a/genshi/template/astutil.py b/genshi/template/astutil.py --- a/genshi/template/astutil.py +++ b/genshi/template/astutil.py @@ -281,20 +281,28 @@ self._change_indent(-1) # With(expr context_expr, expr? optional_vars, stmt* body) + # With(withitem* items, stmt* body) in Python >= 3.3 def visit_With(self, node): self._new_line() self._write('with ') - self.visit(node.context_expr) - if getattr(node, 'optional_vars', None): - self._write(' as ') - self.visit(node.optional_vars) + items = getattr(node, 'items', None) + first = True + if items is None: + items = [node] + for item in items: + if not first: + self._write(', ') + first = False + self.visit(item.context_expr) + if getattr(item, 'optional_vars', None): + self._write(' as ') + self.visit(item.optional_vars) self._write(':') self._change_indent(1) for statement in node.body: self.visit(statement) self._change_indent(-1) - if IS_PYTHON2: # Raise(expr? type, expr? inst, expr? tback) def visit_Raise(self, node): @@ -379,6 +387,33 @@ self.visit(statement) self._change_indent(-1) + # New in Py3.3 + # Try(stmt* body, excepthandler* handlers, stmt* orelse, stmt* finalbody) + def visit_Try(self, node): + self._new_line() + self._write('try:') + self._change_indent(1) + for statement in node.body: + self.visit(statement) + self._change_indent(-1) + if getattr(node, 'handlers', None): + for handler in node.handlers: + self.visit(handler) + self._new_line() + if getattr(node, 'orelse', None): + self._write('else:') + self._change_indent(1) + for statement in node.orelse: + self.visit(statement) + self._change_indent(-1) + if getattr(node, 'finalbody', None): + self._new_line() + self._write('finally:') + self._change_indent(1) + for statement in node.finalbody: + self.visit(statement) + self._change_indent(-1) + # Assert(expr test, expr? msg) def visit_Assert(self, node): self._new_line() @@ -766,6 +801,7 @@ visit_Raise = _clone visit_TryExcept = _clone visit_TryFinally = _clone + visit_Try = _clone visit_Assert = _clone visit_ExceptHandler = _clone diff --git a/genshi/template/tests/eval.py b/genshi/template/tests/eval.py --- a/genshi/template/tests/eval.py +++ b/genshi/template/tests/eval.py @@ -859,6 +859,29 @@ suite.execute(d) self.assertEqual([0, 3, 4], d['results']) + if sys.version_info >= (3, 3): + def test_with_statement_with_multiple_items(self): + fd, path = mkstemp() + f = os.fdopen(fd, "w") + try: + f.write('foo\n') + f.seek(0) + f.close() + + d = {'path': path} + suite = Suite("""from __future__ import with_statement +lines = [] +with open(path) as file1, open(path) as file2: + for line in file1: + lines.append(line) + for line in file2: + lines.append(line) +""") + suite.execute(d) + self.assertEqual(['foo\n', 'foo\n'], d['lines']) + finally: + os.remove(path) + def suite(): suite = unittest.TestSuite()