extended the XmlTextReader API a bit, addding accessors for the current
* xmlreader.c include/libxml/xmlreader.h doc/libxml2-api.xml:
extended the XmlTextReader API a bit, addding accessors for
the current doc and node, and an entity substitution mode for
the parser.
* python/libxml.py python/libxml2class.txt: related updates
* python/tests/Makefile.am python/tests/reader.py
python/tests/reader2.py python/tests/reader3.py: updated a bit
the old tests and added a new one to test the entities handling
Daniel
diff --git a/ChangeLog b/ChangeLog
index 0f24c4a..f7edb25 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,3 +1,14 @@
+Sat Dec 28 23:49:12 CET 2002 Daniel Veillard <daniel@veillard.com>
+
+ * xmlreader.c include/libxml/xmlreader.h doc/libxml2-api.xml:
+ extended the XmlTextReader API a bit, addding accessors for
+ the current doc and node, and an entity substitution mode for
+ the parser.
+ * python/libxml.py python/libxml2class.txt: related updates
+ * python/tests/Makefile.am python/tests/reader.py
+ python/tests/reader2.py python/tests/reader3.py: updated a bit
+ the old tests and added a new one to test the entities handling
+
Sat Dec 28 22:11:57 CET 2002 Daniel Veillard <daniel@veillard.com>
* python/generator.py python/libxml2class.txt
diff --git a/doc/libxml2-api.xml b/doc/libxml2-api.xml
index d92e9ea..b680ace 100644
--- a/doc/libxml2-api.xml
+++ b/doc/libxml2-api.xml
@@ -1092,6 +1092,7 @@
<file name='xmlreader'>
<exports symbol='XML_PARSER_DEFAULTATTRS'/>
<exports symbol='XML_PARSER_LOADDTD'/>
+ <exports symbol='XML_PARSER_SUBST_ENTITIES'/>
<exports symbol='XML_PARSER_VALIDATE'/>
<exports symbol='xmlFreeTextReader'/>
<exports symbol='xmlNewTextReader'/>
@@ -1101,6 +1102,8 @@
<exports symbol='xmlTextReaderAttributeCount'/>
<exports symbol='xmlTextReaderBaseUri'/>
<exports symbol='xmlTextReaderClose'/>
+ <exports symbol='xmlTextReaderCurrentDoc'/>
+ <exports symbol='xmlTextReaderCurrentNode'/>
<exports symbol='xmlTextReaderDepth'/>
<exports symbol='xmlTextReaderGetAttribute'/>
<exports symbol='xmlTextReaderGetAttributeNo'/>
@@ -2382,6 +2385,7 @@
<enum name='XML_PARSER_PUBLIC_LITERAL' file='parser' value='16' type='xmlParserInputState' info=' within a PUBLIC value'/>
<enum name='XML_PARSER_START' file='parser' value='0' type='xmlParserInputState' info='nothing has been parsed'/>
<enum name='XML_PARSER_START_TAG' file='parser' value='6' type='xmlParserInputState' info='within a start tag'/>
+ <enum name='XML_PARSER_SUBST_ENTITIES' file='xmlreader' value='4' type='xmlParserProperties'/>
<enum name='XML_PARSER_SYSTEM_LITERAL' file='parser' value='13' type='xmlParserInputState' info='within a SYSTEM value'/>
<enum name='XML_PARSER_VALIDATE' file='xmlreader' value='3' type='xmlParserProperties'/>
<enum name='XML_PI_NODE' file='tree' value='7' type='xmlElementType'/>
@@ -7917,6 +7921,16 @@
<return type='int' info='0 or -1 in case of error'/>
<arg name='reader' type='xmlTextReaderPtr' info='the xmlTextReaderPtr used'/>
</function>
+ <function name='xmlTextReaderCurrentDoc' file='xmlreader'>
+ <info>Hacking interface allowing to get the xmlDocPtr correponding to the current document being accessed by the xmlTextReader. This is dangerous because the associated node may be destroyed on the next Reads.</info>
+ <return type='xmlDocPtr' info='the xmlDocPtr or NULL in case of error.'/>
+ <arg name='reader' type='xmlTextReaderPtr' info='the xmlTextReaderPtr used'/>
+ </function>
+ <function name='xmlTextReaderCurrentNode' file='xmlreader'>
+ <info>Hacking interface allowing to get the xmlNodePtr correponding to the current node being accessed by the xmlTextReader. This is dangerous because the underlying node may be destroyed on the next Reads.</info>
+ <return type='xmlNodePtr' info='the xmlNodePtr or NULL in case of error.'/>
+ <arg name='reader' type='xmlTextReaderPtr' info='the xmlTextReaderPtr used'/>
+ </function>
<function name='xmlTextReaderDepth' file='xmlreader'>
<info>The depth of the node in the tree.</info>
<return type='int' info='the depth or -1 in case of error'/>
diff --git a/include/libxml/xmlreader.h b/include/libxml/xmlreader.h
index fbe1de0..457dcd5 100644
--- a/include/libxml/xmlreader.h
+++ b/include/libxml/xmlreader.h
@@ -18,8 +18,9 @@
typedef enum {
XML_PARSER_LOADDTD = 1,
- XML_PARSER_DEFAULTATTRS,
- XML_PARSER_VALIDATE
+ XML_PARSER_DEFAULTATTRS = 2,
+ XML_PARSER_VALIDATE = 3,
+ XML_PARSER_SUBST_ENTITIES = 4
} xmlParserProperties;
typedef struct _xmlTextReader xmlTextReader;
@@ -96,6 +97,8 @@
int value);
int xmlTextReaderGetParserProp (xmlTextReaderPtr reader,
int prop);
+xmlNodePtr xmlTextReaderCurrentNode (xmlTextReaderPtr reader);
+xmlDocPtr xmlTextReaderCurrentDoc (xmlTextReaderPtr reader);
#ifdef __cplusplus
}
#endif
diff --git a/python/libxml.py b/python/libxml.py
index 8e5ba2a..a1b5a7b 100644
--- a/python/libxml.py
+++ b/python/libxml.py
@@ -378,6 +378,7 @@
PARSER_LOADDTD=1
PARSER_DEFAULTATTRS=2
PARSER_VALIDATE=3
+PARSER_SUBST_ENTITIES=4
#
# Everything below this point is automatically generated
diff --git a/python/libxml2class.txt b/python/libxml2class.txt
index 93c2e9d..2fbc707 100644
--- a/python/libxml2class.txt
+++ b/python/libxml2class.txt
@@ -565,6 +565,8 @@
AttributeCount()
BaseUri()
Close()
+ CurrentDoc()
+ CurrentNode()
Depth()
GetAttribute()
GetAttributeNo()
diff --git a/python/tests/Makefile.am b/python/tests/Makefile.am
index de1ef3b..6ac6ab1 100644
--- a/python/tests/Makefile.am
+++ b/python/tests/Makefile.am
@@ -21,7 +21,9 @@
resolver.py \
regexp.py \
reader.py \
- reader2.py
+ reader2.py \
+ reader3.py
+
XMLS= \
tst.xml \
diff --git a/python/tests/reader.py b/python/tests/reader.py
index b9e351c..7b7dcc8 100755
--- a/python/tests/reader.py
+++ b/python/tests/reader.py
@@ -1,4 +1,7 @@
#!/usr/bin/python -u
+#
+# this tests the basic APIs of the XmlTextReader interface
+#
import libxml2
import StringIO
import sys
diff --git a/python/tests/reader2.py b/python/tests/reader2.py
index 3a49b50..82e46bd 100755
--- a/python/tests/reader2.py
+++ b/python/tests/reader2.py
@@ -1,6 +1,6 @@
#!/usr/bin/python -u
#
-# this tests the validation with the XmlTextReader interface
+# this tests the DTD validation with the XmlTextReader interface
#
import sys
import glob
diff --git a/python/tests/reader3.py b/python/tests/reader3.py
new file mode 100755
index 0000000..1593afb
--- /dev/null
+++ b/python/tests/reader3.py
@@ -0,0 +1,107 @@
+#!/usr/bin/python -u
+#
+# this tests the validation with the XmlTextReader interface
+#
+import sys
+import StringIO
+import libxml2
+
+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 = StringIO.StringIO(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() != 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 = StringIO.StringIO(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() != 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)
+
+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))
+ libxml2.dumpMemory()
diff --git a/xmlreader.c b/xmlreader.c
index e36bbf3..9640414 100644
--- a/xmlreader.c
+++ b/xmlreader.c
@@ -1864,6 +1864,13 @@
ctxt->validate = 0;
}
return(0);
+ case XML_PARSER_SUBST_ENTITIES:
+ if (value != 0) {
+ ctxt->replaceEntities = 1;
+ } else {
+ ctxt->replaceEntities = 0;
+ }
+ return(0);
}
return(-1);
}
@@ -1897,10 +1904,50 @@
return(0);
case XML_PARSER_VALIDATE:
return(ctxt->validate);
+ case XML_PARSER_SUBST_ENTITIES:
+ return(ctxt->replaceEntities);
}
return(-1);
}
+/**
+ * xmlTextReaderCurrentNode:
+ * @reader: the xmlTextReaderPtr used
+ *
+ * Hacking interface allowing to get the xmlNodePtr correponding to the
+ * current node being accessed by the xmlTextReader. This is dangerous
+ * because the underlying node may be destroyed on the next Reads.
+ *
+ * Returns the xmlNodePtr or NULL in case of error.
+ */
+xmlNodePtr
+xmlTextReaderCurrentNode(xmlTextReaderPtr reader) {
+ if (reader == NULL)
+ return(NULL);
+
+ if (reader->curnode != NULL)
+ return(reader->curnode);
+ return(reader->node);
+}
+
+/**
+ * xmlTextReaderCurrentDoc:
+ * @reader: the xmlTextReaderPtr used
+ *
+ * Hacking interface allowing to get the xmlDocPtr correponding to the
+ * current document being accessed by the xmlTextReader. This is dangerous
+ * because the associated node may be destroyed on the next Reads.
+ *
+ * Returns the xmlDocPtr or NULL in case of error.
+ */
+xmlDocPtr
+xmlTextReaderCurrentDoc(xmlTextReaderPtr reader) {
+ if ((reader == NULL) || (reader->ctxt == NULL))
+ return(NULL);
+
+ return(reader->ctxt->myDoc);
+}
+
/************************************************************************
* *
* Utilities *