[gxml] DomDocument: API improvements
- From: Daniel Espinosa Ortiz <despinosa src gnome org>
- To: commits-list gnome org
- Cc:
- Subject: [gxml] DomDocument: API improvements
- Date: Thu, 21 Mar 2019 19:08:40 +0000 (UTC)
commit 7da6bd6a7b08a1d452ce6df18dce3050fd5567b7
Author: Daniel Espinosa <esodan gmail com>
Date: Thu Mar 21 13:06:23 2019 -0600
DomDocument: API improvements
Parser API improvementes, more reusable code
gxml/DomDocument.vala | 105 ++++++++++++++++++++----
gxml/DomElement.vala | 8 +-
gxml/GXmlDocument.vala | 43 +++++-----
gxml/GomDocument.vala | 145 +++++++++++++---------------------
gxml/GomElement.vala | 29 ++++---
gxml/GomObject.vala | 19 +++--
gxml/Makefile.am | 1 +
gxml/Parser.vala | 62 ++++++---------
gxml/XParser.vala | 51 +++++-------
gxml/meson.build | 1 +
test/GElementTest.vala | 13 +++
test/GXmlDocumentPerformanceTest.vala | 34 ++++----
test/GXmlTest.vala | 5 +-
test/GomDocumentTest.vala | 39 +++++++++
test/GomSerializationTest.vala | 6 +-
15 files changed, 322 insertions(+), 239 deletions(-)
---
diff --git a/gxml/DomDocument.vala b/gxml/DomDocument.vala
index a671132..86ee5e4 100644
--- a/gxml/DomDocument.vala
+++ b/gxml/DomDocument.vala
@@ -1,7 +1,7 @@
/* -*- Mode: vala; indent-tabs-mode: nil; c-basic-offset: 2; tab-width: 2 -*- */
/*
*
- * Copyright (C) 2016 Daniel Espinosa <esodan gmail com>
+ * Copyright (C) 2016-2019 Daniel Espinosa <esodan gmail com>
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public
@@ -71,65 +71,142 @@ public interface GXml.DomDocument : GLib.Object,
*/
public abstract DomTreeWalker create_tree_walker (DomNode root, int what_to_show = (int) 0xFFFFFFFF,
DomNodeFilter? filter = null);
-
/**
* Writes a dump XML representation of document to a file.
*/
- public virtual void write_file (GLib.File file) throws GLib.Error {}
+ public virtual void write_file (GLib.File file, Cancellable? cancellable = null) throws GLib.Error
+ {
+ Parser parser = get_xml_parser ();
+ parser.write_file (file);
+ }
/**
* Writes asynchronically a dump XML representation of document to a file.
*/
public virtual async void write_file_async (GLib.File file,
- Cancellable? cancellable = null) throws GLib.Error {}
+ Cancellable? cancellable = null) throws GLib.Error
+ {
+ Parser parser = get_xml_parser ();
+ yield parser.write_file_async (file);
+ }
/**
* Writes a dump XML representation of document to a stream.
*/
- public virtual void write_stream (GLib.OutputStream stream) throws GLib.Error {}
+ public virtual void write_stream (GLib.OutputStream stream,
+ Cancellable? cancellable = null) throws GLib.Error
+ {
+ Parser parser = get_xml_parser ();
+ parser.write_stream (stream);
+ }
/**
* Writes a dump XML representation of document to a stream.
*/
public virtual async void write_stream_async (GLib.OutputStream stream,
- Cancellable? cancellable = null) throws GLib.Error {}
+ Cancellable? cancellable = null) throws GLib.Error
+ {
+ Parser parser = get_xml_parser ();
+ yield parser.write_stream_async (stream);
+ }
/**
* Creates an {@link GLib.InputStream} to write a string representation
* in XML of {@link GomDocument}
*/
public virtual InputStream create_stream () throws GLib.Error {
- return new MemoryInputStream ();
+ Parser parser = get_xml_parser ();
+ return parser.create_stream ();
}
/**
* Creates an {@link GLib.InputStream} to write a string representation
* in XML of {@link GomDocument}
*/
public virtual async InputStream create_stream_async (Cancellable? cancellable = null) throws GLib.Error {
- return new MemoryInputStream ();
+ Parser parser = get_xml_parser ();
+ parser.cancellable = cancellable;
+ return yield parser.create_stream_async ();
}
/**
* Serialize {@link GomDocument} to a string.
*/
- public virtual string write_string () throws GLib.Error { return ""; }
+ public virtual string write_string (Cancellable? cancellable = null) throws GLib.Error {
+ Parser parser = get_xml_parser ();
+ parser.cancellable = cancellable;
+ return parser.write_string ();
+ }
/**
* Serialize {@link GomDocument} to a string.
*/
- public virtual async string write_string_async (Cancellable? cancellable = null) throws GLib.Error {
return ""; }
+ public virtual async string write_string_async (Cancellable? cancellable = null) throws GLib.Error
+ {
+ Idle.add (write_string_async.callback);
+ yield;
+ return write_string (cancellable);
+ }
/**
* Reads a file contents and parse it to document.
*/
- public virtual void read_from_file (GLib.File file) throws GLib.Error {}
+ public virtual void read_from_file (GLib.File file,
+ Cancellable? cancellable = null) throws GLib.Error {
+ Parser parser = get_xml_parser ();
+ parser.cancellable = cancellable;
+ parser.read_file (file);
+ }
/**
* Reads a file contents and parse it to document.
*/
public virtual async void read_from_file_async (GLib.File file,
- Cancellable? cancellable = null) throws GLib.Error {}
+ Cancellable? cancellable = null) throws GLib.Error {
+ Parser parser = get_xml_parser ();
+ parser.cancellable = cancellable;
+ yield parser.read_file_async (file);
+ }
/**
* Reads a string and parse it to document.
*/
- public virtual void read_from_string (string str) throws GLib.Error {}
+ public virtual void read_from_string (string str, Cancellable? cancellable = null) throws GLib.Error {
+ Parser parser = get_xml_parser ();
+ parser.cancellable = cancellable;
+ parser.read_string (str);
+ }
/**
* Reads a string and parse it to document.
*/
public virtual async void read_from_string_async (string str,
- Cancellable? cancellable = null) throws GLib.Error {}
+ Cancellable? cancellable = null) throws GLib.Error {
+ Parser parser = get_xml_parser ();
+ parser.cancellable = cancellable;
+ yield parser.read_string_async (str);
+ }
+ /**
+ * Reads a string and parse it to document.
+ */
+ public virtual void read_from_stream (GLib.InputStream stream,
+ Cancellable? cancellable = null) throws GLib.Error
+ {
+ Parser parser = get_xml_parser ();
+ parser.cancellable = cancellable;
+ parser.read_stream (stream);
+ }
+ /**
+ * Reads a string and parse it to document.
+ */
+ public virtual async void read_from_stream_async (GLib.InputStream stream,
+ Cancellable? cancellable = null) throws GLib.Error
+ {
+ Parser parser = get_xml_parser ();
+ parser.cancellable = cancellable;
+ yield parser.read_stream_async (stream);
+ }
+ /**
+ * Returns a default XML {@link Parser} to use with this object.
+ */
+ public abstract Parser get_xml_parser ();
+ /**
+ * Set a default XML {@link Parser} to use with this object.
+ */
+ public abstract void set_xml_parser (Parser parser);
+}
+
+public errordomain GXml.DomDocumentError {
+ FILE_NOT_FOUND_ERROR
}
public interface GXml.DomXMLDocument : GLib.Object, GXml.DomDocument {}
diff --git a/gxml/DomElement.vala b/gxml/DomElement.vala
index 6d80dfc..8fb9d98 100644
--- a/gxml/DomElement.vala
+++ b/gxml/DomElement.vala
@@ -108,7 +108,7 @@ public interface GXml.DomElement : GLib.Object,
/**
* Parses an XML string, deserializing it over {@link GomElement}.
*/
- public virtual void read_from_string (string str) throws GLib.Error {}
+ public virtual void read_from_string (string str, Cancellable? cancellable = null) throws GLib.Error {}
/**
* Parses an XML string, deserializing it over {@link GomElement}.
*/
@@ -117,7 +117,7 @@ public interface GXml.DomElement : GLib.Object,
/**
* Serialize {@link GomElement} to a string.
*/
- public virtual string write_string () throws GLib.Error { return ""; }
+ public virtual string write_string (Cancellable? cancellable = null) throws GLib.Error { return ""; }
/**
* Serialize asinchronically {@link GomElement} to a string.
*/
@@ -125,8 +125,8 @@ public interface GXml.DomElement : GLib.Object,
/**
* Uses element's {@link GomDocument} to write an XML to a file, serializing it.
*/
- public virtual void write_file (GLib.File f) throws GLib.Error {
- owner_document.write_file (f);
+ public virtual void write_file (GLib.File f, Cancellable? cancellable = null) throws GLib.Error {
+ owner_document.write_file (f, cancellable);
}
/**
* Uses element's {@link GomDocument} to write asynchronically an XML to a file, serializing it.
diff --git a/gxml/GXmlDocument.vala b/gxml/GXmlDocument.vala
index 19e3006..2944a57 100644
--- a/gxml/GXmlDocument.vala
+++ b/gxml/GXmlDocument.vala
@@ -1,7 +1,7 @@
/* -*- Mode: vala; indent-tabs-mode: nil; c-basic-offset: 2; tab-width: 2 -*- */
/* GDocument.vala
*
- * Copyright (C) 2016 Daniel Espinosa <esodan gmail com>
+ * Copyright (C) 2016-2019 Daniel Espinosa <esodan gmail com>
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public
@@ -38,8 +38,9 @@ public class GXml.GDocument : GXml.GNode,
GXml.DomXMLDocument,
GXml.XPathContext
{
- protected Xml.Doc* doc;
+ internal Xml.Doc* doc;
protected Xml.Buffer _buffer;
+ protected Parser _parser = null;
public GDocument () {
doc = new Xml.Doc ();
@@ -55,33 +56,31 @@ public class GXml.GDocument : GXml.GNode,
public GDocument.from_file (GLib.File file, int options = 0, Cancellable? cancel = null) throws GLib.Error
{
if (!file.query_exists ())
throw new DocumentError.INVALID_DOCUMENT_ERROR (_("File doesn't exist"));
- var b = new MemoryOutputStream.resizable ();
- b.splice (file.read (), 0);
- this.from_string ((string) b.data, options);
+ var parser = new GParser (this);
+ parser.cancellable = cancel;
+ parser.read_stream (file.read ());
}
public GDocument.from_string (string str, int options = 0) throws GLib.Error {
- Xml.reset_last_error ();
- doc = Xml.Parser.parse_memory (str, (int) str.length);
- var e = Xml.get_last_error ();
- if (e != null) {
- var errmsg = "Parser Error for string";
- string s = libxml2_error_to_string (e);
- if (s != null)
- errmsg = ". ";
- throw new GXml.Error.PARSER (errmsg);
- }
- if (doc == null)
- doc = new Xml.Doc ();
+ var parser = new GParser (this);
+ parser.read_string (str);
}
public GDocument.from_stream (GLib.InputStream istream) throws GLib.Error {
- var b = new MemoryOutputStream.resizable ();
- b.splice (istream, 0);
- if (b.data == null)
- throw new DocumentError.INVALID_DOCUMENT_ERROR (_("stream doesn't provide data"));
- this.from_string ((string) b.data);
+ var parser = new GParser (this);
+ parser.read_stream (istream);
}
public GDocument.from_doc (Xml.Doc doc) { this.doc = doc; }
+
+ public Parser GXml.DomDocument.get_xml_parser () {
+ if (_parser != null) {
+ return _parser;
+ }
+ return new GParser (this);
+ }
+ public void set_xml_parser (Parser parser) {
+ _parser = parser;
+ }
+
// GXml.Node
public override bool set_namespace (string uri, string? prefix)
{
diff --git a/gxml/GomDocument.vala b/gxml/GomDocument.vala
index fb46a57..9a75075 100644
--- a/gxml/GomDocument.vala
+++ b/gxml/GomDocument.vala
@@ -1,7 +1,7 @@
/* -*- Mode: vala; indent-tabs-mode: nil; c-basic-offset: 2; tab-width: 2 -*- */
/*
*
- * Copyright (C) 2016 Daniel Espinosa <esodan gmail com>
+ * Copyright (C) 2016-2019 Daniel Espinosa <esodan gmail com>
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public
@@ -27,6 +27,9 @@ using GXml;
*
* This object avoids pre and post XML parsing, by using a one step parsing
* to translate text XML tree to an GObject based tree.
+ *
+ * If you define a property in a derived class with a nick's name '::ROOT' it
+ * will be initialized and used as root node to parse documents.
*/
public class GXml.GomDocument : GomNode,
DomParentNode,
@@ -42,6 +45,7 @@ public class GXml.GomDocument : GomNode,
protected string _character_set;
protected string _content_type;
protected GXml.DomEvent _constructor;
+ protected Parser _parser;
public DomImplementation implementation { get { return _implementation; } }
public string url { get { return _url; } }
public string document_uri { get { return _url; } }
@@ -73,6 +77,7 @@ public class GXml.GomDocument : GomNode,
_compat_mode = "";
_character_set = "utf-8";
_content_type = "application/xml";
+ _parser = null;
}
public GomDocument () {}
public GomDocument.from_path (string path) throws GLib.Error {
@@ -91,113 +96,69 @@ public class GXml.GomDocument : GomNode,
* Creates a document parsing a file.
*/
public GomDocument.from_file (GLib.File file) throws GLib.Error {
- var parser = new XParser (this);
- parser.read_file (file, null);
+ Parser parser = get_xml_parser ();
+ parser.read_file (file);
+ }
+
+ private GomElement get_root_gom_element () {
+ Object obj = null;
+ foreach (ParamSpec spec in this.get_class ().list_properties ()) {
+ if ("::" in spec.get_nick () && spec.name.down () == "root") {
+ if (spec.value_type.is_a (typeof (GomElement))) {
+ Value val = Value (Type.OBJECT);
+ get_property (spec.name, ref val);
+ var roote = val.get_object () as GomElement;
+ if (roote == null) {
+ obj = Object.new (spec.value_type,"owner-document", this.owner_document);
+ try { this.append_child (obj as GomElement); }
+ catch (GLib.Error e) {
+ warning (_("Error while attempting to instantiate root property object: %s").printf
(e.message));
+ obj = null;
+ }
+ val.set_object (obj);
+ set_property (spec.name, val);
+ }
+ }
+ }
+ }
+ return obj as GomElement;
}
/**
* Creates a document parsing a stream.
*/
public GomDocument.from_stream (GLib.InputStream stream) throws GLib.Error {
- var parser = new XParser (this);
- parser.read_stream (stream, null);
+ Parser parser = get_xml_parser ();
+ parser.read_stream (stream);
}
/**
* Creates a document parsing a string.
*/
public GomDocument.from_string (string str) throws GLib.Error {
- var parser = new XParser (this);
- parser.read_string (str, null);
+ Parser parser = get_xml_parser ();
+ parser.read_string (str);
}
- /**
- * Writes a dump XML representation of document to a file.
- */
- public void write_file (GLib.File file) throws GLib.Error {
- var parser = new XParser (this);
- parser.write_file (file, null);
- }
- /**
- * Writes asynchronically a dump XML representation of document to a file.
- */
- public async void write_file_async (GLib.File file, Cancellable? cancellable = null) throws GLib.Error {
- var parser = new XParser (this);
- yield parser.write_file_async (file, null);
- }
- /**
- * Writes a dump XML representation of document to a stream.
- */
- public void write_stream (GLib.OutputStream stream) throws GLib.Error {
- var parser = new XParser (this);
- parser.write_stream (stream, null);
- }
- /**
- * Writes a dump XML representation of document to a stream.
- */
- public async void write_stream_async (GLib.OutputStream stream, Cancellable? cancellable = null) throws
GLib.Error {
- var parser = new XParser (this);
- parser.write_stream (stream, null);
- }
- /**
- * Creates an {@link GLib.InputStream} to write a string representation
- * in XML of {@link GomDocument}
- */
- public InputStream create_stream () throws GLib.Error {
- var parser = new XParser (this);
- return parser.create_stream (null);
- }
- /**
- * Creates an {@link GLib.InputStream} to write a string representation
- * in XML of {@link GomDocument}
- */
- public async InputStream create_stream_async (Cancellable? cancellable = null) throws GLib.Error {
- var parser = new XParser (this);
- return yield parser.create_stream_async (null);
- }
- /**
- * Serialize {@link GomDocument} to a string.
- */
- public string write_string () throws GLib.Error {
- var parser = new XParser (this);
- return parser.write_string ();
- }
- /**
- * Serialize {@link GomDocument} to a string.
- */
- public async string write_string_async (Cancellable? cancellable = null) throws GLib.Error {
- var parser = new XParser (this);
- return yield parser.write_string_async ();
- }
- /**
- * Reads a file contents and parse it to document.
- */
- public void read_from_file (GLib.File file) throws GLib.Error {
- var parser = new XParser (this);
- parser.read_file (file, null);
- }
- /**
- * Reads a file contents and parse it to document.
- */
- public async void read_from_file_async (GLib.File file, Cancellable? cancellable = null) throws GLib.Error
{
- var parser = new XParser (this);
- yield parser.read_file_async (file, null);
- }
- /**
- * Reads a string and parse it to document.
- */
- public void read_from_string (string str) throws GLib.Error {
- var parser = new XParser (this);
- parser.read_string (str, null);
- }
- /**
- * Reads a string and parse it to document.
- */
- public async void read_from_string_async (string str, Cancellable? cancellable = null) throws GLib.Error {
- var parser = new XParser (this);
- yield parser.read_string_async (str, null);
+ public Parser get_xml_parser () {
+ var roote = get_root_gom_element ();
+ Parser parser = null;
+ if (roote != null) {
+ parser = new XParser (roote);
+ } else {
+ parser = new XParser (this);
+ }
+ if (_parser != null) {
+ parser.backup = _parser.backup;
+ parser.indent = _parser.indent;
+ parser.cancellable = _parser.cancellable;
+ }
+ return parser;
}
+ public void set_xml_parser (Parser parser) {
+ _parser = parser;
+ }
public DomElement create_element (string local_name) throws GLib.Error {
var e = new GomElement ();
e.initialize_document (this, local_name);
diff --git a/gxml/GomElement.vala b/gxml/GomElement.vala
index f2f57a3..9d084c8 100644
--- a/gxml/GomElement.vala
+++ b/gxml/GomElement.vala
@@ -54,7 +54,8 @@ public class GXml.GomElement : GomNode,
public void read_from_file (GLib.File f,
GLib.Cancellable? cancellable = null) throws GLib.Error {
var parser = new XParser (this);
- parser.read_file (f, cancellable);
+ parser.cancellable = cancellable;
+ parser.read_file (f);
}
/**
* Parses asinchronically an XML file, deserializing it over {@link GomElement}.
@@ -62,7 +63,8 @@ public class GXml.GomElement : GomNode,
public async void read_from_file_async (GLib.File f,
GLib.Cancellable? cancellable = null) throws GLib.Error {
var parser = new XParser (this);
- yield parser.read_file_async (f, cancellable);
+ parser.cancellable = cancellable;
+ yield parser.read_file_async (f);
}
/**
* Parses an XML over a {@link GLib.InputStream}, deserializing it over {@link GomElement}.
@@ -70,7 +72,8 @@ public class GXml.GomElement : GomNode,
public void read_from_stream (GLib.InputStream istream,
GLib.Cancellable? cancellable = null) throws GLib.Error {
var parser = new XParser (this);
- parser.read_stream (istream, cancellable);
+ parser.cancellable = cancellable;
+ parser.read_stream (istream);
}
/**
* Parses asynchronically an XML over a {@link GLib.InputStream}, deserializing it over {@link GomElement}.
@@ -78,27 +81,31 @@ public class GXml.GomElement : GomNode,
public async void read_from_stream_async (GLib.InputStream istream,
GLib.Cancellable? cancellable = null) throws GLib.Error {
var parser = new XParser (this);
- yield parser.read_stream_async (istream, cancellable);
+ parser.cancellable = cancellable;
+ yield parser.read_stream_async (istream);
}
/**
* Parses an XML string, deserializing it over {@link GomElement}.
*/
- public void read_from_string (string str) throws GLib.Error {
+ public void read_from_string (string str, Cancellable? cancellable = null) throws GLib.Error {
var parser = new XParser (this);
- parser.read_string (str, null);
+ parser.cancellable = cancellable;
+ parser.read_string (str);
}
/**
* Parses an XML string, deserializing it over {@link GomElement}.
*/
public async void read_from_string_async (string str, Cancellable? cancellable = null) throws GLib.Error {
var parser = new XParser (this);
- yield parser.read_string_async (str, null);
+ parser.cancellable = cancellable;
+ yield parser.read_string_async (str);
}
/**
* Serialize {@link GomElement} to a string.
*/
- public string write_string () throws GLib.Error {
+ public string write_string (Cancellable? cancellable = null) throws GLib.Error {
var parser = new XParser (this);
+ parser.cancellable = cancellable;
return parser.write_string ();
}
/**
@@ -106,12 +113,13 @@ public class GXml.GomElement : GomNode,
*/
public async string write_string_async (Cancellable? cancellable = null) throws GLib.Error {
var parser = new XParser (this);
+ parser.cancellable = cancellable;
return yield parser.write_string_async ();
}
/**
* Uses element's {@link GomDocument} to write an XML to a file, serializing it.
*/
- public void write_file (GLib.File f) throws GLib.Error {
+ public void write_file (GLib.File f, Cancellable? cancellable = null) throws GLib.Error {
(this.owner_document as GomDocument).write_file (f);
}
/**
@@ -308,7 +316,6 @@ public class GXml.GomElement : GomNode,
if (p == null) {
GomProperty prop = new GomStringRef (this, name);
_attributes.add (name, prop);
- message ("Set: %s", name);
}
}
});
@@ -770,7 +777,7 @@ public class GXml.GomElement : GomNode,
public void read_unparsed () throws GLib.Error {
if (unparsed == null) return;
var parser = new XParser (this);
- parser.read_child_nodes_string (unparsed, null);
+ parser.read_child_nodes_string (unparsed);
unparsed = null;
}
}
diff --git a/gxml/GomObject.vala b/gxml/GomObject.vala
index 4247e89..6974a64 100644
--- a/gxml/GomObject.vala
+++ b/gxml/GomObject.vala
@@ -1,7 +1,7 @@
/* -*- Mode: vala; indent-tabs-mode: nil; c-basic-offset: 2; tab-width: 2 -*- */
/*
*
- * Copyright (C) 2016 Daniel Espinosa <esodan gmail com>
+ * Copyright (C) 2016-2019 Daniel Espinosa <esodan gmail com>
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public
@@ -51,15 +51,20 @@ public interface GXml.GomObject : GLib.Object,
return l;
}
/**
- * Returns property's {@link GLib.ParamSpec} based on given nick. This function is
- * case insensitive.
+ * Returns property's {@link GLib.ParamSpec} based on given nick, without '::'
+ * This function is case insensitive.
+ *
+ * By default any property to be serialized, should set its nick with a prefix
+ * '::', while this method requires to avoid '::' for property's name to find.
+ * '::' will not be present on serialization output, so you can use any convention
+ * for your attribute's name, like using camel case.
*/
- public virtual ParamSpec? find_property_name (string pname) {
+ public virtual ParamSpec? find_property_name (string nick) {
foreach (ParamSpec spec in this.get_class ().list_properties ()) {
string name = spec.get_nick ();
if ("::" in name) {
name = name.replace ("::","");
- if (name.down () == pname.down ()) {
+ if (name.down () == nick.down ()) {
return spec;
}
}
@@ -73,7 +78,7 @@ public interface GXml.GomObject : GLib.Object,
*
* This method will check if nick's name is equal than given name
* in order to avoid use canonical names like "your-name" if your
- * property is your_name; so you can se nick to "YourName" to find
+ * property is your_name; so you can use nick to "YourName" to find
* and instantiate it.
*/
public virtual ParamSpec? find_object_property_name (string pname) {
@@ -372,6 +377,8 @@ public interface GXml.GomObject : GLib.Object,
* assert (nb.node != null);
* }}}
*
+ * Property's name can be canonical or its nick name, see {@link find_object_property_name}
+ *
* Returns: true if property has been set and initialized, false otherwise.
*/
public virtual bool set_instance_property (string name) {
diff --git a/gxml/Makefile.am b/gxml/Makefile.am
index 144c4a3..545ccca 100644
--- a/gxml/Makefile.am
+++ b/gxml/Makefile.am
@@ -68,6 +68,7 @@ sources = \
GXmlElement.vala \
GXmlNamespace.vala \
GXmlNode.vala \
+ GXmlParser.vala \
GXmlProcessingInstruction.vala \
GXmlText.vala \
GXmlHashMapAttr.vala \
diff --git a/gxml/Parser.vala b/gxml/Parser.vala
index e7b043b..bf75412 100644
--- a/gxml/Parser.vala
+++ b/gxml/Parser.vala
@@ -1,7 +1,7 @@
/* -*- Mode: vala; indent-tabs-mode: nil; c-basic-offset: 2; tab-width: 2 -*- */
/* Parser.vala
*
- * Copyright (C) 2016-2017 Daniel Espinosa <esodan gmail com>
+ * Copyright (C) 2016-2019 Daniel Espinosa <esodan gmail com>
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public
@@ -43,6 +43,10 @@ public interface GXml.Parser : Object {
* Controls if, when writing, identation should be used.
*/
public abstract bool indent { get; set; }
+ /**
+ * Controls if, when writing, identation should be used.
+ */
+ public abstract Cancellable? cancellable { get; set; }
/**
* A {@link GXml.DomDocument} to read to or write from
*/
@@ -50,22 +54,18 @@ public interface GXml.Parser : Object {
/**
* Writes a {@link GXml.DomDocument} to a {@link GLib.File}
*/
- public virtual void write_file (GLib.File file,
- GLib.Cancellable? cancellable)
- throws GLib.Error {
+ public virtual void write_file (GLib.File file) throws GLib.Error {
var ostream = file.replace (null, backup,
GLib.FileCreateFlags.NONE, cancellable);
- write_stream (ostream, cancellable);
+ write_stream (ostream);
}
/**
* Writes a {@link GXml.DomDocument} to a {@link GLib.File}
*/
- public virtual async void write_file_async (GLib.File file,
- GLib.Cancellable? cancellable)
- throws GLib.Error {
- var ostream = file.replace (null, backup,
- GLib.FileCreateFlags.NONE, cancellable);
- yield write_stream_async (ostream, cancellable);
+ public virtual async void write_file_async (GLib.File file) throws GLib.Error {
+ var ostream = yield file.replace_async (null, backup,
+ GLib.FileCreateFlags.NONE, 0, cancellable);
+ yield write_stream_async (ostream);
}
/**
* Writes a {@link node} to a string
@@ -78,68 +78,59 @@ public interface GXml.Parser : Object {
/**
* Writes a {@link GXml.DomDocument} to a {@link GLib.OutputStream}
*/
- public abstract void write_stream (OutputStream stream,
- GLib.Cancellable? cancellable) throws GLib.Error;
+ public abstract void write_stream (OutputStream stream) throws GLib.Error;
/**
* Writes asynchronically a {@link node} to a {@link GLib.OutputStream}
*/
- public abstract async void write_stream_async (OutputStream stream,
- GLib.Cancellable? cancellable = null) throws GLib.Error;
+ public abstract async void write_stream_async (OutputStream stream) throws GLib.Error;
/**
* Reads a {@link node} from a {@link GLib.File}
*/
- public virtual void read_file (GLib.File file,
- GLib.Cancellable? cancellable)
+ public virtual void read_file (GLib.File file)
throws GLib.Error {
if (!file.query_exists ())
throw new GXml.ParserError.INVALID_FILE_ERROR (_("File doesn't exist"));
- read_stream (file.read (), cancellable);
+ read_stream (file.read ());
}
/**
* Reads a {@link GXml.DomDocument} from a {@link GLib.File}
*/
- public async virtual void read_file_async (GLib.File file,
- GLib.Cancellable? cancellable)
- throws GLib.Error {
+ public async virtual void read_file_async (GLib.File file) throws GLib.Error {
if (!file.query_exists ())
throw new GXml.ParserError.INVALID_FILE_ERROR (_("File doesn't exist"));
Idle.add (read_file_async.callback);
yield;
- yield read_stream_async (file.read (), cancellable);
+ yield read_stream_async (file.read ());
}
/**
* Read a {@link GXml.DomDocument} from a {@link GLib.InputStream}
*/
- public abstract void read_stream (InputStream stream,
- GLib.Cancellable? cancellable) throws GLib.Error;
+ public abstract void read_stream (InputStream stream) throws GLib.Error;
/**
* Read a {@link GXml.DomDocument} from a {@link GLib.InputStream}
*/
- public abstract async abstract void read_stream_async (InputStream stream,
- GLib.Cancellable? cancellable) throws GLib.Error;
+ public abstract async abstract void read_stream_async (InputStream stream) throws GLib.Error;
/**
* Reads a {@link node} from a string
*/
- public abstract void read_string (string str,
- GLib.Cancellable? cancellable) throws GLib.Error;
+ public abstract void read_string (string str) throws GLib.Error;
/**
* Reads synchronically {@link node} a from a string
*/
- public abstract async void read_string_async (string str, GLib.Cancellable? cancellable) throws GLib.Error;
+ public abstract async void read_string_async (string str) throws GLib.Error;
/**
* Creates an {@link GLib.InputStream} to write a string representation
* in XML
*/
- public abstract InputStream create_stream (GLib.Cancellable? cancellable = null) throws GLib.Error;
+ public abstract InputStream create_stream () throws GLib.Error;
/**
* Creates asyncronically an {@link GLib.InputStream} to write a string representation
* in XML
*/
- public abstract async InputStream
- create_stream_async (GLib.Cancellable? cancellable = null) throws GLib.Error;
+ public abstract async InputStream create_stream_async () throws GLib.Error;
/**
* Iterates in all child nodes and append them to node.
*/
@@ -287,16 +278,15 @@ public interface GXml.Parser : Object {
/**
* Read all childs node feed by stream.
*/
- public abstract void read_child_nodes_stream (GLib.InputStream istream,
- GLib.Cancellable? cancellable = null) throws GLib.Error;
+ public abstract void read_child_nodes_stream (GLib.InputStream istream) throws GLib.Error;
/**
* Read childs nodes from string
*/
- public virtual void read_child_nodes_string (string str, GLib.Cancellable? cancellable) throws GLib.Error {
+ public virtual void read_child_nodes_string (string str) throws GLib.Error {
if (str == "")
throw new ParserError.INVALID_DATA_ERROR (_("Invalid document string, it is empty or is not allowed"));
var stream = new GLib.MemoryInputStream.from_data (str.data);
- read_child_nodes_stream (stream, cancellable);
+ read_child_nodes_stream (stream);
}
/**
* Reads all child nodes as string
diff --git a/gxml/XParser.vala b/gxml/XParser.vala
index 8be8d32..08212af 100644
--- a/gxml/XParser.vala
+++ b/gxml/XParser.vala
@@ -1,7 +1,7 @@
/* -*- Mode: vala; indent-tabs-mode: nil; c-basic-offset: 2; tab-width: 2 -*- */
/* XParser.vala
*
- * Copyright (C) 2016-2017 Daniel Espinosa <esodan gmail com>
+ * Copyright (C) 2016-2019 Daniel Espinosa <esodan gmail com>
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public
@@ -31,7 +31,6 @@ public class GXml.XParser : Object, GXml.Parser {
private DomNode _node;
private TextReader tr;
private Xml.TextWriter tw;
- private Cancellable cancellable;
private DataInputStream tistream;
public bool backup { get; set; }
@@ -39,6 +38,8 @@ public class GXml.XParser : Object, GXml.Parser {
public DomNode node { get { return _node; } }
+ public Cancellable? cancellable { get; set; }
+
public XParser (DomNode node) {
_node = node;
@@ -55,20 +56,17 @@ public class GXml.XParser : Object, GXml.Parser {
tistream = null;
}
- public void write_stream (OutputStream stream,
- GLib.Cancellable? cancellable = null) throws GLib.Error {
+ public void write_stream (OutputStream stream) throws GLib.Error {
var s = dump ();
var b = new GLib.MemoryInputStream.from_data (s.data, null);
- stream.splice (b, GLib.OutputStreamSpliceFlags.NONE);
+ stream.splice (b, GLib.OutputStreamSpliceFlags.NONE, cancellable);
stream.close ();
tw = null;
}
- public async void write_stream_async (OutputStream stream,
- GLib.Cancellable? cancellable = null) throws GLib.Error {
+ public async void write_stream_async (OutputStream stream) throws GLib.Error {
var s = yield dump_async ();
var b = new GLib.MemoryInputStream.from_data (s.data, null);
- stream.splice (b, GLib.OutputStreamSpliceFlags.NONE);
- stream.close ();
+ yield stream.splice_async (b, GLib.OutputStreamSpliceFlags.NONE, 0, cancellable);
tw = null;
}
@@ -77,7 +75,7 @@ public class GXml.XParser : Object, GXml.Parser {
* in XML
*/
public InputStream
- create_stream (GLib.Cancellable? cancellable = null) throws GLib.Error {
+ create_stream () throws GLib.Error {
var s = dump ();
tw = null;
return new GLib.MemoryInputStream.from_data (s.data, null);
@@ -87,7 +85,7 @@ public class GXml.XParser : Object, GXml.Parser {
* in XML
*/
public async InputStream
- create_stream_async (GLib.Cancellable? cancellable = null) throws GLib.Error {
+ create_stream_async () throws GLib.Error {
var s = yield dump_async ();
tw = null;
return new GLib.MemoryInputStream.from_data (s.data, null);
@@ -99,19 +97,19 @@ public class GXml.XParser : Object, GXml.Parser {
public async string write_string_async () throws GLib.Error {
return yield dump_async ();
}
- public void read_string (string str, GLib.Cancellable? cancellable) throws GLib.Error {
+ public void read_string (string str) throws GLib.Error {
if (str == "")
throw new ParserError.INVALID_DATA_ERROR (_("Invalid document string, it is empty or is not allowed"));
var stream = new GLib.MemoryInputStream.from_data (str.data);
- read_stream (stream, cancellable);
+ read_stream (stream);
}
- public async void read_string_async (string str, GLib.Cancellable? cancellable) throws GLib.Error {
+ public async void read_string_async (string str) throws GLib.Error {
if (str == "")
throw new ParserError.INVALID_DATA_ERROR (_("Invalid document string, it is empty or is not allowed"));
var stream = new GLib.MemoryInputStream.from_data (str.data);
Idle.add (read_string_async.callback);
yield;
- yield read_stream_async (stream, cancellable);
+ yield read_stream_async (stream);
}
static int read_callback (void* context, [CCode (array_length=false)] char[] buffer, int len) {
@@ -137,15 +135,8 @@ public class GXml.XParser : Object, GXml.Parser {
dr += bdr;
}
} catch (GLib.Error e) {
- try {
- message (_("Error reading stream: %s"), e.message);
- // parser->tistream.close (parser->cancellable);
- // parser->tistream = null;
- return -1;
- } catch (GLib.Error e) {
- warning (_("Error closing stream: %s"), e.message);
- return -1;
- }
+ message (_("Error reading stream: %s"), e.message);
+ return -1;
}
return dr;
}
@@ -163,8 +154,7 @@ public class GXml.XParser : Object, GXml.Parser {
return 0;
}
- public void read_stream (GLib.InputStream istream,
- GLib.Cancellable? cancellable = null) throws GLib.Error {
+ public void read_stream (GLib.InputStream istream) throws GLib.Error {
this.cancellable = cancellable;
tistream = new DataInputStream (istream);
tr = new TextReader.for_io (read_callback,
@@ -178,8 +168,7 @@ public class GXml.XParser : Object, GXml.Parser {
tr = null;
tistream = null;
}
- public async void read_stream_async (GLib.InputStream istream,
- GLib.Cancellable? cancellable = null) throws GLib.Error {
+ public async void read_stream_async (GLib.InputStream istream) throws GLib.Error {
this.cancellable = cancellable;
tistream = new DataInputStream (istream);
Idle.add (read_stream_async.callback);
@@ -233,16 +222,14 @@ public class GXml.XParser : Object, GXml.Parser {
}
}
}
- public void read_child_nodes_stream (GLib.InputStream istream,
- GLib.Cancellable? cancellable = null) throws GLib.Error {
+ public void read_child_nodes_stream (GLib.InputStream istream) throws GLib.Error {
var b = new MemoryOutputStream.resizable ();
b.splice (istream, 0);
tr = new TextReader.for_memory ((char[]) b.data, (int) b.get_data_size (), "/gxml_memory");
read_child_nodes (_node);
tr = null;
}
- public async void read_child_nodes_stream_async (GLib.InputStream istream,
- GLib.Cancellable? cancellable = null) throws GLib.Error {
+ public async void read_child_nodes_stream_async (GLib.InputStream istream) throws GLib.Error {
var b = new MemoryOutputStream.resizable ();
b.splice (istream, 0);
Idle.add (read_child_nodes_stream_async.callback);
diff --git a/gxml/meson.build b/gxml/meson.build
index 185bbc2..01633d8 100644
--- a/gxml/meson.build
+++ b/gxml/meson.build
@@ -87,6 +87,7 @@ valasources = files ([
'GXmlListNamespaces.vala',
'GXmlNamespace.vala',
'GXmlNode.vala',
+ 'GXmlParser.vala',
'GXmlProcessingInstruction.vala',
'GXmlText.vala',
'GXPathObject.vala',
diff --git a/test/GElementTest.vala b/test/GElementTest.vala
index 0d83451..9cbd5a5 100644
--- a/test/GElementTest.vala
+++ b/test/GElementTest.vala
@@ -246,5 +246,18 @@ class GElementTest : GXmlTest {
assert_not_reached ();
}
});
+ Test.add_func ("/gxml/g-document/dom-write-read", () => {
+ try {
+ DomDocument d = new GDocument ();
+ File dir = File.new_for_path (GXmlTestConfig.TEST_DIR);
+ assert (dir.query_exists ());
+ File f = File.new_for_uri (dir.get_uri ()+"/test-large.xml");
+ assert (f.query_exists ());
+ d.read_from_file (f);
+ } catch (GLib.Error e) {
+ warning ("Error: %s", e.message);
+ assert_not_reached ();
+ }
+ });
}
}
diff --git a/test/GXmlDocumentPerformanceTest.vala b/test/GXmlDocumentPerformanceTest.vala
index 07e1039..b5b60e4 100644
--- a/test/GXmlDocumentPerformanceTest.vala
+++ b/test/GXmlDocumentPerformanceTest.vala
@@ -28,21 +28,21 @@ class GXmlTest.Suite : Object
GLib.Intl.setlocale (GLib.LocaleCategory.ALL, "");
Test.init (ref args);
Test.add_func ("/gxml/g-document/performance", () => {
- try {
- DomDocument d = new GDocument ();
- File dir = File.new_for_path (GXmlTestConfig.TEST_DIR);
- assert (dir.query_exists ());
- File f = File.new_for_uri (dir.get_uri ()+"/test-large.xml");
- assert (f.query_exists ());
- Test.timer_start ();
- d.read_from_file (f);
- var t = Test.timer_elapsed ();
- message ("Elapsed time: %g", t);
- } catch (GLib.Error e) {
- warning ("Error: %s", e.message);
- assert_not_reached ();
- }
- });
- return Test.run ();
-}
+ try {
+ DomDocument d = new GDocument ();
+ File dir = File.new_for_path (GXmlTestConfig.TEST_DIR);
+ assert (dir.query_exists ());
+ File f = File.new_for_uri (dir.get_uri ()+"/test-large.xml");
+ assert (f.query_exists ());
+ Test.timer_start ();
+ d.read_from_file (f);
+ var t = Test.timer_elapsed ();
+ message ("Elapsed time: %g", t);
+ } catch (GLib.Error e) {
+ warning ("Error: %s", e.message);
+ assert_not_reached ();
+ }
+ });
+ return Test.run ();
+ }
}
diff --git a/test/GXmlTest.vala b/test/GXmlTest.vala
index 9be4077..4e9e6b4 100644
--- a/test/GXmlTest.vala
+++ b/test/GXmlTest.vala
@@ -2,7 +2,7 @@
/* GXmlTest.vala
*
* Copyright (C) 2011-2013 Richard Schwarting <aquarichy gmail com>
- * Copyright (C) 2011-2015 Daniel Espinosa <esodan gmail com>
+ * Copyright (C) 2011-2019 Daniel Espinosa <esodan gmail com>
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public
@@ -69,8 +69,9 @@ class GXmlTest {
GomSerializationTest.add_tests ();
GomSchemaTest.add_tests ();
CssSelectorTest.add_tests ();
+ NodeListTest.add_tests ();
- Test.run ();
+ Test.run ();
return 0;
}
diff --git a/test/GomDocumentTest.vala b/test/GomDocumentTest.vala
index d27ccdf..5a86f03 100644
--- a/test/GomDocumentTest.vala
+++ b/test/GomDocumentTest.vala
@@ -23,6 +23,33 @@
using GXml;
class GomDocumentTest : GXmlTest {
+ class ObjectDocument : GomDocument {
+ [Description (nick="::ROOT")]
+ public ObjectParent root { get; set; }
+ public class ObjectParent : GomElement {
+ construct {
+ try { initialize ("root"); }
+ catch (GLib.Error e) { warning ("Error: "+e.message); }
+ }
+ [Description (nick="::text")]
+ public string text { get; set; }
+ [Description (nick="::prop")]
+ public ObjectProperty prop { get; set; }
+ public class ObjectProperty : Object, GomProperty {
+ public string? value { owned get; set; }
+ public bool validate_value (string? val) {
+ return true;
+ }
+ }
+ public ObjectChild child { get; set; }
+ public class ObjectChild : GomElement {
+ construct {
+ try { initialize ("child"); }
+ catch (GLib.Error e) { warning ("Error: "+e.message); }
+ }
+ }
+ }
+ }
public static void add_tests () {
Test.add_func ("/gxml/gom-document/construct_api", () => {
try {
@@ -540,6 +567,7 @@ class GomDocumentTest : GXmlTest {
n.append_child (n2);
message (d.write_string ());
string str = d.write_string ();
+ message ("Output document: %s", str);
assert ("<Node" in str);
assert ("<Node name=\"value\"><Node2/></Node>" in str);
} catch (GLib.Error e) {
@@ -723,5 +751,16 @@ class GomDocumentTest : GXmlTest {
assert_not_reached ();
} //<!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.1//EN"
"http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd">
});
+ Test.add_func ("/gxml/gom-document/parse-root-element", () => {
+ try {
+ var d = new ObjectDocument ();
+ d.read_from_string ("""<root><child id="id1"/><child id="id2"/></root>""");
+ message (d.write_string ());
+ assert (d.root != null);
+ } catch (GLib.Error e) {
+ GLib.message ("Error: "+e.message);
+ assert_not_reached ();
+ } //<!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.1//EN"
"http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd">
+ });
}
}
diff --git a/test/GomSerializationTest.vala b/test/GomSerializationTest.vala
index cdc6792..f768313 100644
--- a/test/GomSerializationTest.vala
+++ b/test/GomSerializationTest.vala
@@ -971,7 +971,7 @@ class GomSerializationTest : GXmlTest {
try {
var b = new Book ();
var parser = new XParser (b);
- parser.read_string ("<book name=\"Loco\"/>", null);
+ parser.read_string ("<book name=\"Loco\"/>");
string s = parser.write_string ();
assert (s != null);
GLib.message ("Doc:"+s);
@@ -1040,7 +1040,7 @@ class GomSerializationTest : GXmlTest {
#endif
assert ("<Motor/>" in s);
var parser = new XParser (m);
- parser.read_string ("<Motor On=\"true\" Torque=\"3.1416\" Speed=\"3600.1011\" TensionType=\"dc\"
Tension=\"125\"/>", null);
+ parser.read_string ("<Motor On=\"true\" Torque=\"3.1416\" Speed=\"3600.1011\" TensionType=\"dc\"
Tension=\"125\"/>");
s = m.to_string ();
#if DEBUG
GLib.message ("doc:"+s);
@@ -1076,7 +1076,7 @@ class GomSerializationTest : GXmlTest {
#endif
assert ("<BookStand Classification=\"Science\"/>" in s);
var parser = new XParser (bs);
- parser.read_string ("<BookStand Classification=\"Science\"><BookRegister Year=\"2016\"/><BookRegister
Year=\"2010\"/><Test/><BookRegister Year=\"2000\"/></BookStand>", null);
+ parser.read_string ("<BookStand Classification=\"Science\"><BookRegister Year=\"2016\"/><BookRegister
Year=\"2010\"/><Test/><BookRegister Year=\"2000\"/></BookStand>");
s = bs.to_string ();
#if DEBUG
GLib.message ("doc:"+s);
[
Date Prev][
Date Next] [
Thread Prev][
Thread Next]
[
Thread Index]
[
Date Index]
[
Author Index]