Index: util.py
===================================================================
--- util.py	(révision 962)
+++ util.py	(copie de travail)
@@ -243,3 +243,44 @@
     :return: the text with tags removed
     """
     return _STRIPTAGS_RE.sub('', text)
+
+def xpointer2xpath(xpointer):
+    """Returns the XPath representation of an XPointer attribute.
+
+    >>> xpointer2xpath(None)
+    '//*'
+
+    We should return "id('id1')" but the xpath implementation of genshi does
+    not support that.
+
+    >>> xpointer2xpath('id1')
+    "//node()[@id='id1']"
+    >>> xpointer2xpath('id1/2')
+    "//node()[@id='id1']/*[2]"
+
+    Absolute XPointer expression should also be supported although the current
+    XPath parser used by genshi does not support them.
+    
+    >>> xpointer2xpath('/1/2/3')
+    '/*[1]/*[2]/*[3]'
+
+    Support for XPath in the xpointer scheme
+
+    >>> xpointer2xpath('xpointer("//tag")')
+    '//tag'
+    """
+    if xpointer is None:
+        return '//*'
+    match = re.match(r'''xpointer\(["'](.*)["']\)''', xpointer)
+    if match:
+        return match.groups()[0]
+
+    path = xpointer.split('/')
+    start = path.pop(0)
+    if start == '':
+        xpath = ['']
+    else:
+        xpath = ["//node()[@id='%s']" % start]
+    for segment in path:
+        xpath.append('*[%s]' % segment)
+    return '/'.join(xpath)
Index: template/base.py
===================================================================
--- template/base.py	(révision 962)
+++ template/base.py	(copie de travail)
@@ -24,7 +24,8 @@
 import sys
 
 from genshi.core import Attrs, Stream, StreamEventKind, START, TEXT, _ensure
-from genshi.input import ParseError
+from genshi.input import ParseError, XML
+from genshi.util import xpointer2xpath
 
 __all__ = ['Context', 'DirectiveFactory', 'Template', 'TemplateError',
            'TemplateRuntimeError', 'TemplateSyntaxError', 'BadDirectiveError']
@@ -467,7 +468,7 @@
                         yield event
             else:
                 if kind is INCLUDE:
-                    href, cls, fallback = data
+                    href, xpointer, cls, fallback = data
                     if isinstance(href, basestring) and \
                             not getattr(self.loader, 'auto_reload', True):
                         # If the path to the included template is static, and
@@ -476,7 +477,9 @@
                         try:
                             tmpl = self.loader.load(href, relative_to=pos[0],
                                                     cls=cls or self.__class__)
-                            for event in tmpl.stream:
+                            xpath = xpointer2xpath(xpointer)
+                            stream = Stream(tmpl.stream)
+                            for event in stream.select(xpath):
                                 yield event
                         except TemplateNotFound:
                             if fallback is None:
@@ -486,7 +489,8 @@
                         continue
                     elif fallback:
                         # Otherwise the include is performed at run time
-                        data = href, cls, list(self._prepare(fallback))
+                        data = (href, xpointer, cls, 
+                                list(self._prepare(fallback)))
 
                 yield kind, data, pos
 
@@ -602,7 +606,7 @@
 
         for event in stream:
             if event[0] is INCLUDE:
-                href, cls, fallback = event[1]
+                href, xpointer, cls, fallback = event[1]
                 if not isinstance(href, basestring):
                     parts = []
                     for subkind, subdata, subpos in self._eval(href, ctxt,
@@ -613,7 +617,9 @@
                 try:
                     tmpl = self.loader.load(href, relative_to=event[2][0],
                                             cls=cls or self.__class__)
-                    for event in tmpl.generate(ctxt, **vars):
+                    xpath = xpointer2xpath(xpointer)
+                    stream = XML(tmpl.generate(ctxt, **vars)).select(xpath)
+                    for event in stream:
                         yield event
                 except TemplateNotFound:
                     if fallback is None:
Index: template/markup.py
===================================================================
--- template/markup.py	(révision 962)
+++ template/markup.py	(copie de travail)
@@ -222,7 +222,13 @@
                             raise TemplateSyntaxError('Include misses required '
                                                       'attribute "href"',
                                                       self.filepath, *pos[1:])
-                        includes.append((include_href, attrs.get('parse')))
+                        if attrs.get('parse') == 'text' and \
+                           attrs.get('xpointer') is not None:
+                            raise TemplateSyntaxError('Include use an xpointer '
+                                                      'while parsing a text',
+                                                      self.filepath, *pos[1:])
+                        includes.append((include_href, attrs.get('parse'),
+                                         attrs.get('xpointer')))
                         streams.append([])
                     elif tag.localname == 'fallback':
                         streams.append([])
@@ -240,7 +246,7 @@
                     streams.pop() # discard anything between the include tags
                                   # and the fallback element
                     stream = streams[-1]
-                    href, parse = includes.pop()
+                    href, parse, xpointer = includes.pop()
                     try:
                         cls = {
                             'xml': MarkupTemplate,
@@ -250,7 +256,8 @@
                         raise TemplateSyntaxError('Invalid value for "parse" '
                                                   'attribute of include',
                                                   self.filepath, *pos[1:])
-                    stream.append((INCLUDE, (href, cls, fallback), pos))
+                    stream.append((INCLUDE, (href, xpointer, cls, fallback),
+                                   pos))
                 else:
                     stream.append((kind, data, pos))
 
