generated from sethub/template
[libxml2]Add libxml2 library
This commit is contained in:
@@ -0,0 +1,77 @@
|
||||
PYTESTS= \
|
||||
build.py \
|
||||
attribs.py \
|
||||
tst.py \
|
||||
tstxpath.py \
|
||||
xpathext.py \
|
||||
push.py \
|
||||
pushSAX.py \
|
||||
pushSAXhtml.py \
|
||||
error.py \
|
||||
serialize.py\
|
||||
validate.py \
|
||||
tstURI.py \
|
||||
cutnpaste.py\
|
||||
xpathret.py \
|
||||
xpath.py \
|
||||
outbuf.py \
|
||||
inbuf.py \
|
||||
input_callback.py \
|
||||
resolver.py \
|
||||
regexp.py \
|
||||
reader.py \
|
||||
reader2.py \
|
||||
reader3.py \
|
||||
reader4.py \
|
||||
reader5.py \
|
||||
reader6.py \
|
||||
reader7.py \
|
||||
reader8.py \
|
||||
readernext.py \
|
||||
walker.py \
|
||||
nsdel.py \
|
||||
ctxterror.py\
|
||||
readererr.py\
|
||||
relaxng.py \
|
||||
schema.py \
|
||||
thread2.py \
|
||||
sync.py \
|
||||
tstLastError.py \
|
||||
indexes.py \
|
||||
dtdvalid.py \
|
||||
tstmem.py \
|
||||
validDTD.py \
|
||||
validSchemas.py \
|
||||
validRNG.py \
|
||||
compareNodes.py \
|
||||
xpathns.py \
|
||||
xpathleak.py \
|
||||
unicode.py
|
||||
|
||||
XMLS= \
|
||||
tst.xml \
|
||||
valid.xml \
|
||||
invalid.xml \
|
||||
test.dtd
|
||||
|
||||
EXTRA_DIST = $(PYTESTS) $(XMLS) setup_test.py
|
||||
|
||||
CLEANFILES = core tmp.xml *.pyc
|
||||
|
||||
if WITH_PYTHON
|
||||
check-local:
|
||||
@for f in $(XMLS) ; do test -f $$f || $(LN_S) $(srcdir)/$$f . ; done
|
||||
@echo "## running Python regression tests"
|
||||
@(export PYTHONPATH="..:../.libs:$(srcdir)/..:$$PYTHONPATH" ; \
|
||||
export LD_LIBRARY_PATH="$(top_builddir)/.libs:$$LD_LIBRARY_PATH" ; \
|
||||
export DYLD_LIBRARY_PATH="$(top_builddir)/.libs:$$DYLD_LIBRARY_PATH" ; \
|
||||
export PATH="$(top_builddir)/.libs:$$PATH" ; \
|
||||
for test in $(PYTESTS) ; do \
|
||||
log=`$(PYTHON) $(srcdir)/$$test` ; \
|
||||
if [ "$$?" -ne 0 ] ; then \
|
||||
echo "-- $$test" ; \
|
||||
echo "$$log" ; \
|
||||
exit 1 ; \
|
||||
fi ; \
|
||||
done)
|
||||
endif
|
||||
@@ -0,0 +1,35 @@
|
||||
#!/usr/bin/env python3
|
||||
import sys
|
||||
import setup_test
|
||||
import libxml2
|
||||
|
||||
# Memory debug specific
|
||||
libxml2.debugMemory(1)
|
||||
|
||||
#
|
||||
# Testing XML document serialization
|
||||
#
|
||||
doc = libxml2.readDoc(
|
||||
"""<?xml version="1.0" encoding="iso-8859-1"?>
|
||||
<!DOCTYPE test [
|
||||
<!ELEMENT test (#PCDATA) >
|
||||
<!ATTLIST test xmlns:abc CDATA #FIXED "http://abc.org" >
|
||||
<!ATTLIST test abc:attr CDATA #FIXED "def" >
|
||||
]>
|
||||
<test />
|
||||
""", None, None, libxml2.XML_PARSE_DTDATTR)
|
||||
elem = doc.getRootElement()
|
||||
attr = elem.hasNsProp('attr', 'http://abc.org')
|
||||
print(attr.serialize())
|
||||
if attr == None:
|
||||
print("Failed to find defaulted attribute abc:attr")
|
||||
sys.exit(1)
|
||||
|
||||
doc.freeDoc()
|
||||
|
||||
# Memory debug specific
|
||||
libxml2.cleanupParser()
|
||||
if libxml2.debugMemory(1) == 0:
|
||||
print("OK")
|
||||
else:
|
||||
print("Memory leak %d bytes" % (libxml2.debugMemory(1)))
|
||||
@@ -0,0 +1,59 @@
|
||||
#!/usr/bin/env python3
|
||||
import setup_test
|
||||
import libxml2
|
||||
import sys
|
||||
|
||||
# Memory debug specific
|
||||
libxml2.debugMemory(1)
|
||||
|
||||
doc = libxml2.newDoc("1.0")
|
||||
comment = doc.newDocComment("This is a generated document")
|
||||
doc.addChild(comment)
|
||||
pi = libxml2.newPI("test", "PI content")
|
||||
doc.addChild(pi)
|
||||
root = doc.newChild(None, "doc", None)
|
||||
ns = root.newNs("http://example.com/doc", "my")
|
||||
root.setNs(ns)
|
||||
elem = root.newChild(None, "foo", "bar")
|
||||
elem.setBase("http://example.com/imgs")
|
||||
elem.setProp("img", "image.gif")
|
||||
doc.saveFile("tmp.xml")
|
||||
doc.freeDoc()
|
||||
|
||||
doc = libxml2.parseFile("tmp.xml")
|
||||
comment = doc.children
|
||||
if comment.type != "comment" or \
|
||||
comment.content != "This is a generated document":
|
||||
print("error rereading comment")
|
||||
sys.exit(1)
|
||||
pi = comment.next
|
||||
if pi.type != "pi" or pi.name != "test" or pi.content != "PI content":
|
||||
print("error rereading PI")
|
||||
sys.exit(1)
|
||||
root = pi.next
|
||||
if root.name != "doc":
|
||||
print("error rereading root")
|
||||
sys.exit(1)
|
||||
ns = root.ns()
|
||||
if ns.name != "my" or ns.content != "http://example.com/doc":
|
||||
print("error rereading namespace")
|
||||
sys.exit(1)
|
||||
elem = root.children
|
||||
if elem.name != "foo":
|
||||
print("error rereading elem")
|
||||
sys.exit(1)
|
||||
if elem.getBase(None) != "http://example.com/imgs":
|
||||
print("error rereading base")
|
||||
sys.exit(1)
|
||||
if elem.prop("img") != "image.gif":
|
||||
print("error rereading property")
|
||||
sys.exit(1)
|
||||
|
||||
doc.freeDoc()
|
||||
|
||||
# Memory debug specific
|
||||
libxml2.cleanupParser()
|
||||
if libxml2.debugMemory(1) == 0:
|
||||
print("OK")
|
||||
else:
|
||||
print("Memory leak %d bytes" % (libxml2.debugMemory(1)))
|
||||
@@ -0,0 +1,50 @@
|
||||
#!/usr/bin/env python3
|
||||
import sys
|
||||
import setup_test
|
||||
import libxml2
|
||||
|
||||
# Memory debug specific
|
||||
libxml2.debugMemory(1)
|
||||
|
||||
#
|
||||
# Testing XML Node comparison and Node hash-value
|
||||
#
|
||||
doc = libxml2.parseDoc("""<root><foo/></root>""")
|
||||
root = doc.getRootElement()
|
||||
|
||||
# Create two different objects which point to foo
|
||||
foonode1 = root.children
|
||||
foonode2 = root.children
|
||||
|
||||
# Now check that [in]equality tests work ok
|
||||
if not ( foonode1 == foonode2 ):
|
||||
print("Error comparing nodes with ==, nodes should be equal but are unequal")
|
||||
sys.exit(1)
|
||||
if not ( foonode1 != root ):
|
||||
print("Error comparing nodes with ==, nodes should not be equal but are equal")
|
||||
sys.exit(1)
|
||||
if not ( foonode1 != root ):
|
||||
print("Error comparing nodes with !=, nodes should not be equal but are equal")
|
||||
if ( foonode1 != foonode2 ):
|
||||
print("Error comparing nodes with !=, nodes should be equal but are unequal")
|
||||
|
||||
# Next check that the hash function for the objects also works ok
|
||||
if not (hash(foonode1) == hash(foonode2)):
|
||||
print("Error hash values for two equal nodes are different")
|
||||
sys.exit(1)
|
||||
if not (hash(foonode1) != hash(root)):
|
||||
print("Error hash values for two unequal nodes are not different")
|
||||
sys.exit(1)
|
||||
if hash(foonode1) == hash(root):
|
||||
print("Error hash values for two unequal nodes are equal")
|
||||
sys.exit(1)
|
||||
|
||||
# Basic tests successful
|
||||
doc.freeDoc()
|
||||
|
||||
# Memory debug specific
|
||||
libxml2.cleanupParser()
|
||||
if libxml2.debugMemory(1) == 0:
|
||||
print("OK")
|
||||
else:
|
||||
print("Memory leak %d bytes" % (libxml2.debugMemory(1)))
|
||||
@@ -0,0 +1,56 @@
|
||||
#!/usr/bin/env python3
|
||||
#
|
||||
# This test exercise the redirection of error messages with a
|
||||
# functions defined in Python.
|
||||
#
|
||||
import sys
|
||||
import setup_test
|
||||
import libxml2
|
||||
|
||||
# Memory debug specific
|
||||
libxml2.debugMemory(1)
|
||||
|
||||
expect="""--> (3) xmlns: URI foo is not absolute
|
||||
--> (4) Opening and ending tag mismatch: x line 1 and y
|
||||
"""
|
||||
|
||||
err=""
|
||||
def callback(arg,msg,severity,reserved):
|
||||
global err
|
||||
err = err + "%s (%d) %s" % (arg,severity,msg)
|
||||
|
||||
s = """<x xmlns="foo"></y>"""
|
||||
|
||||
parserCtxt = libxml2.createPushParser(None,"",0,"test.xml")
|
||||
parserCtxt.setErrorHandler(callback, "-->")
|
||||
if parserCtxt.getErrorHandler() != (callback,"-->"):
|
||||
print("getErrorHandler failed")
|
||||
sys.exit(1)
|
||||
parserCtxt.parseChunk(s,len(s),1)
|
||||
doc = parserCtxt.doc()
|
||||
doc.freeDoc()
|
||||
parserCtxt = None
|
||||
|
||||
if err != expect:
|
||||
print("error")
|
||||
print("received %s" %(err))
|
||||
print("expected %s" %(expect))
|
||||
sys.exit(1)
|
||||
|
||||
i = 10000
|
||||
while i > 0:
|
||||
parserCtxt = libxml2.createPushParser(None,"",0,"test.xml")
|
||||
parserCtxt.setErrorHandler(callback, "-->")
|
||||
parserCtxt.parseChunk(s,len(s),1)
|
||||
doc = parserCtxt.doc()
|
||||
doc.freeDoc()
|
||||
parserCtxt = None
|
||||
err = ""
|
||||
i = i - 1
|
||||
|
||||
# Memory debug specific
|
||||
libxml2.cleanupParser()
|
||||
if libxml2.debugMemory(1) == 0:
|
||||
print("OK")
|
||||
else:
|
||||
print("Memory leak %d bytes" % (libxml2.debugMemory(1)))
|
||||
@@ -0,0 +1,48 @@
|
||||
#!/usr/bin/env python3
|
||||
import sys
|
||||
import setup_test
|
||||
import libxml2
|
||||
|
||||
# Memory debug specific
|
||||
libxml2.debugMemory(1)
|
||||
|
||||
#
|
||||
# Testing XML document serialization
|
||||
#
|
||||
source = libxml2.parseDoc("""<?xml version="1.0"?>
|
||||
<root xmlns:foo="http://example.org/foo"
|
||||
xmlns:bar="http://example.org/bar">
|
||||
<include xmlns="http://example.org/include">
|
||||
<fragment><foo:elem bar="tricky"/></fragment>
|
||||
</include>
|
||||
</root>
|
||||
""")
|
||||
|
||||
target = libxml2.parseDoc("""<?xml version="1.0"?>
|
||||
<root xmlns:foobar="http://example.org/bar"/>""")
|
||||
|
||||
fragment = source.xpathEval("//*[name()='fragment']")[0]
|
||||
dest = target.getRootElement()
|
||||
|
||||
# do a cut and paste operation
|
||||
fragment.unlinkNode()
|
||||
dest.addChild(fragment)
|
||||
# do the namespace fixup
|
||||
dest.reconciliateNs(target)
|
||||
|
||||
# The source tree can be freed at that point
|
||||
source.freeDoc()
|
||||
|
||||
# check the resulting tree
|
||||
str = dest.serialize()
|
||||
if str != """<root xmlns:foobar="http://example.org/bar" xmlns:default="http://example.org/include" xmlns:foo="http://example.org/foo"><default:fragment><foo:elem bar="tricky"/></default:fragment></root>""":
|
||||
print("reconciliateNs() failed")
|
||||
sys.exit(1)
|
||||
target.freeDoc()
|
||||
|
||||
# Memory debug specific
|
||||
libxml2.cleanupParser()
|
||||
if libxml2.debugMemory(1) == 0:
|
||||
print("OK")
|
||||
else:
|
||||
print("Memory leak %d bytes" % (libxml2.debugMemory(1)))
|
||||
@@ -0,0 +1,32 @@
|
||||
#!/usr/bin/env python3
|
||||
import setup_test
|
||||
import libxml2
|
||||
import sys
|
||||
|
||||
# Memory debug specific
|
||||
libxml2.debugMemory(1)
|
||||
|
||||
dtd="""<!ELEMENT foo EMPTY>"""
|
||||
instance="""<?xml version="1.0"?>
|
||||
<foo></foo>"""
|
||||
|
||||
dtd = libxml2.parseDTD(None, 'test.dtd')
|
||||
ctxt = libxml2.newValidCtxt()
|
||||
doc = libxml2.parseDoc(instance)
|
||||
ret = doc.validateDtd(ctxt, dtd)
|
||||
if ret != 1:
|
||||
print("error doing DTD validation")
|
||||
sys.exit(1)
|
||||
|
||||
doc.freeDoc()
|
||||
dtd.freeDtd()
|
||||
del dtd
|
||||
del ctxt
|
||||
|
||||
# Memory debug specific
|
||||
libxml2.cleanupParser()
|
||||
if libxml2.debugMemory(1) == 0:
|
||||
print("OK")
|
||||
else:
|
||||
print("Memory leak %d bytes" % (libxml2.debugMemory(1)))
|
||||
|
||||
@@ -0,0 +1,51 @@
|
||||
#!/usr/bin/env python3
|
||||
#
|
||||
# This test exercise the redirection of error messages with a
|
||||
# functions defined in Python.
|
||||
#
|
||||
import sys
|
||||
import setup_test
|
||||
import libxml2
|
||||
|
||||
# Memory debug specific
|
||||
libxml2.debugMemory(1)
|
||||
|
||||
expect='--> I/O --> warning : --> failed to load "missing.xml": No such file or directory\n'
|
||||
err=""
|
||||
def callback(ctx, str):
|
||||
global err
|
||||
|
||||
err = err + "%s %s" % (ctx, str)
|
||||
|
||||
got_exc = 0
|
||||
libxml2.registerErrorHandler(callback, "-->")
|
||||
try:
|
||||
doc = libxml2.parseFile("missing.xml")
|
||||
except libxml2.parserError:
|
||||
got_exc = 1
|
||||
|
||||
if got_exc == 0:
|
||||
print("Failed to get a parser exception")
|
||||
sys.exit(1)
|
||||
|
||||
if err != expect:
|
||||
print("error")
|
||||
print("received %s" %(err))
|
||||
print("expected %s" %(expect))
|
||||
sys.exit(1)
|
||||
|
||||
i = 10000
|
||||
while i > 0:
|
||||
try:
|
||||
doc = libxml2.parseFile("missing.xml")
|
||||
except libxml2.parserError:
|
||||
got_exc = 1
|
||||
err = ""
|
||||
i = i - 1
|
||||
|
||||
# Memory debug specific
|
||||
libxml2.cleanupParser()
|
||||
if libxml2.debugMemory(1) == 0:
|
||||
print("OK")
|
||||
else:
|
||||
print("Memory leak %d bytes" % (libxml2.debugMemory(1)))
|
||||
@@ -0,0 +1,30 @@
|
||||
#!/usr/bin/env python3
|
||||
import sys
|
||||
import setup_test
|
||||
import libxml2
|
||||
try:
|
||||
import StringIO
|
||||
str_io = StringIO.StringIO
|
||||
except:
|
||||
import io
|
||||
str_io = io.StringIO
|
||||
|
||||
# Memory debug specific
|
||||
libxml2.debugMemory(1)
|
||||
|
||||
i = 0
|
||||
while i < 5000:
|
||||
f = str_io("foobar")
|
||||
buf = libxml2.inputBuffer(f)
|
||||
i = i + 1
|
||||
|
||||
del f
|
||||
del buf
|
||||
|
||||
# Memory debug specific
|
||||
libxml2.cleanupParser()
|
||||
if libxml2.debugMemory(1) == 0:
|
||||
print("OK")
|
||||
else:
|
||||
print("Memory leak %d bytes" % (libxml2.debugMemory(1)))
|
||||
|
||||
@@ -0,0 +1,113 @@
|
||||
#!/usr/bin/env python3
|
||||
# -*- coding: ISO-8859-1 -*-
|
||||
import sys
|
||||
import setup_test
|
||||
import libxml2
|
||||
|
||||
# Memory debug specific
|
||||
libxml2.debugMemory(1)
|
||||
|
||||
ctxt = None
|
||||
|
||||
class callback:
|
||||
def __init__(self, startd, starte, ende, delta, endd):
|
||||
self.startd = startd
|
||||
self.starte = starte
|
||||
self.ende = ende
|
||||
self.endd = endd
|
||||
self.delta = delta
|
||||
self.count = 0
|
||||
|
||||
def startDocument(self):
|
||||
global ctxt
|
||||
if ctxt.byteConsumed() != self.startd:
|
||||
print("document start at wrong index: %d expecting %d\n" % (
|
||||
ctxt.byteConsumed(), self.startd))
|
||||
sys.exit(1)
|
||||
|
||||
def endDocument(self):
|
||||
global ctxt
|
||||
expect = self.ende + self.delta * (self.count - 1) + self.endd
|
||||
if ctxt.byteConsumed() != expect:
|
||||
print("document end at wrong index: %d expecting %d\n" % (
|
||||
ctxt.byteConsumed(), expect))
|
||||
sys.exit(1)
|
||||
|
||||
def startElement(self, tag, attrs):
|
||||
global ctxt
|
||||
if tag == "bar1":
|
||||
expect = self.starte + self.delta * self.count
|
||||
if ctxt.byteConsumed() != expect:
|
||||
print("element start at wrong index: %d expecting %d\n" % (
|
||||
ctxt.byteConsumed(), expect))
|
||||
sys.exit(1)
|
||||
|
||||
|
||||
def endElement(self, tag):
|
||||
global ctxt
|
||||
if tag == "bar1":
|
||||
expect = self.ende + self.delta * self.count
|
||||
if ctxt.byteConsumed() != expect:
|
||||
print("element end at wrong index: %d expecting %d\n" % (
|
||||
ctxt.byteConsumed(), expect))
|
||||
sys.exit(1)
|
||||
self.count = self.count + 1
|
||||
|
||||
def characters(self, data):
|
||||
pass
|
||||
|
||||
#
|
||||
# First run a pure UTF-8 test
|
||||
#
|
||||
handler = callback(0, 13, 27, 198, 183)
|
||||
ctxt = libxml2.createPushParser(handler, "<foo>\n", 6, "test.xml")
|
||||
chunk = """ <bar1>chars1</bar1>
|
||||
<bar2>chars2</bar2>
|
||||
<bar3>chars3</bar3>
|
||||
<bar4>chars4</bar4>
|
||||
<bar5>chars5</bar5>
|
||||
<bar6><s6</bar6>
|
||||
<bar7>chars7</bar7>
|
||||
<bar8>&8</bar8>
|
||||
<bar9>chars9</bar9>
|
||||
"""
|
||||
i = 0
|
||||
while i < 10000:
|
||||
ctxt.parseChunk(chunk, len(chunk), 0)
|
||||
i = i + 1
|
||||
chunk = "</foo>"
|
||||
ctxt.parseChunk(chunk, len(chunk), 1)
|
||||
ctxt=None
|
||||
|
||||
#
|
||||
# Then run a test relying on ISO-Latin-1
|
||||
#
|
||||
handler = callback(43, 57, 71, 198, 183)
|
||||
chunk="""<?xml version="1.0" encoding="ISO-8859-1"?>
|
||||
<foo>
|
||||
"""
|
||||
ctxt = libxml2.createPushParser(handler, chunk, len(chunk), "test.xml")
|
||||
chunk = """ <bar1>chars1</bar1>
|
||||
<bar2>chars2</bar2>
|
||||
<bar3>chars3</bar3>
|
||||
<bar4>chàrs4</bar4>
|
||||
<bar5>chars5</bar5>
|
||||
<bar6><s6</bar6>
|
||||
<bar7>chars7</bar7>
|
||||
<bar8>&8</bar8>
|
||||
<bar9>très 9</bar9>
|
||||
"""
|
||||
i = 0
|
||||
while i < 10000:
|
||||
ctxt.parseChunk(chunk, len(chunk), 0)
|
||||
i = i + 1
|
||||
chunk = "</foo>"
|
||||
ctxt.parseChunk(chunk, len(chunk), 1)
|
||||
ctxt=None
|
||||
|
||||
# Memory debug specific
|
||||
libxml2.cleanupParser()
|
||||
if libxml2.debugMemory(1) == 0:
|
||||
print("OK")
|
||||
else:
|
||||
print("Memory leak %d bytes" % (libxml2.debugMemory(1)))
|
||||
@@ -0,0 +1,149 @@
|
||||
#!/usr/bin/env python3
|
||||
#
|
||||
# This tests custom input callbacks
|
||||
#
|
||||
import sys
|
||||
import setup_test
|
||||
import libxml2
|
||||
try:
|
||||
import StringIO
|
||||
str_io = StringIO.StringIO
|
||||
except:
|
||||
import io
|
||||
str_io = io.StringIO
|
||||
|
||||
# We implement a new scheme, py://strings/ that will reference this dictionary
|
||||
pystrings = {
|
||||
'catalogs/catalog.xml' :
|
||||
'''<?xml version="1.0" encoding="utf-8"?>
|
||||
<!DOCTYPE catalog PUBLIC "-//OASIS//DTD Entity Resolution XML Catalog V1.0//EN" "http://www.oasis-open.org/committees/entity/release/1.0/catalog.dtd">
|
||||
<catalog xmlns="urn:oasis:names:tc:entity:xmlns:xml:catalog">
|
||||
<rewriteSystem systemIdStartString="http://example.com/dtds/" rewritePrefix="../dtds/"/>
|
||||
</catalog>''',
|
||||
|
||||
'xml/sample.xml' :
|
||||
'''<?xml version="1.0" encoding="utf-8"?>
|
||||
<!DOCTYPE root SYSTEM "http://example.com/dtds/sample.dtd">
|
||||
<root>&sample.entity;</root>''',
|
||||
|
||||
'dtds/sample.dtd' :
|
||||
'''
|
||||
<!ELEMENT root (#PCDATA)>
|
||||
<!ENTITY sample.entity "replacement text">'''
|
||||
}
|
||||
|
||||
prefix = "py://strings/"
|
||||
startURL = prefix + "xml/sample.xml"
|
||||
catURL = prefix + "catalogs/catalog.xml"
|
||||
|
||||
def my_input_cb(URI):
|
||||
if not(URI.startswith(prefix)):
|
||||
return None
|
||||
path = URI[len(prefix):]
|
||||
if path not in pystrings:
|
||||
return None
|
||||
return str_io(pystrings[path])
|
||||
|
||||
|
||||
def run_test(desc, docpath, catalog, exp_status="verified", exp_err=[], test_callback=None,
|
||||
root_name="root", root_content="replacement text"):
|
||||
opts = libxml2.XML_PARSE_DTDLOAD | libxml2.XML_PARSE_NONET | libxml2.XML_PARSE_COMPACT
|
||||
actual_err = []
|
||||
|
||||
def my_global_error_cb(ctx, msg):
|
||||
actual_err.append((-1, msg))
|
||||
def my_ctx_error_cb(arg, msg, severity, reserved):
|
||||
actual_err.append((severity, msg))
|
||||
|
||||
libxml2.registerErrorHandler(my_global_error_cb, None)
|
||||
try:
|
||||
parser = libxml2.createURLParserCtxt(docpath, opts)
|
||||
parser.setErrorHandler(my_ctx_error_cb, None)
|
||||
if catalog is not None:
|
||||
parser.addLocalCatalog(catalog)
|
||||
if test_callback is not None:
|
||||
test_callback()
|
||||
parser.parseDocument()
|
||||
doc = parser.doc()
|
||||
actual_status = "loaded"
|
||||
e = doc.getRootElement()
|
||||
if e.name == root_name and e.content == root_content:
|
||||
actual_status = "verified"
|
||||
doc.freeDoc()
|
||||
except libxml2.parserError:
|
||||
actual_status = "not loaded"
|
||||
|
||||
if actual_status != exp_status:
|
||||
print("Test '%s' failed: expect status '%s', actual '%s'" % (desc, exp_status, actual_status))
|
||||
sys.exit(1)
|
||||
elif actual_err != exp_err:
|
||||
print("Test '%s' failed" % desc)
|
||||
print("Expect errors:")
|
||||
for s,m in exp_err: print(" [%2d] '%s'" % (s,m))
|
||||
print("Actual errors:")
|
||||
for s,m in actual_err: print(" [%2d] '%s'" % (s,m))
|
||||
sys.exit(1)
|
||||
|
||||
|
||||
# Check that we cannot read custom schema without custom callback
|
||||
run_test(desc="Loading entity without custom callback",
|
||||
docpath=startURL, catalog=None,
|
||||
exp_status="not loaded", exp_err=[
|
||||
(-1, "I/O "),
|
||||
(-1, "warning : "),
|
||||
(-1, "failed to load \"py://strings/xml/sample.xml\": No such file or directory\n")
|
||||
])
|
||||
|
||||
# Register handler and try to load the same entity
|
||||
libxml2.registerInputCallback(my_input_cb)
|
||||
run_test(desc="Loading entity with custom callback",
|
||||
docpath=startURL, catalog=None,
|
||||
exp_status="loaded", exp_err=[
|
||||
( 4, 'failed to load "http://example.com/dtds/sample.dtd": Attempt to load network entity\n'),
|
||||
( 4, "Entity 'sample.entity' not defined\n")
|
||||
])
|
||||
|
||||
# Register a catalog (also accessible via pystr://) and retry
|
||||
run_test(desc="Loading entity with custom callback and catalog",
|
||||
docpath=startURL, catalog=catURL)
|
||||
|
||||
# Unregister custom callback when parser is already created
|
||||
run_test(desc="Loading entity and unregistering callback",
|
||||
docpath=startURL, catalog=catURL,
|
||||
test_callback=lambda: libxml2.popInputCallbacks(),
|
||||
exp_status="loaded", exp_err=[
|
||||
( 3, "failed to load \"py://strings/dtds/sample.dtd\": No such file or directory\n"),
|
||||
( 4, "Entity 'sample.entity' not defined\n")
|
||||
])
|
||||
|
||||
# Try to load the document again
|
||||
run_test(desc="Retry loading document after unregistering callback",
|
||||
docpath=startURL, catalog=catURL,
|
||||
exp_status="not loaded", exp_err=[
|
||||
(-1, "I/O "),
|
||||
(-1, "warning : "),
|
||||
(-1, "failed to load \"py://strings/xml/sample.xml\": No such file or directory\n")
|
||||
])
|
||||
|
||||
# But should be able to read standard I/O yet...
|
||||
run_test(desc="Loading using standard i/o after unregistering callback",
|
||||
docpath="tst.xml", catalog=None,
|
||||
root_name='doc', root_content='bar')
|
||||
|
||||
# Now pop ALL input callbacks, should fail to load even standard I/O
|
||||
try:
|
||||
while True:
|
||||
libxml2.popInputCallbacks()
|
||||
except IndexError:
|
||||
pass
|
||||
|
||||
run_test(desc="Loading using standard i/o after unregistering all callbacks",
|
||||
docpath="tst.xml", catalog=None,
|
||||
exp_status="not loaded", exp_err=[
|
||||
(-1, "I/O "),
|
||||
(-1, "warning : "),
|
||||
(-1, "failed to load \"tst.xml\": No such file or directory\n")
|
||||
])
|
||||
|
||||
print("OK")
|
||||
sys.exit(0);
|
||||
@@ -0,0 +1,6 @@
|
||||
<!DOCTYPE doc [
|
||||
<!ELEMENT doc (a, b, a)>
|
||||
<!ELEMENT a EMPTY>
|
||||
<!ELEMENT b EMPTY>
|
||||
]>
|
||||
<doc><b/><a/><b/></doc>
|
||||
@@ -0,0 +1,62 @@
|
||||
#!/usr/bin/env python3
|
||||
#
|
||||
# this test exercise the XPath basic engine, parser, etc, and
|
||||
# allows to detect memory leaks
|
||||
#
|
||||
import sys
|
||||
import setup_test
|
||||
import libxml2
|
||||
|
||||
instance="""<?xml version="1.0"?>
|
||||
<tag xmlns:foo='urn:foo' xmlns:bar='urn:bar' xmlns:baz='urn:baz' />"""
|
||||
|
||||
def namespaceDefs(node):
|
||||
n = node.nsDefs()
|
||||
while n:
|
||||
yield n
|
||||
n = n.next
|
||||
|
||||
def checkNamespaceDefs(node, count):
|
||||
nsList = list(namespaceDefs(node))
|
||||
#print nsList
|
||||
if len(nsList) != count :
|
||||
raise Exception("Error: saw %d namespace declarations. Expected %d" % (len(nsList), count))
|
||||
|
||||
# Memory debug specific
|
||||
libxml2.debugMemory(1)
|
||||
|
||||
# Remove single namespace
|
||||
doc = libxml2.parseDoc(instance)
|
||||
node = doc.getRootElement()
|
||||
checkNamespaceDefs(node, 3)
|
||||
ns = node.removeNsDef('urn:bar')
|
||||
checkNamespaceDefs(node, 2)
|
||||
ns.freeNsList()
|
||||
doc.freeDoc()
|
||||
|
||||
# Remove all namespaces
|
||||
doc = libxml2.parseDoc(instance)
|
||||
node = doc.getRootElement()
|
||||
checkNamespaceDefs(node, 3)
|
||||
ns = node.removeNsDef(None)
|
||||
checkNamespaceDefs(node, 0)
|
||||
ns.freeNsList()
|
||||
doc.freeDoc()
|
||||
|
||||
# Remove a namespace referred to by a child
|
||||
doc = libxml2.newDoc("1.0")
|
||||
root = doc.newChild(None, "root", None)
|
||||
namespace = root.newNs("http://example.com/sample", "s")
|
||||
child = root.newChild(namespace, "child", None)
|
||||
root.removeNsDef("http://example.com/sample")
|
||||
doc.reconciliateNs(root)
|
||||
namespace.freeNsList()
|
||||
doc.serialize() # This should not segfault
|
||||
doc.freeDoc()
|
||||
|
||||
# Memory debug specific
|
||||
libxml2.cleanupParser()
|
||||
if libxml2.debugMemory(1) == 0:
|
||||
print("OK")
|
||||
else:
|
||||
print("Memory leak %d bytes" % (libxml2.debugMemory(1)))
|
||||
@@ -0,0 +1,110 @@
|
||||
#!/usr/bin/env python3
|
||||
import sys
|
||||
import setup_test
|
||||
import libxml2
|
||||
try:
|
||||
import StringIO
|
||||
str_io = StringIO.StringIO
|
||||
except:
|
||||
import io
|
||||
str_io = io.StringIO
|
||||
|
||||
def testSimpleBufferWrites():
|
||||
f = str_io()
|
||||
buf = libxml2.createOutputBuffer(f, "ISO-8859-1")
|
||||
buf.write(3, "foo")
|
||||
buf.writeString("bar")
|
||||
buf.close()
|
||||
|
||||
if f.getvalue() != "foobar":
|
||||
print("Failed to save to StringIO")
|
||||
sys.exit(1)
|
||||
|
||||
def testSaveDocToBuffer():
|
||||
"""
|
||||
Regression test for bug #154294.
|
||||
"""
|
||||
input = '<foo>Hello</foo>'
|
||||
expected = '''\
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<foo>Hello</foo>
|
||||
'''
|
||||
f = str_io()
|
||||
buf = libxml2.createOutputBuffer(f, 'UTF-8')
|
||||
doc = libxml2.parseDoc(input)
|
||||
doc.saveFileTo(buf, 'UTF-8')
|
||||
doc.freeDoc()
|
||||
if f.getvalue() != expected:
|
||||
print('xmlDoc.saveFileTo() call failed.')
|
||||
print(' got: %s' % repr(f.getvalue()))
|
||||
print('expected: %s' % repr(expected))
|
||||
sys.exit(1)
|
||||
|
||||
def testSaveFormattedDocToBuffer():
|
||||
input = '<outer><inner>Some text</inner><inner/></outer>'
|
||||
# The formatted and non-formatted versions of the output.
|
||||
expected = ('''\
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<outer><inner>Some text</inner><inner/></outer>
|
||||
''', '''\
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<outer>
|
||||
<inner>Some text</inner>
|
||||
<inner/>
|
||||
</outer>
|
||||
''')
|
||||
doc = libxml2.parseDoc(input)
|
||||
for i in (0, 1):
|
||||
f = str_io()
|
||||
buf = libxml2.createOutputBuffer(f, 'UTF-8')
|
||||
doc.saveFormatFileTo(buf, 'UTF-8', i)
|
||||
if f.getvalue() != expected[i]:
|
||||
print('xmlDoc.saveFormatFileTo() call failed.')
|
||||
print(' got: %s' % repr(f.getvalue()))
|
||||
print('expected: %s' % repr(expected[i]))
|
||||
sys.exit(1)
|
||||
doc.freeDoc()
|
||||
|
||||
def testSaveIntoOutputBuffer():
|
||||
"""
|
||||
Similar to the previous two tests, except this time we invoke the save
|
||||
methods on the output buffer object and pass in an XML node object.
|
||||
"""
|
||||
input = '<foo>Hello</foo>'
|
||||
expected = '''\
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<foo>Hello</foo>
|
||||
'''
|
||||
f = str_io()
|
||||
doc = libxml2.parseDoc(input)
|
||||
buf = libxml2.createOutputBuffer(f, 'UTF-8')
|
||||
buf.saveFileTo(doc, 'UTF-8')
|
||||
if f.getvalue() != expected:
|
||||
print('outputBuffer.saveFileTo() call failed.')
|
||||
print(' got: %s' % repr(f.getvalue()))
|
||||
print('expected: %s' % repr(expected))
|
||||
sys.exit(1)
|
||||
f = str_io()
|
||||
buf = libxml2.createOutputBuffer(f, 'UTF-8')
|
||||
buf.saveFormatFileTo(doc, 'UTF-8', 1)
|
||||
if f.getvalue() != expected:
|
||||
print('outputBuffer.saveFormatFileTo() call failed.')
|
||||
print(' got: %s' % repr(f.getvalue()))
|
||||
print('expected: %s' % repr(expected))
|
||||
sys.exit(1)
|
||||
doc.freeDoc()
|
||||
|
||||
if __name__ == '__main__':
|
||||
# Memory debug specific
|
||||
libxml2.debugMemory(1)
|
||||
|
||||
testSimpleBufferWrites()
|
||||
testSaveDocToBuffer()
|
||||
testSaveFormattedDocToBuffer()
|
||||
testSaveIntoOutputBuffer()
|
||||
|
||||
libxml2.cleanupParser()
|
||||
if libxml2.debugMemory(1) == 0:
|
||||
print("OK")
|
||||
else:
|
||||
print("Memory leak %d bytes" % (libxml2.debugMemory(1)))
|
||||
@@ -0,0 +1,35 @@
|
||||
#!/usr/bin/env python3
|
||||
import sys
|
||||
import setup_test
|
||||
import libxml2
|
||||
|
||||
# Memory debug specific
|
||||
libxml2.debugMemory(1)
|
||||
|
||||
ctxt = libxml2.createPushParser(None, "<foo", 4, "test.xml")
|
||||
ctxt.parseChunk("/>", 2, 1)
|
||||
doc = ctxt.doc()
|
||||
ctxt=None
|
||||
if doc.name != "test.xml":
|
||||
print("document name error")
|
||||
sys.exit(1)
|
||||
root = doc.children
|
||||
if root.name != "foo":
|
||||
print("root element name error")
|
||||
sys.exit(1)
|
||||
doc.freeDoc()
|
||||
i = 10000
|
||||
while i > 0:
|
||||
ctxt = libxml2.createPushParser(None, "<foo", 4, "test.xml")
|
||||
ctxt.parseChunk("/>", 2, 1)
|
||||
doc = ctxt.doc()
|
||||
doc.freeDoc()
|
||||
i = i -1
|
||||
ctxt=None
|
||||
|
||||
# Memory debug specific
|
||||
libxml2.cleanupParser()
|
||||
if libxml2.debugMemory(1) == 0:
|
||||
print("OK")
|
||||
else:
|
||||
print("Memory leak %d bytes" % (libxml2.debugMemory(1)))
|
||||
@@ -0,0 +1,64 @@
|
||||
#!/usr/bin/env python3
|
||||
import sys
|
||||
import setup_test
|
||||
import libxml2
|
||||
|
||||
# Memory debug specific
|
||||
libxml2.debugMemory(1)
|
||||
|
||||
log = ""
|
||||
|
||||
class callback:
|
||||
def startDocument(self):
|
||||
global log
|
||||
log = log + "startDocument:"
|
||||
|
||||
def endDocument(self):
|
||||
global log
|
||||
log = log + "endDocument:"
|
||||
|
||||
def startElement(self, tag, attrs):
|
||||
global log
|
||||
log = log + "startElement %s %s:" % (tag, attrs)
|
||||
|
||||
def endElement(self, tag):
|
||||
global log
|
||||
log = log + "endElement %s:" % (tag)
|
||||
|
||||
def characters(self, data):
|
||||
global log
|
||||
log = log + "characters: %s:" % (data)
|
||||
|
||||
def warning(self, msg):
|
||||
global log
|
||||
log = log + "warning: %s:" % (msg)
|
||||
|
||||
def error(self, msg):
|
||||
global log
|
||||
log = log + "error: %s:" % (msg)
|
||||
|
||||
def fatalError(self, msg):
|
||||
global log
|
||||
log = log + "fatalError: %s:" % (msg)
|
||||
|
||||
handler = callback()
|
||||
|
||||
ctxt = libxml2.createPushParser(handler, "<foo", 4, "test.xml")
|
||||
chunk = " url='tst'>b"
|
||||
ctxt.parseChunk(chunk, len(chunk), 0)
|
||||
chunk = "ar</foo>"
|
||||
ctxt.parseChunk(chunk, len(chunk), 1)
|
||||
ctxt=None
|
||||
|
||||
reference = "startDocument:startElement foo {'url': 'tst'}:characters: bar:endElement foo:endDocument:"
|
||||
if log != reference:
|
||||
print("Error got: %s" % log)
|
||||
print("Exprected: %s" % reference)
|
||||
sys.exit(1)
|
||||
|
||||
# Memory debug specific
|
||||
libxml2.cleanupParser()
|
||||
if libxml2.debugMemory(1) == 0:
|
||||
print("OK")
|
||||
else:
|
||||
print("Memory leak %d bytes" % (libxml2.debugMemory(1)))
|
||||
@@ -0,0 +1,64 @@
|
||||
#!/usr/bin/env python3
|
||||
import sys
|
||||
import setup_test
|
||||
import libxml2
|
||||
|
||||
# Memory debug specific
|
||||
libxml2.debugMemory(1)
|
||||
|
||||
log = ""
|
||||
|
||||
class callback:
|
||||
def startDocument(self):
|
||||
global log
|
||||
log = log + "startDocument:"
|
||||
|
||||
def endDocument(self):
|
||||
global log
|
||||
log = log + "endDocument:"
|
||||
|
||||
def startElement(self, tag, attrs):
|
||||
global log
|
||||
log = log + "startElement %s %s:" % (tag, attrs)
|
||||
|
||||
def endElement(self, tag):
|
||||
global log
|
||||
log = log + "endElement %s:" % (tag)
|
||||
|
||||
def characters(self, data):
|
||||
global log
|
||||
log = log + "characters: %s:" % (data)
|
||||
|
||||
def warning(self, msg):
|
||||
global log
|
||||
log = log + "warning: %s:" % (msg)
|
||||
|
||||
def error(self, msg):
|
||||
global log
|
||||
log = log + "error: %s:" % (msg)
|
||||
|
||||
def fatalError(self, msg):
|
||||
global log
|
||||
log = log + "fatalError: %s:" % (msg)
|
||||
|
||||
handler = callback()
|
||||
|
||||
ctxt = libxml2.htmlCreatePushParser(handler, "<foo", 4, "test.xml")
|
||||
chunk = " url='tst'>b"
|
||||
ctxt.htmlParseChunk(chunk, len(chunk), 0)
|
||||
chunk = "ar</foo>"
|
||||
ctxt.htmlParseChunk(chunk, len(chunk), 1)
|
||||
ctxt=None
|
||||
|
||||
reference = """startDocument:startElement html None:startElement body None:startElement foo {'url': 'tst'}:characters: bar:endElement foo:endElement body:endElement html:endDocument:"""
|
||||
if log != reference:
|
||||
print("Error got: %s" % log)
|
||||
print("Exprected: %s" % reference)
|
||||
sys.exit(1)
|
||||
|
||||
# Memory debug specific
|
||||
libxml2.cleanupParser()
|
||||
if libxml2.debugMemory(1) == 0:
|
||||
print("OK")
|
||||
else:
|
||||
print("Memory leak %d bytes" % (libxml2.debugMemory(1)))
|
||||
@@ -0,0 +1,446 @@
|
||||
#!/usr/bin/env python3
|
||||
# -*- coding: ISO-8859-1 -*-
|
||||
#
|
||||
# this tests the basic APIs of the XmlTextReader interface
|
||||
#
|
||||
import setup_test
|
||||
import libxml2
|
||||
import sys
|
||||
try:
|
||||
import StringIO
|
||||
str_io = StringIO.StringIO
|
||||
except:
|
||||
import io
|
||||
str_io = io.StringIO
|
||||
|
||||
# Memory debug specific
|
||||
libxml2.debugMemory(1)
|
||||
|
||||
f = str_io("""<a><b b1="b1"/><c>content of c</c></a>""")
|
||||
input = libxml2.inputBuffer(f)
|
||||
reader = input.newTextReader("test1")
|
||||
ret = reader.Read()
|
||||
if ret != 1:
|
||||
print("test1: Error reading to first element")
|
||||
sys.exit(1)
|
||||
if reader.Name() != "a" or reader.IsEmptyElement() != 0 or \
|
||||
reader.NodeType() != 1 or reader.HasAttributes() != 0:
|
||||
print("test1: Error reading the first element")
|
||||
sys.exit(1)
|
||||
ret = reader.Read()
|
||||
if ret != 1:
|
||||
print("test1: Error reading to second element")
|
||||
sys.exit(1)
|
||||
if reader.Name() != "b" or reader.IsEmptyElement() != 1 or \
|
||||
reader.NodeType() != 1 or reader.HasAttributes() != 1:
|
||||
print("test1: Error reading the second element")
|
||||
sys.exit(1)
|
||||
ret = reader.Read()
|
||||
if ret != 1:
|
||||
print("test1: Error reading to third element")
|
||||
sys.exit(1)
|
||||
if reader.Name() != "c" or reader.IsEmptyElement() != 0 or \
|
||||
reader.NodeType() != 1 or reader.HasAttributes() != 0:
|
||||
print("test1: Error reading the third element")
|
||||
sys.exit(1)
|
||||
ret = reader.Read()
|
||||
if ret != 1:
|
||||
print("test1: Error reading to text node")
|
||||
sys.exit(1)
|
||||
if reader.Name() != "#text" or reader.IsEmptyElement() != 0 or \
|
||||
reader.NodeType() != 3 or reader.HasAttributes() != 0 or \
|
||||
reader.Value() != "content of c":
|
||||
print("test1: Error reading the text node")
|
||||
sys.exit(1)
|
||||
ret = reader.Read()
|
||||
if ret != 1:
|
||||
print("test1: Error reading to end of third element")
|
||||
sys.exit(1)
|
||||
if reader.Name() != "c" or reader.IsEmptyElement() != 0 or \
|
||||
reader.NodeType() != 15 or reader.HasAttributes() != 0:
|
||||
print("test1: Error reading the end of third element")
|
||||
sys.exit(1)
|
||||
ret = reader.Read()
|
||||
if ret != 1:
|
||||
print("test1: Error reading to end of first element")
|
||||
sys.exit(1)
|
||||
if reader.Name() != "a" or reader.IsEmptyElement() != 0 or \
|
||||
reader.NodeType() != 15 or reader.HasAttributes() != 0:
|
||||
print("test1: Error reading the end of first element")
|
||||
sys.exit(1)
|
||||
ret = reader.Read()
|
||||
if ret != 0:
|
||||
print("test1: Error reading to end of document")
|
||||
sys.exit(1)
|
||||
|
||||
#
|
||||
# example from the XmlTextReader docs
|
||||
#
|
||||
f = str_io("""<test xmlns:dt="urn:datatypes" dt:type="int"/>""")
|
||||
input = libxml2.inputBuffer(f)
|
||||
reader = input.newTextReader("test2")
|
||||
|
||||
ret = reader.Read()
|
||||
if ret != 1:
|
||||
print("Error reading test element")
|
||||
sys.exit(1)
|
||||
if reader.GetAttributeNo(0) != "urn:datatypes" or \
|
||||
reader.GetAttributeNo(1) != "int" or \
|
||||
reader.GetAttributeNs("type", "urn:datatypes") != "int" or \
|
||||
reader.GetAttribute("dt:type") != "int":
|
||||
print("error reading test attributes")
|
||||
sys.exit(1)
|
||||
|
||||
#
|
||||
# example from the XmlTextReader docs
|
||||
#
|
||||
f = str_io("""<root xmlns:a="urn:456">
|
||||
<item>
|
||||
<ref href="a:b"/>
|
||||
</item>
|
||||
</root>""")
|
||||
input = libxml2.inputBuffer(f)
|
||||
reader = input.newTextReader("test3")
|
||||
|
||||
ret = reader.Read()
|
||||
while ret == 1:
|
||||
if reader.Name() == "ref":
|
||||
if reader.LookupNamespace("a") != "urn:456":
|
||||
print("error resolving namespace prefix")
|
||||
sys.exit(1)
|
||||
break
|
||||
ret = reader.Read()
|
||||
if ret != 1:
|
||||
print("Error finding the ref element")
|
||||
sys.exit(1)
|
||||
|
||||
#
|
||||
# Home made example for the various attribute access functions
|
||||
#
|
||||
f = str_io("""<testattr xmlns="urn:1" xmlns:a="urn:2" b="b" a:b="a:b"/>""")
|
||||
input = libxml2.inputBuffer(f)
|
||||
reader = input.newTextReader("test4")
|
||||
ret = reader.Read()
|
||||
if ret != 1:
|
||||
print("Error reading the testattr element")
|
||||
sys.exit(1)
|
||||
#
|
||||
# Attribute exploration by index
|
||||
#
|
||||
if reader.MoveToAttributeNo(0) != 1:
|
||||
print("Failed moveToAttribute(0)")
|
||||
sys.exit(1)
|
||||
if reader.Value() != "urn:1":
|
||||
print("Failed to read attribute(0)")
|
||||
sys.exit(1)
|
||||
if reader.Name() != "xmlns":
|
||||
print("Failed to read attribute(0) name")
|
||||
sys.exit(1)
|
||||
if reader.MoveToAttributeNo(1) != 1:
|
||||
print("Failed moveToAttribute(1)")
|
||||
sys.exit(1)
|
||||
if reader.Value() != "urn:2":
|
||||
print("Failed to read attribute(1)")
|
||||
sys.exit(1)
|
||||
if reader.Name() != "xmlns:a":
|
||||
print("Failed to read attribute(1) name")
|
||||
sys.exit(1)
|
||||
if reader.MoveToAttributeNo(2) != 1:
|
||||
print("Failed moveToAttribute(2)")
|
||||
sys.exit(1)
|
||||
if reader.Value() != "b":
|
||||
print("Failed to read attribute(2)")
|
||||
sys.exit(1)
|
||||
if reader.Name() != "b":
|
||||
print("Failed to read attribute(2) name")
|
||||
sys.exit(1)
|
||||
if reader.MoveToAttributeNo(3) != 1:
|
||||
print("Failed moveToAttribute(3)")
|
||||
sys.exit(1)
|
||||
if reader.Value() != "a:b":
|
||||
print("Failed to read attribute(3)")
|
||||
sys.exit(1)
|
||||
if reader.Name() != "a:b":
|
||||
print("Failed to read attribute(3) name")
|
||||
sys.exit(1)
|
||||
#
|
||||
# Attribute exploration by name
|
||||
#
|
||||
if reader.MoveToAttribute("xmlns") != 1:
|
||||
print("Failed moveToAttribute('xmlns')")
|
||||
sys.exit(1)
|
||||
if reader.Value() != "urn:1":
|
||||
print("Failed to read attribute('xmlns')")
|
||||
sys.exit(1)
|
||||
if reader.MoveToAttribute("xmlns:a") != 1:
|
||||
print("Failed moveToAttribute('xmlns')")
|
||||
sys.exit(1)
|
||||
if reader.Value() != "urn:2":
|
||||
print("Failed to read attribute('xmlns:a')")
|
||||
sys.exit(1)
|
||||
if reader.MoveToAttribute("b") != 1:
|
||||
print("Failed moveToAttribute('b')")
|
||||
sys.exit(1)
|
||||
if reader.Value() != "b":
|
||||
print("Failed to read attribute('b')")
|
||||
sys.exit(1)
|
||||
if reader.MoveToAttribute("a:b") != 1:
|
||||
print("Failed moveToAttribute('a:b')")
|
||||
sys.exit(1)
|
||||
if reader.Value() != "a:b":
|
||||
print("Failed to read attribute('a:b')")
|
||||
sys.exit(1)
|
||||
if reader.MoveToAttributeNs("b", "urn:2") != 1:
|
||||
print("Failed moveToAttribute('b', 'urn:2')")
|
||||
sys.exit(1)
|
||||
if reader.Value() != "a:b":
|
||||
print("Failed to read attribute('b', 'urn:2')")
|
||||
sys.exit(1)
|
||||
#
|
||||
# Go back and read in sequence
|
||||
#
|
||||
if reader.MoveToElement() != 1:
|
||||
print("Failed to move back to element")
|
||||
sys.exit(1)
|
||||
if reader.MoveToFirstAttribute() != 1:
|
||||
print("Failed to move to first attribute")
|
||||
sys.exit(1)
|
||||
if reader.Value() != "urn:1":
|
||||
print("Failed to read attribute(0)")
|
||||
sys.exit(1)
|
||||
if reader.Name() != "xmlns":
|
||||
print("Failed to read attribute(0) name")
|
||||
sys.exit(1)
|
||||
if reader.MoveToNextAttribute() != 1:
|
||||
print("Failed to move to next attribute")
|
||||
sys.exit(1)
|
||||
if reader.Value() != "urn:2":
|
||||
print("Failed to read attribute(1)")
|
||||
sys.exit(1)
|
||||
if reader.Name() != "xmlns:a":
|
||||
print("Failed to read attribute(1) name")
|
||||
sys.exit(1)
|
||||
if reader.MoveToNextAttribute() != 1:
|
||||
print("Failed to move to next attribute")
|
||||
sys.exit(1)
|
||||
if reader.Value() != "b":
|
||||
print("Failed to read attribute(2)")
|
||||
sys.exit(1)
|
||||
if reader.Name() != "b":
|
||||
print("Failed to read attribute(2) name")
|
||||
sys.exit(1)
|
||||
if reader.MoveToNextAttribute() != 1:
|
||||
print("Failed to move to next attribute")
|
||||
sys.exit(1)
|
||||
if reader.Value() != "a:b":
|
||||
print("Failed to read attribute(3)")
|
||||
sys.exit(1)
|
||||
if reader.Name() != "a:b":
|
||||
print("Failed to read attribute(3) name")
|
||||
sys.exit(1)
|
||||
if reader.MoveToNextAttribute() != 0:
|
||||
print("Failed to detect last attribute")
|
||||
sys.exit(1)
|
||||
|
||||
|
||||
#
|
||||
# a couple of tests for namespace nodes
|
||||
#
|
||||
f = str_io("""<a xmlns="http://example.com/foo"/>""")
|
||||
input = libxml2.inputBuffer(f)
|
||||
reader = input.newTextReader("test6")
|
||||
ret = reader.Read()
|
||||
if ret != 1:
|
||||
print("test6: failed to Read()")
|
||||
sys.exit(1)
|
||||
ret = reader.MoveToFirstAttribute()
|
||||
if ret != 1:
|
||||
print("test6: failed to MoveToFirstAttribute()")
|
||||
sys.exit(1)
|
||||
if reader.NamespaceUri() != "http://www.w3.org/2000/xmlns/" or \
|
||||
reader.LocalName() != "xmlns" or reader.Name() != "xmlns" or \
|
||||
reader.Value() != "http://example.com/foo" or reader.NodeType() != 2:
|
||||
print("test6: failed to read the namespace node")
|
||||
sys.exit(1)
|
||||
|
||||
f = str_io("""<a xmlns:prefix="http://example.com/foo"/>""")
|
||||
input = libxml2.inputBuffer(f)
|
||||
reader = input.newTextReader("test7")
|
||||
ret = reader.Read()
|
||||
if ret != 1:
|
||||
print("test7: failed to Read()")
|
||||
sys.exit(1)
|
||||
ret = reader.MoveToFirstAttribute()
|
||||
if ret != 1:
|
||||
print("test7: failed to MoveToFirstAttribute()")
|
||||
sys.exit(1)
|
||||
if reader.NamespaceUri() != "http://www.w3.org/2000/xmlns/" or \
|
||||
reader.LocalName() != "prefix" or reader.Name() != "xmlns:prefix" or \
|
||||
reader.Value() != "http://example.com/foo" or reader.NodeType() != 2:
|
||||
print("test7: failed to read the namespace node")
|
||||
sys.exit(1)
|
||||
|
||||
#
|
||||
# Test for a limit case:
|
||||
#
|
||||
f = str_io("""<a/>""")
|
||||
input = libxml2.inputBuffer(f)
|
||||
reader = input.newTextReader("test8")
|
||||
ret = reader.Read()
|
||||
if ret != 1:
|
||||
print("test8: failed to read the node")
|
||||
sys.exit(1)
|
||||
if reader.Name() != "a" or reader.IsEmptyElement() != 1:
|
||||
print("test8: failed to analyze the node")
|
||||
sys.exit(1)
|
||||
ret = reader.Read()
|
||||
if ret != 0:
|
||||
print("test8: failed to detect the EOF")
|
||||
sys.exit(1)
|
||||
|
||||
#
|
||||
# Another test provided by Stéphane Bidoul and checked with C#
|
||||
#
|
||||
def tst_reader(s):
|
||||
f = str_io(s)
|
||||
input = libxml2.inputBuffer(f)
|
||||
reader = input.newTextReader("tst")
|
||||
res = ""
|
||||
while reader.Read():
|
||||
res=res + "%s (%s) [%s] %d %d\n" % (reader.NodeType(),reader.Name(),
|
||||
reader.Value(), reader.IsEmptyElement(),
|
||||
reader.Depth())
|
||||
if reader.NodeType() == 1: # Element
|
||||
while reader.MoveToNextAttribute():
|
||||
res = res + "-- %s (%s) [%s] %d %d\n" % (reader.NodeType(),
|
||||
reader.Name(),reader.Value(),
|
||||
reader.IsEmptyElement(), reader.Depth())
|
||||
return res
|
||||
|
||||
doc="""<a><b b1="b1"/><c>content of c</c></a>"""
|
||||
expect="""1 (a) [None] 0 0
|
||||
1 (b) [None] 1 1
|
||||
-- 2 (b1) [b1] 0 2
|
||||
1 (c) [None] 0 1
|
||||
3 (#text) [content of c] 0 2
|
||||
15 (c) [None] 0 1
|
||||
15 (a) [None] 0 0
|
||||
"""
|
||||
res = tst_reader(doc)
|
||||
if res != expect:
|
||||
print("test5 failed")
|
||||
print(res)
|
||||
sys.exit(1)
|
||||
|
||||
doc="""<test><b/><c/></test>"""
|
||||
expect="""1 (test) [None] 0 0
|
||||
1 (b) [None] 1 1
|
||||
1 (c) [None] 1 1
|
||||
15 (test) [None] 0 0
|
||||
"""
|
||||
res = tst_reader(doc)
|
||||
if res != expect:
|
||||
print("test9 failed")
|
||||
print(res)
|
||||
sys.exit(1)
|
||||
|
||||
doc="""<a><b>bbb</b><c>ccc</c></a>"""
|
||||
expect="""1 (a) [None] 0 0
|
||||
1 (b) [None] 0 1
|
||||
3 (#text) [bbb] 0 2
|
||||
15 (b) [None] 0 1
|
||||
1 (c) [None] 0 1
|
||||
3 (#text) [ccc] 0 2
|
||||
15 (c) [None] 0 1
|
||||
15 (a) [None] 0 0
|
||||
"""
|
||||
res = tst_reader(doc)
|
||||
if res != expect:
|
||||
print("test10 failed")
|
||||
print(res)
|
||||
sys.exit(1)
|
||||
|
||||
doc="""<test a="a"/>"""
|
||||
expect="""1 (test) [None] 1 0
|
||||
-- 2 (a) [a] 0 1
|
||||
"""
|
||||
res = tst_reader(doc)
|
||||
if res != expect:
|
||||
print("test11 failed")
|
||||
print(res)
|
||||
sys.exit(1)
|
||||
|
||||
doc="""<test><a>aaa</a><b/></test>"""
|
||||
expect="""1 (test) [None] 0 0
|
||||
1 (a) [None] 0 1
|
||||
3 (#text) [aaa] 0 2
|
||||
15 (a) [None] 0 1
|
||||
1 (b) [None] 1 1
|
||||
15 (test) [None] 0 0
|
||||
"""
|
||||
res = tst_reader(doc)
|
||||
if res != expect:
|
||||
print("test12 failed")
|
||||
print(res)
|
||||
sys.exit(1)
|
||||
|
||||
doc="""<test><p></p></test>"""
|
||||
expect="""1 (test) [None] 0 0
|
||||
1 (p) [None] 0 1
|
||||
15 (p) [None] 0 1
|
||||
15 (test) [None] 0 0
|
||||
"""
|
||||
res = tst_reader(doc)
|
||||
if res != expect:
|
||||
print("test13 failed")
|
||||
print(res)
|
||||
sys.exit(1)
|
||||
|
||||
doc="""<p></p>"""
|
||||
expect="""1 (p) [None] 0 0
|
||||
15 (p) [None] 0 0
|
||||
"""
|
||||
res = tst_reader(doc)
|
||||
if res != expect:
|
||||
print("test14 failed")
|
||||
print(res)
|
||||
sys.exit(1)
|
||||
|
||||
#
|
||||
# test from bug #108801
|
||||
#
|
||||
doc="""<?xml version="1.0" standalone="no"?>
|
||||
<!DOCTYPE article PUBLIC "-//OASIS//DTD DocBook XML V4.1.2//EN"
|
||||
"http://www.oasis-open.org/docbook/xml/4.1.2/docbookx.dtd" [
|
||||
]>
|
||||
|
||||
<article>
|
||||
xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx
|
||||
</article>
|
||||
"""
|
||||
expect="""10 (article) [None] 0 0
|
||||
1 (article) [None] 0 0
|
||||
3 (#text) [
|
||||
xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx
|
||||
] 0 1
|
||||
15 (article) [None] 0 0
|
||||
"""
|
||||
res = tst_reader(doc)
|
||||
if res != expect:
|
||||
print("test15 failed")
|
||||
print(res)
|
||||
sys.exit(1)
|
||||
|
||||
#
|
||||
# cleanup for memory allocation counting
|
||||
#
|
||||
del f
|
||||
del input
|
||||
del reader
|
||||
|
||||
# Memory debug specific
|
||||
libxml2.cleanupParser()
|
||||
if libxml2.debugMemory(1) == 0:
|
||||
print("OK")
|
||||
else:
|
||||
print("Memory leak %d bytes" % (libxml2.debugMemory(1)))
|
||||
@@ -0,0 +1,337 @@
|
||||
#!/usr/bin/env python3
|
||||
# -*- coding: utf-8 -*-
|
||||
#
|
||||
# this tests the DTD validation with the XmlTextReader interface
|
||||
#
|
||||
import sys
|
||||
import glob
|
||||
import os
|
||||
import setup_test
|
||||
import libxml2
|
||||
try:
|
||||
import StringIO
|
||||
str_io = StringIO.StringIO
|
||||
except:
|
||||
import io
|
||||
str_io = io.StringIO
|
||||
|
||||
# Memory debug specific
|
||||
libxml2.debugMemory(1)
|
||||
|
||||
err = ""
|
||||
basedir = os.path.dirname(os.path.realpath(__file__))
|
||||
dir_prefix = os.path.realpath(os.path.join(basedir, "..", "..", "test", "valid"))
|
||||
|
||||
# This dictionary reflects the contents of the files
|
||||
# ../../test/valid/*.xml.err that are not empty, except that
|
||||
# the file paths in the messages start with ../../test/
|
||||
|
||||
expect = {
|
||||
'766956':
|
||||
"""{0}/dtds/766956.dtd:2: parser error : PEReference: expecting ';'
|
||||
%ä%ent;
|
||||
^
|
||||
{0}/dtds/766956.dtd:2: parser error : Content error in the external subset
|
||||
%ä%ent;
|
||||
^
|
||||
Entity: line 1:
|
||||
value
|
||||
^
|
||||
""".format(dir_prefix),
|
||||
'781333':
|
||||
"""{0}/781333.xml:4: element a: validity error : Element a content does not follow the DTD, expecting ( ..., got
|
||||
<a/>
|
||||
^
|
||||
{0}/781333.xml:5: element a: validity error : Element a content does not follow the DTD, Expecting more children
|
||||
|
||||
^
|
||||
""".format(dir_prefix),
|
||||
'cond_sect2':
|
||||
"""{0}/dtds/cond_sect2.dtd:15: parser error : Parameter entity must match extSubsetDecl
|
||||
%ent;
|
||||
^
|
||||
Entity: line 1:
|
||||
]]>
|
||||
^
|
||||
{0}/dtds/cond_sect2.dtd:15: parser error : Content error in the external subset
|
||||
%ent;
|
||||
^
|
||||
Entity: line 1:
|
||||
]]>
|
||||
^
|
||||
""".format(dir_prefix),
|
||||
'rss':
|
||||
"""{0}/rss.xml:177: element rss: validity error : Element rss does not carry attribute version
|
||||
</rss>
|
||||
^
|
||||
""".format(dir_prefix),
|
||||
't8':
|
||||
"""{0}/t8.xml:6: parser error : Content error in the internal subset
|
||||
%defroot; %defmiddle; %deftest;
|
||||
^
|
||||
Entity: line 1:
|
||||
<!ELEMENT root (middle) >
|
||||
^
|
||||
""".format(dir_prefix),
|
||||
't8a':
|
||||
"""{0}/t8a.xml:6: parser error : Content error in the internal subset
|
||||
%defroot;%defmiddle;%deftest;
|
||||
^
|
||||
Entity: line 1:
|
||||
<!ELEMENT root (middle) >
|
||||
^
|
||||
""".format(dir_prefix),
|
||||
'xlink':
|
||||
"""{0}/xlink.xml:450: element termdef: validity error : ID dt-arc already defined
|
||||
<p><termdef id="dt-arc" term="Arc">An <ter
|
||||
^
|
||||
validity error : attribute def line 199 references an unknown ID "dt-xlg"
|
||||
""".format(dir_prefix),
|
||||
}
|
||||
|
||||
# Add prefix_dir and extension to the keys
|
||||
expect = {os.path.join(dir_prefix, key + ".xml"): val for key, val in expect.items()}
|
||||
|
||||
def callback(ctx, str):
|
||||
global err
|
||||
err = err + "%s" % (str)
|
||||
libxml2.registerErrorHandler(callback, "")
|
||||
|
||||
parsing_error_files = ["766956", "cond_sect2", "t8", "t8a", "pe-in-text-decl"]
|
||||
expect_parsing_error = [os.path.join(dir_prefix, f + ".xml") for f in parsing_error_files]
|
||||
|
||||
valid_files = glob.glob(os.path.join(dir_prefix, "*.x*"))
|
||||
assert valid_files, "found no valid files in '{}'".format(dir_prefix)
|
||||
valid_files.sort()
|
||||
failures = 0
|
||||
for file in valid_files:
|
||||
err = ""
|
||||
reader = libxml2.newTextReaderFilename(file)
|
||||
#print "%s:" % (file)
|
||||
reader.SetParserProp(libxml2.PARSER_VALIDATE, 1)
|
||||
ret = reader.Read()
|
||||
while ret == 1:
|
||||
ret = reader.Read()
|
||||
if ret != 0 and file not in expect_parsing_error:
|
||||
print("Error parsing and validating %s" % (file))
|
||||
#sys.exit(1)
|
||||
if file in expect and err != expect[file]:
|
||||
failures += 1
|
||||
print("Error: ", err)
|
||||
if file in expect:
|
||||
print("Expected: ", expect[file])
|
||||
|
||||
if failures:
|
||||
print("Failed %d tests" % failures)
|
||||
sys.exit(1)
|
||||
|
||||
#
|
||||
# another separate test based on Stephane Bidoul one
|
||||
#
|
||||
s = """
|
||||
<!DOCTYPE test [
|
||||
<!ELEMENT test (x,b)>
|
||||
<!ELEMENT x (c)>
|
||||
<!ELEMENT b (#PCDATA)>
|
||||
<!ELEMENT c (#PCDATA)>
|
||||
<!ENTITY x "<x><c>xxx</c></x>">
|
||||
]>
|
||||
<test>
|
||||
&x;
|
||||
<b>bbb</b>
|
||||
</test>
|
||||
"""
|
||||
expect="""10,test
|
||||
1,test
|
||||
14,#text
|
||||
1,x
|
||||
1,c
|
||||
3,#text
|
||||
15,c
|
||||
15,x
|
||||
14,#text
|
||||
1,b
|
||||
3,#text
|
||||
15,b
|
||||
14,#text
|
||||
15,test
|
||||
"""
|
||||
res=""
|
||||
err=""
|
||||
|
||||
input = libxml2.inputBuffer(str_io(s))
|
||||
reader = input.newTextReader("test2")
|
||||
reader.SetParserProp(libxml2.PARSER_LOADDTD,1)
|
||||
reader.SetParserProp(libxml2.PARSER_DEFAULTATTRS,1)
|
||||
reader.SetParserProp(libxml2.PARSER_SUBST_ENTITIES,1)
|
||||
reader.SetParserProp(libxml2.PARSER_VALIDATE,1)
|
||||
while reader.Read() == 1:
|
||||
res = res + "%s,%s\n" % (reader.NodeType(),reader.Name())
|
||||
|
||||
if res != expect:
|
||||
print("test2 failed: unexpected output")
|
||||
print(res)
|
||||
sys.exit(1)
|
||||
if err != "":
|
||||
print("test2 failed: validation error found")
|
||||
print(err)
|
||||
sys.exit(1)
|
||||
|
||||
#
|
||||
# Another test for external entity parsing and validation
|
||||
#
|
||||
|
||||
s = """<!DOCTYPE test [
|
||||
<!ELEMENT test (x)>
|
||||
<!ELEMENT x (#PCDATA)>
|
||||
<!ENTITY e SYSTEM "tst.ent">
|
||||
]>
|
||||
<test>
|
||||
&e;
|
||||
</test>
|
||||
"""
|
||||
tst_ent = """<x>hello</x>"""
|
||||
expect="""10 test
|
||||
1 test
|
||||
14 #text
|
||||
1 x
|
||||
3 #text
|
||||
15 x
|
||||
14 #text
|
||||
15 test
|
||||
"""
|
||||
res=""
|
||||
|
||||
def myResolver(URL, ID, ctxt):
|
||||
if URL == "tst.ent":
|
||||
return(str_io(tst_ent))
|
||||
return None
|
||||
|
||||
libxml2.setEntityLoader(myResolver)
|
||||
|
||||
input = libxml2.inputBuffer(str_io(s))
|
||||
reader = input.newTextReader("test3")
|
||||
reader.SetParserProp(libxml2.PARSER_LOADDTD,1)
|
||||
reader.SetParserProp(libxml2.PARSER_DEFAULTATTRS,1)
|
||||
reader.SetParserProp(libxml2.PARSER_SUBST_ENTITIES,1)
|
||||
reader.SetParserProp(libxml2.PARSER_VALIDATE,1)
|
||||
while reader.Read() == 1:
|
||||
res = res + "%s %s\n" % (reader.NodeType(),reader.Name())
|
||||
|
||||
if res != expect:
|
||||
print("test3 failed: unexpected output")
|
||||
print(res)
|
||||
sys.exit(1)
|
||||
if err != "":
|
||||
print("test3 failed: validation error found")
|
||||
print(err)
|
||||
sys.exit(1)
|
||||
|
||||
#
|
||||
# Another test for recursive entity parsing, validation, and replacement of
|
||||
# entities, making sure the entity ref node doesn't show up in that case
|
||||
#
|
||||
|
||||
s = """<!DOCTYPE test [
|
||||
<!ELEMENT test (x, x)>
|
||||
<!ELEMENT x (y)>
|
||||
<!ELEMENT y (#PCDATA)>
|
||||
<!ENTITY x "<x>&y;</x>">
|
||||
<!ENTITY y "<y>yyy</y>">
|
||||
]>
|
||||
<test>
|
||||
&x;
|
||||
&x;
|
||||
</test>"""
|
||||
expect="""10 test 0
|
||||
1 test 0
|
||||
14 #text 1
|
||||
1 x 1
|
||||
1 y 2
|
||||
3 #text 3
|
||||
15 y 2
|
||||
15 x 1
|
||||
14 #text 1
|
||||
1 x 1
|
||||
1 y 2
|
||||
3 #text 3
|
||||
15 y 2
|
||||
15 x 1
|
||||
14 #text 1
|
||||
15 test 0
|
||||
"""
|
||||
res=""
|
||||
err=""
|
||||
|
||||
input = libxml2.inputBuffer(str_io(s))
|
||||
reader = input.newTextReader("test4")
|
||||
reader.SetParserProp(libxml2.PARSER_LOADDTD,1)
|
||||
reader.SetParserProp(libxml2.PARSER_DEFAULTATTRS,1)
|
||||
reader.SetParserProp(libxml2.PARSER_SUBST_ENTITIES,1)
|
||||
reader.SetParserProp(libxml2.PARSER_VALIDATE,1)
|
||||
while reader.Read() == 1:
|
||||
res = res + "%s %s %d\n" % (reader.NodeType(),reader.Name(),reader.Depth())
|
||||
|
||||
if res != expect:
|
||||
print("test4 failed: unexpected output")
|
||||
print(res)
|
||||
sys.exit(1)
|
||||
if err != "":
|
||||
print("test4 failed: validation error found")
|
||||
print(err)
|
||||
sys.exit(1)
|
||||
|
||||
#
|
||||
# The same test but without entity substitution this time
|
||||
#
|
||||
|
||||
s = """<!DOCTYPE test [
|
||||
<!ELEMENT test (x, x)>
|
||||
<!ELEMENT x (y)>
|
||||
<!ELEMENT y (#PCDATA)>
|
||||
<!ENTITY x "<x>&y;</x>">
|
||||
<!ENTITY y "<y>yyy</y>">
|
||||
]>
|
||||
<test>
|
||||
&x;
|
||||
&x;
|
||||
</test>"""
|
||||
expect="""10 test 0
|
||||
1 test 0
|
||||
14 #text 1
|
||||
5 x 1
|
||||
14 #text 1
|
||||
5 x 1
|
||||
14 #text 1
|
||||
15 test 0
|
||||
"""
|
||||
res=""
|
||||
err=""
|
||||
|
||||
input = libxml2.inputBuffer(str_io(s))
|
||||
reader = input.newTextReader("test5")
|
||||
reader.SetParserProp(libxml2.PARSER_VALIDATE,1)
|
||||
while reader.Read() == 1:
|
||||
res = res + "%s %s %d\n" % (reader.NodeType(),reader.Name(),reader.Depth())
|
||||
|
||||
if res != expect:
|
||||
print("test5 failed: unexpected output")
|
||||
print(res)
|
||||
sys.exit(1)
|
||||
if err != "":
|
||||
print("test5 failed: validation error found")
|
||||
print(err)
|
||||
sys.exit(1)
|
||||
|
||||
#
|
||||
# cleanup
|
||||
#
|
||||
del input
|
||||
del reader
|
||||
|
||||
# Memory debug specific
|
||||
libxml2.cleanupParser()
|
||||
if libxml2.debugMemory(1) == 0:
|
||||
print("OK")
|
||||
else:
|
||||
print("Memory leak %d bytes" % (libxml2.debugMemory(1)))
|
||||
@@ -0,0 +1,160 @@
|
||||
#!/usr/bin/env python3
|
||||
#
|
||||
# this tests the entities substitutions with the XmlTextReader interface
|
||||
#
|
||||
import sys
|
||||
import setup_test
|
||||
import libxml2
|
||||
try:
|
||||
import StringIO
|
||||
str_io = StringIO.StringIO
|
||||
except:
|
||||
import io
|
||||
str_io = io.StringIO
|
||||
|
||||
docstr="""<?xml version='1.0'?>
|
||||
<!DOCTYPE doc [
|
||||
<!ENTITY tst "<p>test</p>">
|
||||
]>
|
||||
<doc>&tst;</doc>"""
|
||||
|
||||
# Memory debug specific
|
||||
libxml2.debugMemory(1)
|
||||
|
||||
#
|
||||
# First test, normal don't substitute entities.
|
||||
#
|
||||
f = str_io(docstr)
|
||||
input = libxml2.inputBuffer(f)
|
||||
reader = input.newTextReader("test_noent")
|
||||
ret = reader.Read()
|
||||
if ret != 1:
|
||||
print("Error reading to root")
|
||||
sys.exit(1)
|
||||
if reader.Name() == "doc" or reader.NodeType() == 10:
|
||||
ret = reader.Read()
|
||||
if ret != 1:
|
||||
print("Error reading to root")
|
||||
sys.exit(1)
|
||||
if reader.Name() != "doc" or reader.NodeType() != 1:
|
||||
print("test_normal: Error reading the root element")
|
||||
sys.exit(1)
|
||||
ret = reader.Read()
|
||||
if ret != 1:
|
||||
print("test_normal: Error reading to the entity")
|
||||
sys.exit(1)
|
||||
if reader.Name() != "tst" or reader.NodeType() != 5:
|
||||
print("test_normal: Error reading the entity")
|
||||
sys.exit(1)
|
||||
ret = reader.Read()
|
||||
if ret != 1:
|
||||
print("test_normal: Error reading to the end of root")
|
||||
sys.exit(1)
|
||||
if reader.Name() != "doc" or reader.NodeType() != 15:
|
||||
print("test_normal: Error reading the end of the root element")
|
||||
sys.exit(1)
|
||||
ret = reader.Read()
|
||||
if ret != 0:
|
||||
print("test_normal: Error detecting the end")
|
||||
sys.exit(1)
|
||||
|
||||
#
|
||||
# Second test, completely substitute the entities.
|
||||
#
|
||||
f = str_io(docstr)
|
||||
input = libxml2.inputBuffer(f)
|
||||
reader = input.newTextReader("test_noent")
|
||||
reader.SetParserProp(libxml2.PARSER_SUBST_ENTITIES, 1)
|
||||
ret = reader.Read()
|
||||
if ret != 1:
|
||||
print("Error reading to root")
|
||||
sys.exit(1)
|
||||
if reader.Name() == "doc" or reader.NodeType() == 10:
|
||||
ret = reader.Read()
|
||||
if ret != 1:
|
||||
print("Error reading to root")
|
||||
sys.exit(1)
|
||||
if reader.Name() != "doc" or reader.NodeType() != 1:
|
||||
print("test_noent: Error reading the root element")
|
||||
sys.exit(1)
|
||||
ret = reader.Read()
|
||||
if ret != 1:
|
||||
print("test_noent: Error reading to the entity content")
|
||||
sys.exit(1)
|
||||
if reader.Name() != "p" or reader.NodeType() != 1:
|
||||
print("test_noent: Error reading the p element from entity")
|
||||
sys.exit(1)
|
||||
ret = reader.Read()
|
||||
if ret != 1:
|
||||
print("test_noent: Error reading to the text node")
|
||||
sys.exit(1)
|
||||
if reader.NodeType() != 3 or reader.Value() != "test":
|
||||
print("test_noent: Error reading the text node")
|
||||
sys.exit(1)
|
||||
ret = reader.Read()
|
||||
if ret != 1:
|
||||
print("test_noent: Error reading to the end of p element")
|
||||
sys.exit(1)
|
||||
if reader.Name() != "p" or reader.NodeType() != 15:
|
||||
print("test_noent: Error reading the end of the p element")
|
||||
sys.exit(1)
|
||||
ret = reader.Read()
|
||||
if ret != 1:
|
||||
print("test_noent: Error reading to the end of root")
|
||||
sys.exit(1)
|
||||
if reader.Name() != "doc" or reader.NodeType() != 15:
|
||||
print("test_noent: Error reading the end of the root element")
|
||||
sys.exit(1)
|
||||
ret = reader.Read()
|
||||
if ret != 0:
|
||||
print("test_noent: Error detecting the end")
|
||||
sys.exit(1)
|
||||
|
||||
#
|
||||
# third test, crazy stuff about empty element in external parsed entities
|
||||
#
|
||||
s = """<!DOCTYPE struct [
|
||||
<!ENTITY simplestruct2.ent SYSTEM "simplestruct2.ent">
|
||||
]>
|
||||
<struct>&simplestruct2.ent;</struct>
|
||||
"""
|
||||
expect="""10 struct 0 0
|
||||
1 struct 0 0
|
||||
1 descr 1 1
|
||||
15 struct 0 0
|
||||
"""
|
||||
res=""
|
||||
simplestruct2_ent="""<descr/>"""
|
||||
|
||||
def myResolver(URL, ID, ctxt):
|
||||
if URL == "simplestruct2.ent":
|
||||
return(str_io(simplestruct2_ent))
|
||||
return None
|
||||
|
||||
libxml2.setEntityLoader(myResolver)
|
||||
|
||||
input = libxml2.inputBuffer(str_io(s))
|
||||
reader = input.newTextReader("test3")
|
||||
reader.SetParserProp(libxml2.PARSER_SUBST_ENTITIES,1)
|
||||
while reader.Read() == 1:
|
||||
res = res + "%s %s %d %d\n" % (reader.NodeType(),reader.Name(),
|
||||
reader.Depth(),reader.IsEmptyElement())
|
||||
|
||||
if res != expect:
|
||||
print("test3 failed: unexpected output")
|
||||
print(res)
|
||||
sys.exit(1)
|
||||
|
||||
#
|
||||
# cleanup
|
||||
#
|
||||
del f
|
||||
del input
|
||||
del reader
|
||||
|
||||
# Memory debug specific
|
||||
libxml2.cleanupParser()
|
||||
if libxml2.debugMemory(1) == 0:
|
||||
print("OK")
|
||||
else:
|
||||
print("Memory leak %d bytes" % (libxml2.debugMemory(1)))
|
||||
@@ -0,0 +1,50 @@
|
||||
#!/usr/bin/env python3
|
||||
#
|
||||
# this tests the basic APIs of the XmlTextReader interface
|
||||
#
|
||||
import setup_test
|
||||
import libxml2
|
||||
import sys
|
||||
try:
|
||||
import StringIO
|
||||
str_io = StringIO.StringIO
|
||||
except:
|
||||
import io
|
||||
str_io = io.StringIO
|
||||
|
||||
# Memory debug specific
|
||||
libxml2.debugMemory(1)
|
||||
|
||||
def tst_reader(s):
|
||||
f = str_io(s)
|
||||
input = libxml2.inputBuffer(f)
|
||||
reader = input.newTextReader("tst")
|
||||
res = ""
|
||||
while reader.Read():
|
||||
res=res + "%s (%s) [%s] %d\n" % (reader.NodeType(),reader.Name(),
|
||||
reader.Value(), reader.IsEmptyElement())
|
||||
if reader.NodeType() == 1: # Element
|
||||
while reader.MoveToNextAttribute():
|
||||
res = res + "-- %s (%s) [%s]\n" % (reader.NodeType(),
|
||||
reader.Name(),reader.Value())
|
||||
return res
|
||||
|
||||
expect="""1 (test) [None] 0
|
||||
1 (b) [None] 1
|
||||
1 (c) [None] 1
|
||||
15 (test) [None] 0
|
||||
"""
|
||||
|
||||
res = tst_reader("""<test><b/><c/></test>""")
|
||||
|
||||
if res != expect:
|
||||
print("Did not get the expected error message:")
|
||||
print(res)
|
||||
sys.exit(1)
|
||||
|
||||
# Memory debug specific
|
||||
libxml2.cleanupParser()
|
||||
if libxml2.debugMemory(1) == 0:
|
||||
print("OK")
|
||||
else:
|
||||
print("Memory leak %d bytes" % (libxml2.debugMemory(1)))
|
||||
@@ -0,0 +1,49 @@
|
||||
#!/usr/bin/env python3
|
||||
#
|
||||
# this tests the Expand() API of the xmlTextReader interface
|
||||
# this extract the Dragon bibliography entries from the XML specification
|
||||
#
|
||||
import setup_test
|
||||
import libxml2
|
||||
import os
|
||||
import sys
|
||||
|
||||
# Memory debug specific
|
||||
libxml2.debugMemory(1)
|
||||
|
||||
expect="""<bibl id="Aho" key="Aho/Ullman">Aho, Alfred V.,
|
||||
Ravi Sethi, and Jeffrey D. Ullman.
|
||||
<emph>Compilers: Principles, Techniques, and Tools</emph>.
|
||||
Reading: Addison-Wesley, 1986, rpt. corr. 1988.</bibl>"""
|
||||
|
||||
basedir = os.path.dirname(os.path.realpath(__file__))
|
||||
f = open(os.path.join(basedir, '../../test/valid/REC-xml-19980210.xml'), 'rb')
|
||||
input = libxml2.inputBuffer(f)
|
||||
reader = input.newTextReader("REC")
|
||||
res=""
|
||||
while reader.Read() > 0:
|
||||
while reader.Name() == 'bibl':
|
||||
node = reader.Expand() # expand the subtree
|
||||
if node.xpathEval("@id = 'Aho'"): # use XPath on it
|
||||
res = res + node.serialize()
|
||||
if reader.Next() != 1: # skip the subtree
|
||||
break;
|
||||
|
||||
if res != expect:
|
||||
print("Error: didn't get the expected output")
|
||||
print("got '%s'" % (res))
|
||||
print("expected '%s'" % (expect))
|
||||
|
||||
|
||||
#
|
||||
# cleanup
|
||||
#
|
||||
del input
|
||||
del reader
|
||||
|
||||
# Memory debug specific
|
||||
libxml2.cleanupParser()
|
||||
if libxml2.debugMemory(1) == 0:
|
||||
print("OK")
|
||||
else:
|
||||
print("Memory leak %d bytes" % (libxml2.debugMemory(1)))
|
||||
@@ -0,0 +1,128 @@
|
||||
#!/usr/bin/env python3
|
||||
#
|
||||
# this tests the entities substitutions with the XmlTextReader interface
|
||||
#
|
||||
import sys
|
||||
import setup_test
|
||||
import libxml2
|
||||
try:
|
||||
import StringIO
|
||||
str_io = StringIO.StringIO
|
||||
except:
|
||||
import io
|
||||
str_io = io.StringIO
|
||||
|
||||
schema="""<element name="foo" xmlns="http://relaxng.org/ns/structure/1.0"
|
||||
datatypeLibrary="http://www.w3.org/2001/XMLSchema-datatypes">
|
||||
<oneOrMore>
|
||||
<element name="label">
|
||||
<text/>
|
||||
</element>
|
||||
<optional>
|
||||
<element name="opt">
|
||||
<empty/>
|
||||
</element>
|
||||
</optional>
|
||||
<element name="item">
|
||||
<data type="byte"/>
|
||||
</element>
|
||||
</oneOrMore>
|
||||
</element>
|
||||
"""
|
||||
# Memory debug specific
|
||||
libxml2.debugMemory(1)
|
||||
|
||||
#
|
||||
# Parse the Relax NG Schemas
|
||||
#
|
||||
rngp = libxml2.relaxNGNewMemParserCtxt(schema, len(schema))
|
||||
rngs = rngp.relaxNGParse()
|
||||
del rngp
|
||||
|
||||
#
|
||||
# Parse and validate the correct document
|
||||
#
|
||||
docstr="""<foo>
|
||||
<label>some text</label>
|
||||
<item>100</item>
|
||||
</foo>"""
|
||||
|
||||
f = str_io(docstr)
|
||||
input = libxml2.inputBuffer(f)
|
||||
reader = input.newTextReader("correct")
|
||||
reader.RelaxNGSetSchema(rngs)
|
||||
ret = reader.Read()
|
||||
while ret == 1:
|
||||
ret = reader.Read()
|
||||
|
||||
if ret != 0:
|
||||
print("Error parsing the document")
|
||||
sys.exit(1)
|
||||
|
||||
if reader.IsValid() != 1:
|
||||
print("Document failed to validate")
|
||||
sys.exit(1)
|
||||
|
||||
#
|
||||
# Parse and validate the incorrect document
|
||||
#
|
||||
docstr="""<foo>
|
||||
<label>some text</label>
|
||||
<item>1000</item>
|
||||
</foo>"""
|
||||
|
||||
err=""
|
||||
# RNG errors are not as good as before , TODO
|
||||
#expect="""RNG validity error: file error line 3 element text
|
||||
#Type byte doesn't allow value '1000'
|
||||
#RNG validity error: file error line 3 element text
|
||||
#Error validating datatype byte
|
||||
#RNG validity error: file error line 3 element text
|
||||
#Element item failed to validate content
|
||||
#"""
|
||||
expect="""Type byte doesn't allow value '1000'
|
||||
Error validating datatype byte
|
||||
Element item failed to validate content
|
||||
"""
|
||||
|
||||
def callback(ctx, str):
|
||||
global err
|
||||
err = err + "%s" % (str)
|
||||
libxml2.registerErrorHandler(callback, "")
|
||||
|
||||
f = str_io(docstr)
|
||||
input = libxml2.inputBuffer(f)
|
||||
reader = input.newTextReader("error")
|
||||
reader.RelaxNGSetSchema(rngs)
|
||||
ret = reader.Read()
|
||||
while ret == 1:
|
||||
ret = reader.Read()
|
||||
|
||||
if ret != 0:
|
||||
print("Error parsing the document")
|
||||
sys.exit(1)
|
||||
|
||||
if reader.IsValid() != 0:
|
||||
print("Document failed to detect the validation error")
|
||||
sys.exit(1)
|
||||
|
||||
if err != expect:
|
||||
print("Did not get the expected error message:")
|
||||
print(err)
|
||||
sys.exit(1)
|
||||
|
||||
#
|
||||
# cleanup
|
||||
#
|
||||
del f
|
||||
del input
|
||||
del reader
|
||||
del rngs
|
||||
libxml2.relaxNGCleanupTypes()
|
||||
|
||||
# Memory debug specific
|
||||
libxml2.cleanupParser()
|
||||
if libxml2.debugMemory(1) == 0:
|
||||
print("OK")
|
||||
else:
|
||||
print("Memory leak %d bytes" % (libxml2.debugMemory(1)))
|
||||
@@ -0,0 +1,101 @@
|
||||
#!/usr/bin/env python3
|
||||
#
|
||||
# this tests the entities substitutions with the XmlTextReader interface
|
||||
#
|
||||
import sys
|
||||
import setup_test
|
||||
import libxml2
|
||||
|
||||
# Memory debug specific
|
||||
libxml2.debugMemory(1)
|
||||
|
||||
result = ""
|
||||
def processNode(reader):
|
||||
global result
|
||||
|
||||
result = result + "%d %d %s %d\n" % (reader.Depth(), reader.NodeType(),
|
||||
reader.Name(), reader.IsEmptyElement())
|
||||
|
||||
#
|
||||
# Parse a document testing the readerForxxx API
|
||||
#
|
||||
docstr="""<foo>
|
||||
<label>some text</label>
|
||||
<item>100</item>
|
||||
</foo>"""
|
||||
expect="""0 1 foo 0
|
||||
1 14 #text 0
|
||||
1 1 label 0
|
||||
2 3 #text 0
|
||||
1 15 label 0
|
||||
1 14 #text 0
|
||||
1 1 item 0
|
||||
2 3 #text 0
|
||||
1 15 item 0
|
||||
1 14 #text 0
|
||||
0 15 foo 0
|
||||
"""
|
||||
result = ""
|
||||
|
||||
reader = libxml2.readerForDoc(docstr, "test1", None, 0)
|
||||
ret = reader.Read()
|
||||
while ret == 1:
|
||||
processNode(reader)
|
||||
ret = reader.Read()
|
||||
|
||||
if ret != 0:
|
||||
print("Error parsing the document test1")
|
||||
sys.exit(1)
|
||||
|
||||
if result != expect:
|
||||
print("Unexpected result for test1")
|
||||
print(result)
|
||||
sys.exit(1)
|
||||
|
||||
#
|
||||
# Reuse the reader for another document testing the ReaderNewxxx API
|
||||
#
|
||||
docstr="""<foo>
|
||||
<label>some text</label>
|
||||
<item>1000</item>
|
||||
</foo>"""
|
||||
expect="""0 1 foo 0
|
||||
1 14 #text 0
|
||||
1 1 label 0
|
||||
2 3 #text 0
|
||||
1 15 label 0
|
||||
1 14 #text 0
|
||||
1 1 item 0
|
||||
2 3 #text 0
|
||||
1 15 item 0
|
||||
1 14 #text 0
|
||||
0 15 foo 0
|
||||
"""
|
||||
result = ""
|
||||
|
||||
reader.NewDoc(docstr, "test2", None, 0)
|
||||
ret = reader.Read()
|
||||
while ret == 1:
|
||||
processNode(reader)
|
||||
ret = reader.Read()
|
||||
|
||||
if ret != 0:
|
||||
print("Error parsing the document test2")
|
||||
sys.exit(1)
|
||||
|
||||
if result != expect:
|
||||
print("Unexpected result for test2")
|
||||
print(result)
|
||||
sys.exit(1)
|
||||
|
||||
#
|
||||
# cleanup
|
||||
#
|
||||
del reader
|
||||
|
||||
# Memory debug specific
|
||||
libxml2.cleanupParser()
|
||||
if libxml2.debugMemory(1) == 0:
|
||||
print("OK")
|
||||
else:
|
||||
print("Memory leak %d bytes" % (libxml2.debugMemory(1)))
|
||||
@@ -0,0 +1,36 @@
|
||||
#!/usr/bin/env python3
|
||||
#
|
||||
# this tests the entities substitutions with the XmlTextReader interface
|
||||
#
|
||||
import sys
|
||||
import setup_test
|
||||
import libxml2
|
||||
|
||||
# Memory debug specific
|
||||
libxml2.debugMemory(1)
|
||||
|
||||
#
|
||||
# Parse a document testing the Close() API
|
||||
#
|
||||
docstr="""<foo>
|
||||
<label>some text</label>
|
||||
<item>100</item>
|
||||
</foo>"""
|
||||
|
||||
reader = libxml2.readerForDoc(docstr, "test1", None, 0)
|
||||
ret = reader.Read()
|
||||
ret = reader.Read()
|
||||
ret = reader.Close()
|
||||
|
||||
if ret != 0:
|
||||
print("Error closing the document test1")
|
||||
sys.exit(1)
|
||||
|
||||
del reader
|
||||
|
||||
# Memory debug specific
|
||||
libxml2.cleanupParser()
|
||||
if libxml2.debugMemory(1) == 0:
|
||||
print("OK")
|
||||
else:
|
||||
print("Memory leak %d bytes" % (libxml2.debugMemory(1)))
|
||||
@@ -0,0 +1,56 @@
|
||||
#!/usr/bin/env python3
|
||||
#
|
||||
# this tests the basic APIs of the XmlTextReader interface
|
||||
#
|
||||
import setup_test
|
||||
import libxml2
|
||||
import sys
|
||||
try:
|
||||
import StringIO
|
||||
str_io = StringIO.StringIO
|
||||
except:
|
||||
import io
|
||||
str_io = io.StringIO
|
||||
|
||||
# Memory debug specific
|
||||
libxml2.debugMemory(1)
|
||||
|
||||
expect="""--> (3) test1:1:xmlns: URI foo is not absolute
|
||||
--> (4) test1:1:Opening and ending tag mismatch: c line 1 and a
|
||||
"""
|
||||
err=""
|
||||
def myErrorHandler(arg,msg,severity,locator):
|
||||
global err
|
||||
err = err + "%s (%d) %s:%d:%s" % (arg,severity,locator.BaseURI(),locator.LineNumber(),msg)
|
||||
|
||||
f = str_io("""<a xmlns="foo"><b b1="b1"/><c>content of c</a>""")
|
||||
input = libxml2.inputBuffer(f)
|
||||
reader = input.newTextReader("test1")
|
||||
reader.SetErrorHandler(myErrorHandler,"-->")
|
||||
while reader.Read() == 1:
|
||||
pass
|
||||
|
||||
if err != expect:
|
||||
print("error")
|
||||
print("received %s" %(err))
|
||||
print("expected %s" %(expect))
|
||||
sys.exit(1)
|
||||
|
||||
reader.SetErrorHandler(None,None)
|
||||
if reader.GetErrorHandler() != (None,None):
|
||||
print("GetErrorHandler failed")
|
||||
sys.exit(1)
|
||||
|
||||
#
|
||||
# cleanup for memory allocation counting
|
||||
#
|
||||
del f
|
||||
del input
|
||||
del reader
|
||||
|
||||
# Memory debug specific
|
||||
libxml2.cleanupParser()
|
||||
if libxml2.debugMemory(1) == 0:
|
||||
print("OK")
|
||||
else:
|
||||
print("Memory leak %d bytes" % (libxml2.debugMemory(1)))
|
||||
@@ -0,0 +1,86 @@
|
||||
#!/usr/bin/env python3
|
||||
# -*- coding: ISO-8859-1 -*-
|
||||
#
|
||||
# this tests the next API of the XmlTextReader interface
|
||||
#
|
||||
import setup_test
|
||||
import libxml2
|
||||
import sys
|
||||
try:
|
||||
import StringIO
|
||||
str_io = StringIO.StringIO
|
||||
except:
|
||||
import io
|
||||
str_io = io.StringIO
|
||||
|
||||
# Memory debug specific
|
||||
libxml2.debugMemory(1)
|
||||
|
||||
f = str_io("""<a><b><c /></b><d>content of d</d></a>""")
|
||||
input = libxml2.inputBuffer(f)
|
||||
reader = input.newTextReader("test_next")
|
||||
ret = reader.Read()
|
||||
if ret != 1:
|
||||
print("test_next: Error reading to first element")
|
||||
sys.exit(1)
|
||||
if reader.Name() != "a" or reader.IsEmptyElement() != 0 or \
|
||||
reader.NodeType() != 1 or reader.HasAttributes() != 0:
|
||||
print("test_next: Error reading the first element")
|
||||
sys.exit(1)
|
||||
ret = reader.Read()
|
||||
if ret != 1:
|
||||
print("test_next: Error reading to second element")
|
||||
sys.exit(1)
|
||||
if reader.Name() != "b" or reader.IsEmptyElement() != 0 or \
|
||||
reader.NodeType() != 1 or reader.HasAttributes() != 0:
|
||||
print("test_next: Error reading the second element")
|
||||
sys.exit(1)
|
||||
ret = reader.Read()
|
||||
if ret != 1:
|
||||
print("test_next: Error reading to third element")
|
||||
sys.exit(1)
|
||||
if reader.Name() != "c" or reader.NodeType() != 1 or \
|
||||
reader.HasAttributes() != 0:
|
||||
print("test_next: Error reading the third element")
|
||||
sys.exit(1)
|
||||
ret = reader.Read()
|
||||
if ret != 1:
|
||||
print("test_next: Error reading to end of third element")
|
||||
sys.exit(1)
|
||||
if reader.Name() != "b" or reader.NodeType() != 15:
|
||||
print("test_next: Error reading to end of second element")
|
||||
sys.exit(1)
|
||||
ret = reader.Next()
|
||||
if ret != 1:
|
||||
print("test_next: Error moving to third element")
|
||||
sys.exit(1)
|
||||
if reader.Name() != "d" or reader.IsEmptyElement() != 0 or \
|
||||
reader.NodeType() != 1 or reader.HasAttributes() != 0:
|
||||
print("test_next: Error reading third element")
|
||||
sys.exit(1)
|
||||
ret = reader.Next()
|
||||
if ret != 1:
|
||||
print("test_next: Error reading to end of first element")
|
||||
sys.exit(1)
|
||||
if reader.Name() != "a" or reader.IsEmptyElement() != 0 or \
|
||||
reader.NodeType() != 15 or reader.HasAttributes() != 0:
|
||||
print("test_next: Error reading the end of first element")
|
||||
sys.exit(1)
|
||||
ret = reader.Read()
|
||||
if ret != 0:
|
||||
print("test_next: Error reading to end of document")
|
||||
sys.exit(1)
|
||||
|
||||
#
|
||||
# cleanup for memory allocation counting
|
||||
#
|
||||
del f
|
||||
del input
|
||||
del reader
|
||||
|
||||
# Memory debug specific
|
||||
libxml2.cleanupParser()
|
||||
if libxml2.debugMemory(1) == 0:
|
||||
print("OK")
|
||||
else:
|
||||
print("Memory leak %d bytes" % (libxml2.debugMemory(1)))
|
||||
@@ -0,0 +1,43 @@
|
||||
#!/usr/bin/env python3
|
||||
import sys
|
||||
import setup_test
|
||||
import libxml2
|
||||
|
||||
# Memory debug specific
|
||||
libxml2.debugMemory(1)
|
||||
|
||||
|
||||
def check_regex(regex, inside, outside):
|
||||
re = libxml2.regexpCompile(regex)
|
||||
for c in inside:
|
||||
if re.regexpExec(c) != 1:
|
||||
print("error checking inside", repr(regex), repr(c))
|
||||
sys.exit(1)
|
||||
for c in outside:
|
||||
if re.regexpExec(c) != 0:
|
||||
print("error checking outside", repr(regex), repr(c))
|
||||
sys.exit(1)
|
||||
if re.regexpIsDeterminist() != 1:
|
||||
print("error checking determinism")
|
||||
sys.exit(1)
|
||||
del re
|
||||
|
||||
|
||||
check_regex("a|b", "ab", ["ab", ""])
|
||||
# https://gitlab.gnome.org/GNOME/libxml2/-/issues/1086
|
||||
check_regex(r"[\t-\r]", "\t\n\r", ["a", "(", ""])
|
||||
check_regex("[\\t-\\r]", "\t\n\r", ["a", "(", ""])
|
||||
check_regex(r"[\[-\]]", "[]\\", "Z^")
|
||||
check_regex(r"[\*-/]", "*+,-./", "()0")
|
||||
# Non-standard escape sequences
|
||||
check_regex(r"[\u0041-\u005A]", "ABCMYZ", ["a", "0", "[", ""])
|
||||
check_regex(r"[\u0009\u0061-\u007A]", "\tabcmyz", ["A", "0", "{", "", "\n"])
|
||||
check_regex(r"[\!-\%]", '!"#$%', ["&", " ", "a", ""])
|
||||
check_regex(r"[\:-\>]", ':;<=>', ["?", "9", "@", ""])
|
||||
|
||||
# Memory debug specific
|
||||
libxml2.cleanupParser()
|
||||
if libxml2.debugMemory(1) == 0:
|
||||
print("OK")
|
||||
else:
|
||||
print("Memory leak %d bytes" % (libxml2.debugMemory(1)))
|
||||
@@ -0,0 +1,48 @@
|
||||
#!/usr/bin/env python3
|
||||
import setup_test
|
||||
import libxml2
|
||||
import sys
|
||||
|
||||
# Memory debug specific
|
||||
libxml2.debugMemory(1)
|
||||
|
||||
schema="""<?xml version="1.0"?>
|
||||
<element name="foo"
|
||||
xmlns="http://relaxng.org/ns/structure/1.0"
|
||||
xmlns:a="http://relaxng.org/ns/annotation/1.0"
|
||||
xmlns:ex1="http://www.example.com/n1"
|
||||
xmlns:ex2="http://www.example.com/n2">
|
||||
<a:documentation>A foo element.</a:documentation>
|
||||
<element name="ex1:bar1">
|
||||
<empty/>
|
||||
</element>
|
||||
<element name="ex2:bar2">
|
||||
<empty/>
|
||||
</element>
|
||||
</element>
|
||||
"""
|
||||
instance="""<?xml version="1.0"?>
|
||||
<foo><pre1:bar1 xmlns:pre1="http://www.example.com/n1"/><pre2:bar2 xmlns:pre2="http://www.example.com/n2"/></foo>"""
|
||||
|
||||
rngp = libxml2.relaxNGNewMemParserCtxt(schema, len(schema))
|
||||
rngs = rngp.relaxNGParse()
|
||||
ctxt = rngs.relaxNGNewValidCtxt()
|
||||
doc = libxml2.parseDoc(instance)
|
||||
ret = doc.relaxNGValidateDoc(ctxt)
|
||||
if ret != 0:
|
||||
print("error doing RelaxNG validation")
|
||||
sys.exit(1)
|
||||
|
||||
doc.freeDoc()
|
||||
del rngp
|
||||
del rngs
|
||||
del ctxt
|
||||
libxml2.relaxNGCleanupTypes()
|
||||
|
||||
# Memory debug specific
|
||||
libxml2.cleanupParser()
|
||||
if libxml2.debugMemory(1) == 0:
|
||||
print("OK")
|
||||
else:
|
||||
print("Memory leak %d bytes" % (libxml2.debugMemory(1)))
|
||||
|
||||
@@ -0,0 +1,44 @@
|
||||
#!/usr/bin/env python3
|
||||
import sys
|
||||
import setup_test
|
||||
import libxml2
|
||||
try:
|
||||
import StringIO
|
||||
str_io = StringIO.StringIO
|
||||
except:
|
||||
import io
|
||||
str_io = io.StringIO
|
||||
|
||||
# Memory debug specific
|
||||
libxml2.debugMemory(1)
|
||||
|
||||
def myResolver(URL, ID, ctxt):
|
||||
return(str_io("<foo/>"))
|
||||
|
||||
libxml2.setEntityLoader(myResolver)
|
||||
|
||||
doc = libxml2.parseFile("doesnotexist.xml")
|
||||
root = doc.children
|
||||
if root.name != "foo":
|
||||
print("root element name error")
|
||||
sys.exit(1)
|
||||
doc.freeDoc()
|
||||
|
||||
i = 0
|
||||
while i < 5000:
|
||||
doc = libxml2.parseFile("doesnotexist.xml")
|
||||
root = doc.children
|
||||
if root.name != "foo":
|
||||
print("root element name error")
|
||||
sys.exit(1)
|
||||
doc.freeDoc()
|
||||
i = i + 1
|
||||
|
||||
|
||||
# Memory debug specific
|
||||
libxml2.cleanupParser()
|
||||
if libxml2.debugMemory(1) == 0:
|
||||
print("OK")
|
||||
else:
|
||||
print("Memory leak %d bytes" % (libxml2.debugMemory(1)))
|
||||
|
||||
@@ -0,0 +1,52 @@
|
||||
#!/usr/bin/env python3
|
||||
import setup_test
|
||||
import libxml2
|
||||
import sys
|
||||
|
||||
# Memory debug specific
|
||||
libxml2.debugMemory(1)
|
||||
|
||||
schema="""<?xml version="1.0" encoding="iso-8859-1"?>
|
||||
<schema xmlns = "http://www.w3.org/2001/XMLSchema">
|
||||
<element name = "Customer">
|
||||
<complexType>
|
||||
<sequence>
|
||||
<element name = "FirstName" type = "string" />
|
||||
<element name = "MiddleInitial" type = "string" />
|
||||
<element name = "LastName" type = "string" />
|
||||
</sequence>
|
||||
<attribute name = "customerID" type = "integer" />
|
||||
</complexType>
|
||||
</element>
|
||||
</schema>"""
|
||||
|
||||
instance="""<?xml version="1.0" encoding="iso-8859-1"?>
|
||||
<Customer customerID = "24332">
|
||||
<FirstName>Raymond</FirstName>
|
||||
<MiddleInitial>G</MiddleInitial>
|
||||
<LastName>Bayliss</LastName>
|
||||
</Customer>
|
||||
"""
|
||||
|
||||
ctxt_parser = libxml2.schemaNewMemParserCtxt(schema, len(schema))
|
||||
ctxt_schema = ctxt_parser.schemaParse()
|
||||
ctxt_valid = ctxt_schema.schemaNewValidCtxt()
|
||||
doc = libxml2.parseDoc(instance)
|
||||
ret = doc.schemaValidateDoc(ctxt_valid)
|
||||
if ret != 0:
|
||||
print("error doing schema validation")
|
||||
sys.exit(1)
|
||||
|
||||
doc.freeDoc()
|
||||
del ctxt_parser
|
||||
del ctxt_schema
|
||||
del ctxt_valid
|
||||
libxml2.schemaCleanupTypes()
|
||||
|
||||
# Memory debug specific
|
||||
libxml2.cleanupParser()
|
||||
if libxml2.debugMemory(1) == 0:
|
||||
print("OK")
|
||||
else:
|
||||
print("Memory leak %d bytes" % (libxml2.debugMemory(1)))
|
||||
|
||||
@@ -0,0 +1,144 @@
|
||||
#!/usr/bin/env python3
|
||||
import sys
|
||||
import setup_test
|
||||
import libxml2
|
||||
|
||||
# Memory debug specific
|
||||
libxml2.debugMemory(1)
|
||||
|
||||
#
|
||||
# Testing XML document serialization
|
||||
#
|
||||
doc = libxml2.parseDoc("""<root><foo>hello</foo></root>""")
|
||||
str = doc.serialize()
|
||||
if str != """<?xml version="1.0"?>
|
||||
<root><foo>hello</foo></root>
|
||||
""":
|
||||
print("error serializing XML document 1")
|
||||
sys.exit(1)
|
||||
str = doc.serialize("iso-8859-1")
|
||||
if str != """<?xml version="1.0" encoding="iso-8859-1"?>
|
||||
<root><foo>hello</foo></root>
|
||||
""":
|
||||
print("error serializing XML document 2")
|
||||
sys.exit(1)
|
||||
str = doc.serialize(format=1)
|
||||
if str != """<?xml version="1.0"?>
|
||||
<root>
|
||||
<foo>hello</foo>
|
||||
</root>
|
||||
""":
|
||||
print("error serializing XML document 3")
|
||||
sys.exit(1)
|
||||
str = doc.serialize("iso-8859-1", 1)
|
||||
if str != """<?xml version="1.0" encoding="iso-8859-1"?>
|
||||
<root>
|
||||
<foo>hello</foo>
|
||||
</root>
|
||||
""":
|
||||
print("error serializing XML document 4")
|
||||
sys.exit(1)
|
||||
|
||||
#
|
||||
# Test serializing a subnode
|
||||
#
|
||||
root = doc.getRootElement()
|
||||
str = root.serialize()
|
||||
if str != """<root><foo>hello</foo></root>""":
|
||||
print("error serializing XML root 1")
|
||||
sys.exit(1)
|
||||
str = root.serialize("iso-8859-1")
|
||||
if str != """<root><foo>hello</foo></root>""":
|
||||
print("error serializing XML root 2")
|
||||
sys.exit(1)
|
||||
str = root.serialize(format=1)
|
||||
if str != """<root>
|
||||
<foo>hello</foo>
|
||||
</root>""":
|
||||
print("error serializing XML root 3")
|
||||
sys.exit(1)
|
||||
str = root.serialize("iso-8859-1", 1)
|
||||
if str != """<root>
|
||||
<foo>hello</foo>
|
||||
</root>""":
|
||||
print("error serializing XML root 4")
|
||||
sys.exit(1)
|
||||
doc.freeDoc()
|
||||
|
||||
#
|
||||
# Testing HTML document serialization
|
||||
#
|
||||
doc = libxml2.htmlParseDoc("""<html><head><title>Hello</title><body><p>hello</body></html>""", None)
|
||||
str = doc.serialize()
|
||||
if str != """<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.0 Transitional//EN" "http://www.w3.org/TR/REC-html40/loose.dtd">
|
||||
<html><head><title>Hello</title></head><body><p>hello</p></body></html>
|
||||
""":
|
||||
print("error serializing HTML document 1")
|
||||
sys.exit(1)
|
||||
str = doc.serialize("ISO-8859-1")
|
||||
if str != """<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.0 Transitional//EN" "http://www.w3.org/TR/REC-html40/loose.dtd">
|
||||
<html><head><meta charset="ISO-8859-1"><title>Hello</title></head><body><p>hello</p></body></html>
|
||||
""":
|
||||
print("error serializing HTML document 2")
|
||||
sys.exit(1)
|
||||
str = doc.serialize(format=1)
|
||||
if str != """<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.0 Transitional//EN" "http://www.w3.org/TR/REC-html40/loose.dtd">
|
||||
<html>
|
||||
<head><title>Hello</title></head>
|
||||
<body><p>hello</p></body>
|
||||
</html>
|
||||
""":
|
||||
print("error serializing HTML document 3")
|
||||
sys.exit(1)
|
||||
str = doc.serialize("iso-8859-1", 1)
|
||||
if str != """<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.0 Transitional//EN" "http://www.w3.org/TR/REC-html40/loose.dtd">
|
||||
<html>
|
||||
<head>
|
||||
<meta charset="iso-8859-1">
|
||||
<title>Hello</title>
|
||||
</head>
|
||||
<body><p>hello</p></body>
|
||||
</html>
|
||||
""":
|
||||
print("error serializing HTML document 4", str)
|
||||
sys.exit(1)
|
||||
|
||||
#
|
||||
# Test serializing a subnode
|
||||
#
|
||||
doc.htmlSetMetaEncoding(None)
|
||||
root = doc.getRootElement()
|
||||
str = root.serialize()
|
||||
if str != """<html><head><title>Hello</title></head><body><p>hello</p></body></html>""":
|
||||
print("error serializing HTML root 1")
|
||||
sys.exit(1)
|
||||
str = root.serialize("ISO-8859-1")
|
||||
if str != """<html><head><meta charset="ISO-8859-1"><title>Hello</title></head><body><p>hello</p></body></html>""":
|
||||
print("error serializing HTML root 2")
|
||||
sys.exit(1)
|
||||
str = root.serialize(format=1)
|
||||
if str != """<html>
|
||||
<head><title>Hello</title></head>
|
||||
<body><p>hello</p></body>
|
||||
</html>""":
|
||||
print("error serializing HTML root 3")
|
||||
sys.exit(1)
|
||||
str = root.serialize("iso-8859-1", 1)
|
||||
if str != """<html>
|
||||
<head>
|
||||
<meta charset="iso-8859-1">
|
||||
<title>Hello</title>
|
||||
</head>
|
||||
<body><p>hello</p></body>
|
||||
</html>""":
|
||||
print("error serializing HTML root 4")
|
||||
sys.exit(1)
|
||||
|
||||
doc.freeDoc()
|
||||
|
||||
# Memory debug specific
|
||||
libxml2.cleanupParser()
|
||||
if libxml2.debugMemory(1) == 0:
|
||||
print("OK")
|
||||
else:
|
||||
print("Memory leak %d bytes" % (libxml2.debugMemory(1)))
|
||||
@@ -0,0 +1,5 @@
|
||||
import os
|
||||
import sys
|
||||
|
||||
if hasattr(os, 'add_dll_directory'):
|
||||
os.add_dll_directory(os.path.join(os.getcwd(), '..', '..', '.libs'))
|
||||
@@ -0,0 +1,138 @@
|
||||
#!/usr/bin/env python3
|
||||
import sys
|
||||
import setup_test
|
||||
import libxml2
|
||||
|
||||
# Memory debug specific
|
||||
libxml2.debugMemory(1)
|
||||
|
||||
log = ""
|
||||
|
||||
class callback:
|
||||
def startDocument(self):
|
||||
global log
|
||||
log = log + "startDocument:"
|
||||
|
||||
def endDocument(self):
|
||||
global log
|
||||
log = log + "endDocument:"
|
||||
|
||||
def startElement(self, tag, attrs):
|
||||
global log
|
||||
log = log + "startElement %s %s:" % (tag, attrs)
|
||||
|
||||
def endElement(self, tag):
|
||||
global log
|
||||
log = log + "endElement %s:" % (tag)
|
||||
|
||||
def characters(self, data):
|
||||
global log
|
||||
log = log + "characters: %s:" % (data)
|
||||
|
||||
def warning(self, msg):
|
||||
global log
|
||||
log = log + "warning: %s:" % (msg)
|
||||
|
||||
def error(self, msg):
|
||||
global log
|
||||
log = log + "error: %s:" % (msg)
|
||||
|
||||
def fatalError(self, msg):
|
||||
global log
|
||||
log = log + "fatalError: %s:" % (msg)
|
||||
|
||||
handler = callback()
|
||||
|
||||
log=""
|
||||
chunk="""<foo><bar2/>"""
|
||||
ctxt = libxml2.createPushParser(handler, None, 0, "test.xml")
|
||||
ctxt.parseChunk(chunk, len(chunk), 0)
|
||||
ctxt=None
|
||||
|
||||
reference = "startDocument:startElement foo None:startElement bar2 None:endElement bar2:"
|
||||
if log != reference:
|
||||
print("Error got: %s" % log)
|
||||
print("Expected: %s" % reference)
|
||||
sys.exit(1)
|
||||
|
||||
log=""
|
||||
chunk="""<foo><bar2></bar2>"""
|
||||
ctxt = libxml2.createPushParser(handler, None, 0, "test.xml")
|
||||
ctxt.parseChunk(chunk, len(chunk), 0)
|
||||
ctxt=None
|
||||
|
||||
reference = "startDocument:startElement foo None:startElement bar2 None:endElement bar2:"
|
||||
if log != reference:
|
||||
print("Error got: %s" % log)
|
||||
print("Expected: %s" % reference)
|
||||
sys.exit(1)
|
||||
|
||||
log=""
|
||||
chunk="""<foo><bar2>"""
|
||||
ctxt = libxml2.createPushParser(handler, None, 0, "test.xml")
|
||||
ctxt.parseChunk(chunk, len(chunk), 0)
|
||||
ctxt=None
|
||||
|
||||
reference = "startDocument:startElement foo None:startElement bar2 None:"
|
||||
if log != reference:
|
||||
print("Error got: %s" % log)
|
||||
print("Expected: %s" % reference)
|
||||
sys.exit(1)
|
||||
|
||||
log=""
|
||||
chunk="""<foo><bar2 a="1" b='2' />"""
|
||||
ctxt = libxml2.createPushParser(handler, None, 0, "test.xml")
|
||||
ctxt.parseChunk(chunk, len(chunk), 0)
|
||||
ctxt=None
|
||||
|
||||
reference1 = "startDocument:startElement foo None:startElement bar2 {'a': '1', 'b': '2'}:endElement bar2:"
|
||||
reference2 = "startDocument:startElement foo None:startElement bar2 {'b': '2', 'a': '1'}:endElement bar2:"
|
||||
if log not in (reference1, reference2):
|
||||
print("Error got: %s" % log)
|
||||
print("Expected: %s" % reference)
|
||||
sys.exit(1)
|
||||
|
||||
log=""
|
||||
chunk="""<foo><bar2 a="1" b='2' >"""
|
||||
ctxt = libxml2.createPushParser(handler, None, 0, "test.xml")
|
||||
ctxt.parseChunk(chunk, len(chunk), 0)
|
||||
ctxt=None
|
||||
|
||||
reference1 = "startDocument:startElement foo None:startElement bar2 {'a': '1', 'b': '2'}:"
|
||||
reference2 = "startDocument:startElement foo None:startElement bar2 {'b': '2', 'a': '1'}:"
|
||||
if log not in (reference1, reference2):
|
||||
print("Error got: %s" % log)
|
||||
print("Expected: %s" % reference)
|
||||
sys.exit(1)
|
||||
|
||||
log=""
|
||||
chunk="""<foo><bar2 a="1" b='2' ></bar2>"""
|
||||
ctxt = libxml2.createPushParser(handler, None, 0, "test.xml")
|
||||
ctxt.parseChunk(chunk, len(chunk), 0)
|
||||
ctxt=None
|
||||
|
||||
reference1 = "startDocument:startElement foo None:startElement bar2 {'a': '1', 'b': '2'}:endElement bar2:"
|
||||
reference2 = "startDocument:startElement foo None:startElement bar2 {'b': '2', 'a': '1'}:endElement bar2:"
|
||||
if log not in (reference1, reference2):
|
||||
print("Error got: %s" % log)
|
||||
print("Expected: %s" % reference)
|
||||
sys.exit(1)
|
||||
|
||||
log=""
|
||||
chunk="""<foo><bar2 a="b='1' />"""
|
||||
ctxt = libxml2.createPushParser(handler, None, 0, "test.xml")
|
||||
ctxt.parseChunk(chunk, len(chunk), 0)
|
||||
ctxt=None
|
||||
|
||||
reference = "startDocument:startElement foo None:"
|
||||
if log != reference:
|
||||
print("Error got: %s" % log)
|
||||
print("Expected: %s" % reference)
|
||||
sys.exit(1)
|
||||
|
||||
# Memory debug specific
|
||||
libxml2.cleanupParser()
|
||||
if libxml2.debugMemory(1) == 0:
|
||||
print("OK")
|
||||
else:
|
||||
print("Memory leak %d bytes" % (libxml2.debugMemory(1)))
|
||||
@@ -0,0 +1 @@
|
||||
<!ELEMENT foo EMPTY>
|
||||
@@ -0,0 +1,105 @@
|
||||
#!/usr/bin/env python3
|
||||
import string, sys, time
|
||||
try:
|
||||
from _thread import get_ident
|
||||
except:
|
||||
from thread import get_ident
|
||||
from threading import Thread, Lock
|
||||
|
||||
import setup_test
|
||||
import libxml2
|
||||
|
||||
# Memory debug specific
|
||||
libxml2.debugMemory(1)
|
||||
|
||||
THREADS_COUNT = 15
|
||||
|
||||
failed = 0
|
||||
|
||||
class ErrorHandler:
|
||||
|
||||
def __init__(self):
|
||||
self.errors = []
|
||||
self.lock = Lock()
|
||||
|
||||
def handler(self,ctx,str):
|
||||
self.lock.acquire()
|
||||
self.errors.append(str)
|
||||
self.lock.release()
|
||||
|
||||
def getPedanticParserDefault():
|
||||
old = libxml2.pedanticParserDefault(0)
|
||||
libxml2.pedanticParserDefault(old)
|
||||
return old
|
||||
|
||||
def test(expectedPedanticParserDefault):
|
||||
time.sleep(1)
|
||||
global failed
|
||||
# check a per thread-global
|
||||
if expectedPedanticParserDefault != getPedanticParserDefault():
|
||||
failed = 1
|
||||
print("FAILED to obtain correct value for " \
|
||||
"pedanticParserDefault in thread %d" % get_ident())
|
||||
# check the global error handler
|
||||
# (which is NOT per-thread in the python bindings)
|
||||
try:
|
||||
doc = libxml2.parseFile("bad.xml")
|
||||
except:
|
||||
pass
|
||||
else:
|
||||
assert "failed"
|
||||
|
||||
# global error handler
|
||||
eh = ErrorHandler()
|
||||
libxml2.registerErrorHandler(eh.handler,"")
|
||||
|
||||
# set on the main thread only
|
||||
libxml2.pedanticParserDefault(1)
|
||||
test(1)
|
||||
ec = len(eh.errors)
|
||||
if ec == 0:
|
||||
print("FAILED: should have obtained errors")
|
||||
sys.exit(1)
|
||||
|
||||
ts = []
|
||||
for i in range(THREADS_COUNT):
|
||||
# expect 0 for pedanticParserDefault because
|
||||
# the new value has been set on the main thread only
|
||||
ts.append(Thread(target=test,args=(0,)))
|
||||
for t in ts:
|
||||
t.start()
|
||||
for t in ts:
|
||||
t.join()
|
||||
|
||||
if len(eh.errors) != ec+THREADS_COUNT*ec:
|
||||
print("FAILED: did not obtain the correct number of errors")
|
||||
sys.exit(1)
|
||||
|
||||
# set pedanticParserDefault for future new threads
|
||||
libxml2.thrDefPedanticParserDefaultValue(1)
|
||||
ts = []
|
||||
for i in range(THREADS_COUNT):
|
||||
# expect 1 for pedanticParserDefault
|
||||
ts.append(Thread(target=test,args=(1,)))
|
||||
for t in ts:
|
||||
t.start()
|
||||
for t in ts:
|
||||
t.join()
|
||||
|
||||
if len(eh.errors) != ec+THREADS_COUNT*ec*2:
|
||||
print("FAILED: did not obtain the correct number of errors")
|
||||
sys.exit(1)
|
||||
|
||||
if failed:
|
||||
print("FAILED")
|
||||
sys.exit(1)
|
||||
|
||||
# Memory debug specific
|
||||
libxml2.cleanupParser()
|
||||
# Note that this can leak memory on Windows if the global state
|
||||
# destructors weren't run yet. They should be called eventually,
|
||||
# so this leak should be harmless.
|
||||
if libxml2.debugMemory(1) == 0:
|
||||
print("OK")
|
||||
else:
|
||||
print("Memory leak %d bytes" % (libxml2.debugMemory(1)))
|
||||
@@ -0,0 +1,28 @@
|
||||
#!/usr/bin/env python3
|
||||
import sys
|
||||
import setup_test
|
||||
import libxml2
|
||||
|
||||
# Memory debug specific
|
||||
libxml2.debugMemory(1)
|
||||
|
||||
doc = libxml2.parseFile("tst.xml")
|
||||
if doc.name != "tst.xml":
|
||||
print("doc.name failed")
|
||||
sys.exit(1)
|
||||
root = doc.children
|
||||
if root.name != "doc":
|
||||
print("root.name failed")
|
||||
sys.exit(1)
|
||||
child = root.children
|
||||
if child.name != "foo":
|
||||
print("child.name failed")
|
||||
sys.exit(1)
|
||||
doc.freeDoc()
|
||||
|
||||
# Memory debug specific
|
||||
libxml2.cleanupParser()
|
||||
if libxml2.debugMemory(1) == 0:
|
||||
print("OK")
|
||||
else:
|
||||
print("Memory leak %d bytes" % (libxml2.debugMemory(1)))
|
||||
@@ -0,0 +1 @@
|
||||
<doc><foo>bar</foo></doc>
|
||||
@@ -0,0 +1,85 @@
|
||||
#!/usr/bin/env python3
|
||||
import sys, unittest
|
||||
|
||||
import setup_test
|
||||
import libxml2
|
||||
|
||||
class TestCase(unittest.TestCase):
|
||||
|
||||
def runTest(self):
|
||||
self.test1()
|
||||
self.test2()
|
||||
|
||||
def setUp(self):
|
||||
libxml2.debugMemory(1)
|
||||
|
||||
def tearDown(self):
|
||||
libxml2.cleanupParser()
|
||||
if libxml2.debugMemory(1) != 0:
|
||||
self.fail("Memory leak %d bytes" % (libxml2.debugMemory(1),))
|
||||
else:
|
||||
print("OK")
|
||||
|
||||
def failUnlessXmlError(self,f,args,exc,domain,code,message,level,file,line):
|
||||
"""Run function f, with arguments args and expect an exception exc;
|
||||
when the exception is raised, check the libxml2.lastError for
|
||||
expected values."""
|
||||
# disable the default error handler
|
||||
def noerr(ctx, str):
|
||||
pass
|
||||
# None is not acceptable as function.
|
||||
libxml2.registerErrorHandler(noerr,None)
|
||||
try:
|
||||
f(*args)
|
||||
except exc:
|
||||
e = libxml2.lastError()
|
||||
if e is None:
|
||||
self.fail("lastError not set")
|
||||
if 0:
|
||||
print("domain = ",e.domain())
|
||||
print("code = ",e.code())
|
||||
print("message =",repr(e.message()))
|
||||
print("level =",e.level())
|
||||
print("file =",e.file())
|
||||
print("line =",e.line())
|
||||
print()
|
||||
self.assertEqual(domain,e.domain())
|
||||
self.assertEqual(code,e.code())
|
||||
self.assertEqual(message,e.message())
|
||||
self.assertEqual(level,e.level())
|
||||
self.assertEqual(file,e.file())
|
||||
self.assertEqual(line,e.line())
|
||||
else:
|
||||
self.fail("exception %s should have been raised" % exc)
|
||||
|
||||
def test1(self):
|
||||
"""Test readFile with a file that does not exist"""
|
||||
self.failUnlessXmlError(libxml2.readFile,
|
||||
("dummy.xml",None,0),
|
||||
libxml2.treeError,
|
||||
domain=libxml2.XML_FROM_IO,
|
||||
code=libxml2.XML_IO_ENOENT,
|
||||
message='failed to load "dummy.xml": No such file or directory\n',
|
||||
level=libxml2.XML_ERR_WARNING,
|
||||
file=None,
|
||||
line=0)
|
||||
|
||||
def test2(self):
|
||||
"""Test a well-formedness error: we get the last error only"""
|
||||
s = "<x>\n<a>\n</x>"
|
||||
self.failUnlessXmlError(libxml2.readMemory,
|
||||
(s,len(s),"dummy.xml",None,0),
|
||||
libxml2.treeError,
|
||||
domain=libxml2.XML_FROM_PARSER,
|
||||
code=libxml2.XML_ERR_TAG_NAME_MISMATCH,
|
||||
message='Opening and ending tag mismatch: a line 2 and x\n',
|
||||
level=libxml2.XML_ERR_FATAL,
|
||||
file='dummy.xml',
|
||||
line=3)
|
||||
|
||||
if __name__ == "__main__":
|
||||
test = TestCase()
|
||||
test.setUp()
|
||||
test.test1()
|
||||
test.test2()
|
||||
test.tearDown()
|
||||
@@ -0,0 +1,41 @@
|
||||
#!/usr/bin/env python3
|
||||
import sys
|
||||
import setup_test
|
||||
import libxml2
|
||||
|
||||
# Memory debug specific
|
||||
libxml2.debugMemory(1)
|
||||
|
||||
uri = libxml2.parseURI("http://example.org:8088/foo/bar?query=simple#fragid")
|
||||
if uri.scheme() != 'http':
|
||||
print("Error parsing URI: wrong scheme")
|
||||
sys.exit(1)
|
||||
if uri.server() != 'example.org':
|
||||
print("Error parsing URI: wrong server")
|
||||
sys.exit(1)
|
||||
if uri.port() != 8088:
|
||||
print("Error parsing URI: wrong port")
|
||||
sys.exit(1)
|
||||
if uri.path() != '/foo/bar':
|
||||
print("Error parsing URI: wrong path")
|
||||
sys.exit(1)
|
||||
if uri.query() != 'query=simple':
|
||||
print("Error parsing URI: wrong query")
|
||||
sys.exit(1)
|
||||
if uri.fragment() != 'fragid':
|
||||
print("Error parsing URI: wrong query")
|
||||
sys.exit(1)
|
||||
uri.setScheme("https")
|
||||
uri.setPort(223)
|
||||
uri.setFragment(None)
|
||||
result=uri.saveUri()
|
||||
if result != "https://example.org:223/foo/bar?query=simple":
|
||||
print("Error modifying or saving the URI")
|
||||
uri = None
|
||||
|
||||
# Memory debug specific
|
||||
libxml2.cleanupParser()
|
||||
if libxml2.debugMemory(1) == 0:
|
||||
print("OK")
|
||||
else:
|
||||
print("Memory leak %d bytes" % (libxml2.debugMemory(1)))
|
||||
@@ -0,0 +1,41 @@
|
||||
#!/usr/bin/env python3
|
||||
import setup_test
|
||||
import libxml2
|
||||
|
||||
try:
|
||||
import libxml2mod
|
||||
except ModuleNotFoundError:
|
||||
from libxmlmods import libxml2mod
|
||||
|
||||
import sys
|
||||
|
||||
def error(msg, data):
|
||||
pass
|
||||
|
||||
# Memory debug specific
|
||||
libxml2.debugMemory(1)
|
||||
|
||||
dtd="""<!ELEMENT foo EMPTY>"""
|
||||
instance="""<?xml version="1.0"?>
|
||||
<foo></foo>"""
|
||||
|
||||
dtd = libxml2.parseDTD(None, 'test.dtd')
|
||||
ctxt = libxml2.newValidCtxt()
|
||||
libxml2mod.xmlSetValidErrors(ctxt._o, error, error)
|
||||
doc = libxml2.parseDoc(instance)
|
||||
ret = doc.validateDtd(ctxt, dtd)
|
||||
if ret != 1:
|
||||
print("error doing DTD validation")
|
||||
sys.exit(1)
|
||||
|
||||
doc.freeDoc()
|
||||
dtd.freeDtd()
|
||||
del dtd
|
||||
del ctxt
|
||||
|
||||
# Memory debug specific
|
||||
libxml2.cleanupParser()
|
||||
if libxml2.debugMemory(1) == 0:
|
||||
print("OK")
|
||||
else:
|
||||
print("Memory leak %d bytes" % (libxml2.debugMemory(1)))
|
||||
@@ -0,0 +1,63 @@
|
||||
#!/usr/bin/env python3
|
||||
import sys
|
||||
import setup_test
|
||||
import libxml2
|
||||
|
||||
#memory debug specific
|
||||
libxml2.debugMemory(1)
|
||||
|
||||
called = ""
|
||||
|
||||
def foo(ctx, x):
|
||||
global called
|
||||
|
||||
#
|
||||
# test that access to the XPath evaluation contexts
|
||||
#
|
||||
pctxt = libxml2.xpathParserContext(_obj=ctx)
|
||||
ctxt = pctxt.context()
|
||||
called = ctxt.function()
|
||||
return x + 1
|
||||
|
||||
def bar(ctxt, x):
|
||||
return "%d" % (x + 2)
|
||||
|
||||
doc = libxml2.parseFile("tst.xml")
|
||||
ctxt = doc.xpathNewContext()
|
||||
res = ctxt.xpathEval("//*")
|
||||
if len(res) != 2:
|
||||
print("xpath query: wrong node set size")
|
||||
sys.exit(1)
|
||||
if res[0].name != "doc" or res[1].name != "foo":
|
||||
print("xpath query: wrong node set value")
|
||||
sys.exit(1)
|
||||
libxml2.registerXPathFunction(ctxt._o, "foo", None, foo)
|
||||
libxml2.registerXPathFunction(ctxt._o, "bar", None, bar)
|
||||
i = 10000
|
||||
while i > 0:
|
||||
res = ctxt.xpathEval("foo(1)")
|
||||
if res != 2:
|
||||
print("xpath extension failure")
|
||||
sys.exit(1)
|
||||
i = i - 1
|
||||
i = 10000
|
||||
while i > 0:
|
||||
res = ctxt.xpathEval("bar(1)")
|
||||
if res != "3":
|
||||
print("xpath extension failure got %s expecting '3'")
|
||||
sys.exit(1)
|
||||
i = i - 1
|
||||
doc.freeDoc()
|
||||
ctxt.xpathFreeContext()
|
||||
|
||||
if called != "foo":
|
||||
print("xpath function: failed to access the context")
|
||||
print("xpath function: %s" % (called))
|
||||
sys.exit(1)
|
||||
|
||||
#memory debug specific
|
||||
libxml2.cleanupParser()
|
||||
if libxml2.debugMemory(1) == 0:
|
||||
print("OK")
|
||||
else:
|
||||
print("Memory leak %d bytes" % (libxml2.debugMemory(1)))
|
||||
@@ -0,0 +1,61 @@
|
||||
from io import BytesIO, StringIO
|
||||
import libxml2
|
||||
import sys
|
||||
from xml.sax.handler import ContentHandler
|
||||
from xml.sax.xmlreader import InputSource
|
||||
import xml.sax
|
||||
|
||||
|
||||
# Test data: an XML file with a 100,000 Unicode smileys, which expand
|
||||
# into 400,000 bytes after UTF-8 encoding.
|
||||
SMILEY = '\U0001f600'
|
||||
TEXT = 100_000 * SMILEY
|
||||
XML_STRING = '<?xml version="1.0" encoding="UTF-8" ?>\n<root>' + TEXT + '</root>'
|
||||
XML_BYTES = XML_STRING.encode('utf-8')
|
||||
|
||||
|
||||
def RunTest(test_name, source):
|
||||
expected = TEXT
|
||||
received = ''
|
||||
|
||||
class TestHandler(ContentHandler):
|
||||
def characters(self, content):
|
||||
nonlocal received
|
||||
received += content
|
||||
|
||||
reader = xml.sax.make_parser(['drv_libxml2'])
|
||||
reader.setContentHandler(TestHandler())
|
||||
reader.parse(source)
|
||||
if expected != received:
|
||||
print(test_name, 'failed!')
|
||||
print('Expected length:', len(expected))
|
||||
print('Received length:', len(received))
|
||||
print('Expected text: (prefix only)', expected[:100])
|
||||
print('Received text: (prefix only)', received[:100])
|
||||
sys.exit(1)
|
||||
|
||||
|
||||
def TestBytesInput():
|
||||
source = InputSource()
|
||||
source.setByteStream(BytesIO(XML_BYTES))
|
||||
RunTest('TestBytesInput', source)
|
||||
|
||||
|
||||
def TestStringInput():
|
||||
source = InputSource()
|
||||
source.setCharacterStream(StringIO(XML_STRING))
|
||||
RunTest('TestStringInput', source)
|
||||
|
||||
|
||||
# Memory debug specific
|
||||
libxml2.debugMemory(1)
|
||||
|
||||
TestBytesInput()
|
||||
TestStringInput()
|
||||
|
||||
# Memory debug specific
|
||||
libxml2.cleanupParser()
|
||||
if libxml2.debugMemory(1) == 0:
|
||||
print("OK")
|
||||
else:
|
||||
print("Memory leak %d bytes" % (libxml2.debugMemory(1)))
|
||||
@@ -0,0 +1,4 @@
|
||||
<!DOCTYPE doc [
|
||||
<!ELEMENT doc EMPTY>
|
||||
]>
|
||||
<doc/>
|
||||
@@ -0,0 +1,59 @@
|
||||
#!/usr/bin/env python3
|
||||
import setup_test
|
||||
import libxml2
|
||||
import sys
|
||||
|
||||
ARG = 'test string'
|
||||
|
||||
class ErrorHandler:
|
||||
|
||||
def __init__(self):
|
||||
self.errors = []
|
||||
|
||||
def handler(self, msg, data):
|
||||
if data != ARG:
|
||||
raise Exception("Error handler did not receive correct argument")
|
||||
self.errors.append(msg)
|
||||
|
||||
|
||||
# Memory debug specific
|
||||
libxml2.debugMemory(1)
|
||||
|
||||
dtd="""<!ELEMENT foo EMPTY>"""
|
||||
valid="""<?xml version="1.0"?>
|
||||
<foo></foo>"""
|
||||
|
||||
invalid="""<?xml version="1.0"?>
|
||||
<foo><bar/></foo>"""
|
||||
|
||||
dtd = libxml2.parseDTD(None, 'test.dtd')
|
||||
ctxt = libxml2.newValidCtxt()
|
||||
e = ErrorHandler()
|
||||
ctxt.setValidityErrorHandler(e.handler, e.handler, ARG)
|
||||
|
||||
# Test valid document
|
||||
doc = libxml2.parseDoc(valid)
|
||||
ret = doc.validateDtd(ctxt, dtd)
|
||||
if ret != 1 or e.errors:
|
||||
print("error doing DTD validation")
|
||||
sys.exit(1)
|
||||
doc.freeDoc()
|
||||
|
||||
# Test invalid document
|
||||
doc = libxml2.parseDoc(invalid)
|
||||
ret = doc.validateDtd(ctxt, dtd)
|
||||
if ret != 0 or not e.errors:
|
||||
print("Error: document supposed to be invalid")
|
||||
doc.freeDoc()
|
||||
|
||||
dtd.freeDtd()
|
||||
del dtd
|
||||
del ctxt
|
||||
|
||||
# Memory debug specific
|
||||
libxml2.cleanupParser()
|
||||
if libxml2.debugMemory(1) == 0:
|
||||
print("OK")
|
||||
else:
|
||||
print("Memory leak %d bytes" % (libxml2.debugMemory(1)))
|
||||
|
||||
@@ -0,0 +1,76 @@
|
||||
#!/usr/bin/env python3
|
||||
import setup_test
|
||||
import libxml2
|
||||
import sys
|
||||
|
||||
ARG = 'test string'
|
||||
|
||||
class ErrorHandler:
|
||||
|
||||
def __init__(self):
|
||||
self.errors = []
|
||||
|
||||
def handler(self, msg, data):
|
||||
if data != ARG:
|
||||
raise Exception("Error handler did not receive correct argument")
|
||||
self.errors.append(msg)
|
||||
|
||||
# Memory debug specific
|
||||
libxml2.debugMemory(1)
|
||||
|
||||
schema="""<?xml version="1.0"?>
|
||||
<element name="foo"
|
||||
xmlns="http://relaxng.org/ns/structure/1.0"
|
||||
xmlns:a="http://relaxng.org/ns/annotation/1.0"
|
||||
xmlns:ex1="http://www.example.com/n1"
|
||||
xmlns:ex2="http://www.example.com/n2">
|
||||
<a:documentation>A foo element.</a:documentation>
|
||||
<element name="ex1:bar1">
|
||||
<empty/>
|
||||
</element>
|
||||
<element name="ex2:bar2">
|
||||
<empty/>
|
||||
</element>
|
||||
</element>
|
||||
"""
|
||||
|
||||
valid="""<?xml version="1.0"?>
|
||||
<foo><pre1:bar1 xmlns:pre1="http://www.example.com/n1"/><pre2:bar2 xmlns:pre2="http://www.example.com/n2"/></foo>"""
|
||||
|
||||
invalid="""<?xml version="1.0"?>
|
||||
<foo><pre1:bar1 xmlns:pre1="http://www.example.com/n1">bad</pre1:bar1><pre2:bar2 xmlns:pre2="http://www.example.com/n2"/></foo>"""
|
||||
|
||||
rngp = libxml2.relaxNGNewMemParserCtxt(schema, len(schema))
|
||||
rngs = rngp.relaxNGParse()
|
||||
ctxt = rngs.relaxNGNewValidCtxt()
|
||||
e = ErrorHandler()
|
||||
ctxt.setValidityErrorHandler(e.handler, e.handler, ARG)
|
||||
|
||||
# Test valid document
|
||||
doc = libxml2.parseDoc(valid)
|
||||
ret = doc.relaxNGValidateDoc(ctxt)
|
||||
if ret != 0 or e.errors:
|
||||
print("error doing RelaxNG validation")
|
||||
sys.exit(1)
|
||||
doc.freeDoc()
|
||||
|
||||
# Test invalid document
|
||||
doc = libxml2.parseDoc(invalid)
|
||||
ret = doc.relaxNGValidateDoc(ctxt)
|
||||
if ret == 0 or not e.errors:
|
||||
print("Error: document supposed to be RelaxNG invalid")
|
||||
sys.exit(1)
|
||||
doc.freeDoc()
|
||||
|
||||
del rngp
|
||||
del rngs
|
||||
del ctxt
|
||||
libxml2.relaxNGCleanupTypes()
|
||||
|
||||
# Memory debug specific
|
||||
libxml2.cleanupParser()
|
||||
if libxml2.debugMemory(1) == 0:
|
||||
print("OK")
|
||||
else:
|
||||
print("Memory leak %d bytes" % (libxml2.debugMemory(1)))
|
||||
|
||||
@@ -0,0 +1,83 @@
|
||||
#!/usr/bin/env python3
|
||||
import setup_test
|
||||
import libxml2
|
||||
import sys
|
||||
|
||||
ARG = 'test string'
|
||||
|
||||
class ErrorHandler:
|
||||
|
||||
def __init__(self):
|
||||
self.errors = []
|
||||
|
||||
def handler(self, msg, data):
|
||||
if data != ARG:
|
||||
raise Exception("Error handler did not receive correct argument")
|
||||
self.errors.append(msg)
|
||||
|
||||
# Memory debug specific
|
||||
libxml2.debugMemory(1)
|
||||
|
||||
schema="""<?xml version="1.0" encoding="iso-8859-1"?>
|
||||
<schema xmlns = "http://www.w3.org/2001/XMLSchema">
|
||||
<element name = "Customer">
|
||||
<complexType>
|
||||
<sequence>
|
||||
<element name = "FirstName" type = "string" />
|
||||
<element name = "MiddleInitial" type = "string" />
|
||||
<element name = "LastName" type = "string" />
|
||||
</sequence>
|
||||
<attribute name = "customerID" type = "integer" />
|
||||
</complexType>
|
||||
</element>
|
||||
</schema>"""
|
||||
|
||||
valid="""<?xml version="1.0" encoding="iso-8859-1"?>
|
||||
<Customer customerID = "24332">
|
||||
<FirstName>Raymond</FirstName>
|
||||
<MiddleInitial>G</MiddleInitial>
|
||||
<LastName>Bayliss</LastName>
|
||||
</Customer>
|
||||
"""
|
||||
|
||||
invalid="""<?xml version="1.0" encoding="iso-8859-1"?>
|
||||
<Customer customerID = "24332">
|
||||
<MiddleInitial>G</MiddleInitial>
|
||||
<LastName>Bayliss</LastName>
|
||||
</Customer>
|
||||
"""
|
||||
|
||||
e = ErrorHandler()
|
||||
ctxt_parser = libxml2.schemaNewMemParserCtxt(schema, len(schema))
|
||||
ctxt_schema = ctxt_parser.schemaParse()
|
||||
ctxt_valid = ctxt_schema.schemaNewValidCtxt()
|
||||
ctxt_valid.setValidityErrorHandler(e.handler, e.handler, ARG)
|
||||
|
||||
# Test valid document
|
||||
doc = libxml2.parseDoc(valid)
|
||||
ret = doc.schemaValidateDoc(ctxt_valid)
|
||||
if ret != 0 or e.errors:
|
||||
print("error doing schema validation")
|
||||
sys.exit(1)
|
||||
doc.freeDoc()
|
||||
|
||||
# Test invalid document
|
||||
doc = libxml2.parseDoc(invalid)
|
||||
ret = doc.schemaValidateDoc(ctxt_valid)
|
||||
if ret == 0 or not e.errors:
|
||||
print("Error: document supposer to be schema invalid")
|
||||
sys.exit(1)
|
||||
doc.freeDoc()
|
||||
|
||||
del ctxt_parser
|
||||
del ctxt_schema
|
||||
del ctxt_valid
|
||||
libxml2.schemaCleanupTypes()
|
||||
|
||||
# Memory debug specific
|
||||
libxml2.cleanupParser()
|
||||
if libxml2.debugMemory(1) == 0:
|
||||
print("OK")
|
||||
else:
|
||||
print("Memory leak %d bytes" % (libxml2.debugMemory(1)))
|
||||
|
||||
@@ -0,0 +1,82 @@
|
||||
#!/usr/bin/env python3
|
||||
import sys
|
||||
import setup_test
|
||||
import libxml2
|
||||
|
||||
# Memory debug specific
|
||||
libxml2.debugMemory(1)
|
||||
|
||||
ctxt = libxml2.createFileParserCtxt("valid.xml")
|
||||
ctxt.validate(1)
|
||||
ctxt.parseDocument()
|
||||
doc = ctxt.doc()
|
||||
valid = ctxt.isValid()
|
||||
|
||||
if doc.name != "valid.xml":
|
||||
print("doc.name failed")
|
||||
sys.exit(1)
|
||||
root = doc.children
|
||||
if root.name != "doc":
|
||||
print("root.name failed")
|
||||
sys.exit(1)
|
||||
if valid != 1:
|
||||
print("validity check failed")
|
||||
sys.exit(1)
|
||||
doc.freeDoc()
|
||||
|
||||
i = 1000
|
||||
while i > 0:
|
||||
ctxt = libxml2.createFileParserCtxt("valid.xml")
|
||||
ctxt.validate(1)
|
||||
ctxt.parseDocument()
|
||||
doc = ctxt.doc()
|
||||
valid = ctxt.isValid()
|
||||
doc.freeDoc()
|
||||
if valid != 1:
|
||||
print("validity check failed")
|
||||
sys.exit(1)
|
||||
i = i - 1
|
||||
|
||||
#deactivate error messages from the validation
|
||||
def noerr(ctx, str):
|
||||
pass
|
||||
|
||||
libxml2.registerErrorHandler(noerr, None)
|
||||
|
||||
ctxt = libxml2.createFileParserCtxt("invalid.xml")
|
||||
ctxt.validate(1)
|
||||
ctxt.parseDocument()
|
||||
doc = ctxt.doc()
|
||||
valid = ctxt.isValid()
|
||||
if doc.name != "invalid.xml":
|
||||
print("doc.name failed")
|
||||
sys.exit(1)
|
||||
root = doc.children
|
||||
if root.name != "doc":
|
||||
print("root.name failed")
|
||||
sys.exit(1)
|
||||
if valid != 0:
|
||||
print("validity check failed")
|
||||
sys.exit(1)
|
||||
doc.freeDoc()
|
||||
|
||||
i = 1000
|
||||
while i > 0:
|
||||
ctxt = libxml2.createFileParserCtxt("invalid.xml")
|
||||
ctxt.validate(1)
|
||||
ctxt.parseDocument()
|
||||
doc = ctxt.doc()
|
||||
valid = ctxt.isValid()
|
||||
doc.freeDoc()
|
||||
if valid != 0:
|
||||
print("validity check failed")
|
||||
sys.exit(1)
|
||||
i = i - 1
|
||||
del ctxt
|
||||
|
||||
# Memory debug specific
|
||||
libxml2.cleanupParser()
|
||||
if libxml2.debugMemory(1) == 0:
|
||||
print("OK")
|
||||
else:
|
||||
print("Memory leak %d bytes" % (libxml2.debugMemory(1)))
|
||||
@@ -0,0 +1,144 @@
|
||||
#!/usr/bin/env python3
|
||||
#
|
||||
# this tests the entities substitutions with the XmlTextReader interface
|
||||
#
|
||||
import sys
|
||||
import setup_test
|
||||
import libxml2
|
||||
|
||||
# Memory debug specific
|
||||
libxml2.debugMemory(1)
|
||||
|
||||
result = ""
|
||||
def processNode(reader):
|
||||
global result
|
||||
|
||||
result = result + "%d %d %s %d\n" % (reader.Depth(), reader.NodeType(),
|
||||
reader.Name(), reader.IsEmptyElement())
|
||||
|
||||
#
|
||||
# Parse a document testing the readerForxxx API
|
||||
#
|
||||
docstr="""<foo>
|
||||
<label>some text</label>
|
||||
<item>100</item>
|
||||
</foo>"""
|
||||
expect="""0 1 foo 0
|
||||
1 14 #text 0
|
||||
1 1 label 0
|
||||
2 3 #text 0
|
||||
1 15 label 0
|
||||
1 14 #text 0
|
||||
1 1 item 0
|
||||
2 3 #text 0
|
||||
1 15 item 0
|
||||
1 14 #text 0
|
||||
0 15 foo 0
|
||||
"""
|
||||
result = ""
|
||||
|
||||
doc = libxml2.parseDoc(docstr)
|
||||
reader = doc.readerWalker();
|
||||
ret = reader.Read()
|
||||
while ret == 1:
|
||||
processNode(reader)
|
||||
ret = reader.Read()
|
||||
|
||||
if ret != 0:
|
||||
print("Error parsing the document test1")
|
||||
sys.exit(1)
|
||||
|
||||
if result != expect:
|
||||
print("Unexpected result for test1")
|
||||
print(result)
|
||||
sys.exit(1)
|
||||
|
||||
doc.freeDoc()
|
||||
|
||||
#
|
||||
# Reuse the reader for another document testing the ReaderNewWalker API
|
||||
#
|
||||
docstr="""<foo>
|
||||
<label>some text</label>
|
||||
<item>1000</item>
|
||||
</foo>"""
|
||||
expect="""0 1 foo 0
|
||||
1 14 #text 0
|
||||
1 1 label 0
|
||||
2 3 #text 0
|
||||
1 15 label 0
|
||||
1 14 #text 0
|
||||
1 1 item 0
|
||||
2 3 #text 0
|
||||
1 15 item 0
|
||||
1 14 #text 0
|
||||
0 15 foo 0
|
||||
"""
|
||||
result = ""
|
||||
|
||||
doc = libxml2.parseDoc(docstr)
|
||||
reader.NewWalker(doc)
|
||||
|
||||
ret = reader.Read()
|
||||
while ret == 1:
|
||||
processNode(reader)
|
||||
ret = reader.Read()
|
||||
|
||||
if ret != 0:
|
||||
print("Error parsing the document test2")
|
||||
sys.exit(1)
|
||||
|
||||
if result != expect:
|
||||
print("Unexpected result for test2")
|
||||
print(result)
|
||||
sys.exit(1)
|
||||
|
||||
doc.freeDoc()
|
||||
|
||||
#
|
||||
# Reuse the reader for another document testing the ReaderNewxxx API
|
||||
#
|
||||
docstr="""<foo>
|
||||
<label>some text</label>
|
||||
<item>1000</item>
|
||||
</foo>"""
|
||||
expect="""0 1 foo 0
|
||||
1 14 #text 0
|
||||
1 1 label 0
|
||||
2 3 #text 0
|
||||
1 15 label 0
|
||||
1 14 #text 0
|
||||
1 1 item 0
|
||||
2 3 #text 0
|
||||
1 15 item 0
|
||||
1 14 #text 0
|
||||
0 15 foo 0
|
||||
"""
|
||||
result = ""
|
||||
|
||||
reader.NewDoc(docstr, "test3", None, 0)
|
||||
ret = reader.Read()
|
||||
while ret == 1:
|
||||
processNode(reader)
|
||||
ret = reader.Read()
|
||||
|
||||
if ret != 0:
|
||||
print("Error parsing the document test3")
|
||||
sys.exit(1)
|
||||
|
||||
if result != expect:
|
||||
print("Unexpected result for test3")
|
||||
print(result)
|
||||
sys.exit(1)
|
||||
|
||||
#
|
||||
# cleanup
|
||||
#
|
||||
del reader
|
||||
|
||||
# Memory debug specific
|
||||
libxml2.cleanupParser()
|
||||
if libxml2.debugMemory(1) == 0:
|
||||
print("OK")
|
||||
else:
|
||||
print("Memory leak %d bytes" % (libxml2.debugMemory(1)))
|
||||
@@ -0,0 +1,51 @@
|
||||
#!/usr/bin/env python3
|
||||
#
|
||||
# this test exercise the XPath basic engine, parser, etc, and
|
||||
# allows to detect memory leaks
|
||||
#
|
||||
import sys
|
||||
import setup_test
|
||||
import libxml2
|
||||
|
||||
# Memory debug specific
|
||||
libxml2.debugMemory(1)
|
||||
|
||||
doc = libxml2.parseFile("tst.xml")
|
||||
if doc.name != "tst.xml":
|
||||
print("doc.name error")
|
||||
sys.exit(1);
|
||||
|
||||
ctxt = doc.xpathNewContext()
|
||||
res = ctxt.xpathEval("//*")
|
||||
if len(res) != 2:
|
||||
print("xpath query: wrong node set size")
|
||||
sys.exit(1)
|
||||
if res[0].name != "doc" or res[1].name != "foo":
|
||||
print("xpath query: wrong node set value")
|
||||
sys.exit(1)
|
||||
ctxt.setContextNode(res[0])
|
||||
res = ctxt.xpathEval("foo")
|
||||
if len(res) != 1:
|
||||
print("xpath query: wrong node set size")
|
||||
sys.exit(1)
|
||||
if res[0].name != "foo":
|
||||
print("xpath query: wrong node set value")
|
||||
sys.exit(1)
|
||||
doc.freeDoc()
|
||||
ctxt.xpathFreeContext()
|
||||
i = 1000
|
||||
while i > 0:
|
||||
doc = libxml2.parseFile("tst.xml")
|
||||
ctxt = doc.xpathNewContext()
|
||||
res = ctxt.xpathEval("//*")
|
||||
doc.freeDoc()
|
||||
ctxt.xpathFreeContext()
|
||||
i = i -1
|
||||
del ctxt
|
||||
|
||||
# Memory debug specific
|
||||
libxml2.cleanupParser()
|
||||
if libxml2.debugMemory(1) == 0:
|
||||
print("OK")
|
||||
else:
|
||||
print("Memory leak %d bytes" % (libxml2.debugMemory(1)))
|
||||
@@ -0,0 +1,49 @@
|
||||
#!/usr/bin/env python3
|
||||
import sys
|
||||
import setup_test
|
||||
import libxml2
|
||||
|
||||
# Memory debug specific
|
||||
libxml2.debugMemory(1)
|
||||
|
||||
def foo(ctx, x):
|
||||
return x + 1
|
||||
|
||||
def bar(ctx, x):
|
||||
return "%d" % (x + 2)
|
||||
|
||||
doc = libxml2.parseFile("tst.xml")
|
||||
ctxt = doc.xpathNewContext()
|
||||
res = ctxt.xpathEval("//*")
|
||||
if len(res) != 2:
|
||||
print("xpath query: wrong node set size")
|
||||
sys.exit(1)
|
||||
if res[0].name != "doc" or res[1].name != "foo":
|
||||
print("xpath query: wrong node set value")
|
||||
sys.exit(1)
|
||||
|
||||
libxml2.registerXPathFunction(ctxt._o, "foo", None, foo)
|
||||
libxml2.registerXPathFunction(ctxt._o, "bar", None, bar)
|
||||
i = 10000
|
||||
while i > 0:
|
||||
res = ctxt.xpathEval("foo(1)")
|
||||
if res != 2:
|
||||
print("xpath extension failure")
|
||||
sys.exit(1)
|
||||
i = i - 1
|
||||
i = 10000
|
||||
while i > 0:
|
||||
res = ctxt.xpathEval("bar(1)")
|
||||
if res != "3":
|
||||
print("xpath extension failure got %s expecting '3'")
|
||||
sys.exit(1)
|
||||
i = i - 1
|
||||
doc.freeDoc()
|
||||
ctxt.xpathFreeContext()
|
||||
|
||||
# Memory debug specific
|
||||
libxml2.cleanupParser()
|
||||
if libxml2.debugMemory(1) == 0:
|
||||
print("OK")
|
||||
else:
|
||||
print("Memory leak %d bytes" % (libxml2.debugMemory(1)))
|
||||
@@ -0,0 +1,55 @@
|
||||
#!/usr/bin/env python3
|
||||
import setup_test
|
||||
import libxml2
|
||||
import sys
|
||||
|
||||
libxml2.debugMemory(True)
|
||||
|
||||
expect="""--> Invalid expression
|
||||
--> Invalid expression
|
||||
--> Invalid expression
|
||||
--> Invalid expression
|
||||
--> Invalid expression
|
||||
--> Invalid expression
|
||||
--> Invalid expression
|
||||
--> Invalid expression
|
||||
--> Invalid expression
|
||||
--> Invalid expression
|
||||
"""
|
||||
err=""
|
||||
def callback(ctx, str):
|
||||
global err
|
||||
|
||||
err = err + "%s %s" % (ctx, str)
|
||||
|
||||
libxml2.registerErrorHandler(callback, "-->")
|
||||
|
||||
doc = libxml2.parseDoc("<fish/>")
|
||||
ctxt = doc.xpathNewContext()
|
||||
ctxt.setContextNode(doc)
|
||||
badexprs = (
|
||||
":false()", "bad:()", "bad(:)", ":bad(:)", "bad:(:)", "bad:bad(:)",
|
||||
"a:/b", "/c:/d", "//e:/f", "g://h"
|
||||
)
|
||||
for expr in badexprs:
|
||||
try:
|
||||
ctxt.xpathEval(expr)
|
||||
except libxml2.xpathError:
|
||||
pass
|
||||
else:
|
||||
print("Unexpectedly legal expression:", expr)
|
||||
ctxt.xpathFreeContext()
|
||||
doc.freeDoc()
|
||||
|
||||
if err != expect:
|
||||
print("error")
|
||||
print("received %s" %(err))
|
||||
print("expected %s" %(expect))
|
||||
sys.exit(1)
|
||||
|
||||
libxml2.cleanupParser()
|
||||
leakedbytes = libxml2.debugMemory(True)
|
||||
if leakedbytes == 0:
|
||||
print("OK")
|
||||
else:
|
||||
print("Memory leak", leakedbytes, "bytes")
|
||||
@@ -0,0 +1,29 @@
|
||||
#!/usr/bin/env python3
|
||||
#
|
||||
import setup_test
|
||||
import libxml2
|
||||
|
||||
expect=' xmlns:a="urn:whatevar"'
|
||||
|
||||
# Memory debug specific
|
||||
libxml2.debugMemory(1)
|
||||
|
||||
d = libxml2.parseDoc("<a:a xmlns:a='urn:whatevar'/>")
|
||||
res=""
|
||||
for n in d.xpathEval("//namespace::*"):
|
||||
res = res + n.serialize()
|
||||
del n
|
||||
d.freeDoc()
|
||||
|
||||
if res != expect:
|
||||
print("test5 failed: unexpected output")
|
||||
print(res)
|
||||
del res
|
||||
del d
|
||||
# Memory debug specific
|
||||
libxml2.cleanupParser()
|
||||
|
||||
if libxml2.debugMemory(1) == 0:
|
||||
print("OK")
|
||||
else:
|
||||
print("Memory leak %d bytes" % (libxml2.debugMemory(1)))
|
||||
@@ -0,0 +1,57 @@
|
||||
#!/usr/bin/env python3
|
||||
import sys
|
||||
import setup_test
|
||||
import libxml2
|
||||
|
||||
#memory debug specific
|
||||
libxml2.debugMemory(1)
|
||||
|
||||
#
|
||||
# A document hosting the nodes returned from the extension function
|
||||
#
|
||||
mydoc = libxml2.newDoc("1.0")
|
||||
|
||||
def foo(ctx, str):
|
||||
global mydoc
|
||||
|
||||
#
|
||||
# test returning a node set works as expected
|
||||
#
|
||||
parent = mydoc.newDocNode(None, 'p', None)
|
||||
mydoc.addChild(parent)
|
||||
node = mydoc.newDocText(str)
|
||||
parent.addChild(node)
|
||||
return [parent]
|
||||
|
||||
doc = libxml2.parseFile("tst.xml")
|
||||
ctxt = doc.xpathNewContext()
|
||||
libxml2.registerXPathFunction(ctxt._o, "foo", None, foo)
|
||||
res = ctxt.xpathEval("foo('hello')")
|
||||
if type(res) != type([]):
|
||||
print("Failed to return a nodeset")
|
||||
sys.exit(1)
|
||||
if len(res) != 1:
|
||||
print("Unexpected nodeset size")
|
||||
sys.exit(1)
|
||||
node = res[0]
|
||||
if node.name != 'p':
|
||||
print("Unexpected nodeset element result")
|
||||
sys.exit(1)
|
||||
node = node.children
|
||||
if node.type != 'text':
|
||||
print("Unexpected nodeset element children type")
|
||||
sys.exit(1)
|
||||
if node.content != 'hello':
|
||||
print("Unexpected nodeset element children content")
|
||||
sys.exit(1)
|
||||
|
||||
doc.freeDoc()
|
||||
mydoc.freeDoc()
|
||||
ctxt.xpathFreeContext()
|
||||
|
||||
#memory debug specific
|
||||
libxml2.cleanupParser()
|
||||
if libxml2.debugMemory(1) == 0:
|
||||
print("OK")
|
||||
else:
|
||||
print("Memory leak %d bytes" % (libxml2.debugMemory(1)))
|
||||
Reference in New Issue
Block a user