attrs.getValue((ns_uri, "attr")) == "val" and \
attrs[(ns_uri, "attr")] == "val"
+class ElemGatherer(ContentHandler):
+ def __init__(self):
+ self.events = []
+ def startElementNS(self, pair, qname, attrs):
+ self.events.append(('start', pair, qname))
+ def endElementNS(self, pair, qname):
+ self.events.append(('end', pair, qname))
+
+def check_expat_nsdecl(text, expected):
+ parser = create_parser(1)
+ handler = ElemGatherer()
+ parser.setContentHandler(handler)
+ parser.feed(text)
+ parser.close()
+ if verbose and handler.events != expected:
+ from pprint import pprint
+ print "Expected:"
+ pprint(expected)
+ print "Received:"
+ pprint(handler.events)
+ return handler.events == expected
+
+def test_expat_nsdecl_single():
+ return check_expat_nsdecl(
+ "<abc xmlns='http://xml.python.org/'></abc>", [
+ ("start", ("http://xml.python.org/", "abc"), "abc"),
+ ("end", ("http://xml.python.org/", "abc"), "abc"),
+ ])
+
+def test_expat_nsdecl_pair_same():
+ # XXX This shows where xml.sax.expatreader can use the wrong
+ # prefix when more than one is in scope for a particular URI.
+ # We still want to exercise this code since previous versions got
+ # the namespace handling wrong in more severe ways (exceptions
+ # that should not have happened).
+ return check_expat_nsdecl(
+ "<abc xmlns='http://xml.python.org/'"
+ " xmlns:foo='http://xml.python.org/'>"
+ "<foo:def/>"
+ "<ghi/>"
+ "</abc>", [
+ ("start", ("http://xml.python.org/", "abc"), "foo:abc"),
+ ("start", ("http://xml.python.org/", "def"), "foo:def"),
+ ("end", ("http://xml.python.org/", "def"), "foo:def"),
+ ("start", ("http://xml.python.org/", "ghi"), "foo:ghi"),
+ ("end", ("http://xml.python.org/", "ghi"), "foo:ghi"),
+ ("end", ("http://xml.python.org/", "abc"), "foo:abc"),
+ ])
+
+def test_expat_nsdecl_pair_diff():
+ return check_expat_nsdecl(
+ "<abc xmlns='http://xml.python.org/1'"
+ " xmlns:foo='http://xml.python.org/2'>"
+ "<foo:def/>"
+ "<ghi/>"
+ "</abc>", [
+ ("start", ("http://xml.python.org/1", "abc"), "abc"),
+ ("start", ("http://xml.python.org/2", "def"), "foo:def"),
+ ("end", ("http://xml.python.org/2", "def"), "foo:def"),
+ ("start", ("http://xml.python.org/1", "ghi"), "ghi"),
+ ("end", ("http://xml.python.org/1", "ghi"), "ghi"),
+ ("end", ("http://xml.python.org/1", "abc"), "abc"),
+ ])
+
# ===== InputSource support
xml_test_out = open(findfile("test"+os.extsep+"xml"+os.extsep+"out")).read()
pair = string.split(name)
if len(pair) == 1:
pair = (None, name)
+ qname = name
else:
pair = tuple(pair)
+ qname = pair[1]
+ if self._ns_stack:
+ prefix = self._ns_stack[-1][pair[0]][-1]
+ if prefix:
+ qname = "%s:%s" % (prefix, pair[1])
newattrs = {}
qnames = {}
apair = string.split(aname)
if len(apair) == 1:
apair = (None, aname)
- qname = aname
+ aqname = aname
else:
apair = tuple(apair)
# XXX need to guess the prefix
prefix = self._ns_stack[-1][apair[0]][-1]
- qname = "%s:%s" % (prefix, apair[1])
+ aqname = "%s:%s" % (prefix, apair[1])
newattrs[apair] = value
- qnames[apair] = qname
+ qnames[apair] = aqname
- self._cont_handler.startElementNS(pair, None,
+ self._cont_handler.startElementNS(pair, qname,
AttributesNSImpl(newattrs, qnames))
def end_element_ns(self, name):
pair = string.split(name)
if len(pair) == 1:
pair = (None, name)
+ qname = name
else:
pair = tuple(pair)
+ qname = pair[1]
+ if self._ns_stack:
+ prefix = self._ns_stack[-1][pair[0]][-1]
+ if prefix:
+ qname = "%s:%s" % (prefix, pair[1])
- self._cont_handler.endElementNS(pair, None)
+ self._cont_handler.endElementNS(pair, qname)
# this is not used (call directly to ContentHandler)
def processing_instruction(self, target, data):
def start_namespace_decl(self, prefix, uri):
if self._ns_stack:
- d = self._ns_stack.copy()
+ d = self._ns_stack[-1].copy()
if d.has_key(uri):
L = d[uri][:]
d[uri] = L
L.append(prefix)
+ else:
+ d[uri] = [prefix]
else:
d = {uri: [prefix]}
self._ns_stack.append(d)