update traversing

This commit is contained in:
a-sansara 2018-08-03 18:47:46 +02:00
parent 7796fb2c5c
commit e6518a32de
12 changed files with 487 additions and 228 deletions

View File

@ -62,7 +62,6 @@ sources = [
'src/vala/Pluie/Io.StreamLineMark.vala',
'src/vala/Pluie/Yaml.global.vala',
'src/vala/Pluie/Yaml.Config.vala',
'src/vala/Pluie/Yaml.Document.vala',
'src/vala/Pluie/Yaml.Event.vala',
'src/vala/Pluie/Yaml.Loader.vala',
'src/vala/Pluie/Yaml.Finder.vala',

View File

@ -0,0 +1,130 @@
/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
*
* @software : lib-yaml <https://git.pluie.org/pluie/lib-yaml>
* @version : 0.3
* @date : 2018
* @licence : GPLv3.0 <http://www.gnu.org/licenses/>
* @author : a-Sansara <[dev]at[pluie]dot[org]>
* @copyright : pluie.org <http://www.pluie.org/>
*
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
*
* This file is part of lib-yaml.
*
* lib-yaml is free software (free as in speech) : you can redistribute it
* and/or modify it under the terms of the GNU General Public License as
* published by the Free Software Foundation, either version 3 of the License,
* or (at your option) any later version.
*
* lib-yaml is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* You should have received a copy of the GNU General Public License
* along with lib-yaml. If not, see <http://www.gnu.org/licenses/>.
*
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
*/
using GLib;
using Gee;
using Pluie;
int main (string[] args)
{
Echo.init(false);
var path = "resources/test.yml";
var done = false;
of.title ("Pluie Yaml Library", Pluie.Yaml.VERSION, "a-sansara");
Pluie.Yaml.Scanner.DEBUG = false;
var config = new Yaml.Config (path, true);
var spath = "bo.host{0}";
var node = config.root_node ();
if ((done = node != null)) {
node.display_childs ();
of.action("retriew child sequence node", "product");
var child = config.get("product");
of.echo (child.to_string (false));
of.action("retriew sequence last child node", child.name);
var nchild = child.last_child ();
if (nchild != null) {
of.echo (nchild.to_string ());
}
of.action("retriew sequence first child node", child.name);
nchild = child.first_child ();
if (nchild != null) {
of.echo (nchild.to_string ());
of.action("retriew sequence next sibling node", nchild.name);
nchild = nchild.next_sibling ();
if (nchild != null) {
of.echo (nchild.to_string ());
of.action("retriew sequence previous sibling node", nchild.name);
nchild = nchild.previous_sibling ();
if (nchild != null) {
of.echo (nchild.to_string ());
}
}
}
of.echo("\n ================================ ");
of.action("retriew mapping child node", "ship-to");
child = config.get("ship-to");
of.echo (child.to_string (false));
of.action("retriew mapping last child node", child.name);
nchild = child.last_child ();
if (nchild != null) {
of.echo (nchild.to_string ());
}
of.action("retriew mapping first child node", child.name);
nchild = child.first_child ();
if (nchild != null) {
of.echo (nchild.to_string ());
}
of.action("loop throught mapping next sibling", child.name);
while (!child.is_last_child()) {
child = child.next_sibling ();
of.echo (child.to_string (false));
}
of.action("loop throught mapping previous sibling", child.name);
while (!child.is_first_child()) {
child = child.previous_sibling ();
of.echo (child.to_string (false));
}
of.echo("\n ================================ ");
of.action ("current node is ", child.name);
of.echo ("switch node : next_sibling ().next_sibling ().first_child ()");
child = child.next_sibling ().next_sibling ().first_child ();
of.action ("current node is ", child.name);
of.echo ("use finder to retriew parent node");
var n = config.get ("bill-to");
if (n!= null) {
of.echo (n.to_string (false));
of.echo ("parent (mapping) contains child ? %d".printf ((int) n.contains (child)));
}
of.action ("current node is ", child.name);
of.echo ("switch node : parent.next_sibling ().next_sibling ().first_child ().first_child ()");
child = child.parent.next_sibling ().next_sibling ().first_child ().first_child ();
of.action ("current node is ", child.name);
of.echo ("use finder to retriew parent node");
n = config.get ("product{0}");
if (n!= null) {
of.echo (n.to_string (false));
of.echo ("parent (sequence) contains child ? %d".printf ((int) n.contains (child)));
}
}
of.rs (done);
of.echo ();
return (int) done;
}

View File

@ -34,29 +34,32 @@ using Pluie;
/**
* parent class representing a Yaml Node whenether was his type
*/
public class Pluie.Yaml.BaseNode : Object, Pluie.Yaml.Node
public class Pluie.Yaml.BaseNode : Object, Pluie.Yaml.Node, Pluie.Yaml.NodeCollection
{
/**
* universal unique identifier
*/
public string uuid { get; internal set; }
public string uuid { get; internal set; }
public string anchor { get; internal set; }
/**
* anchor
*/
public string anchor { get; internal set; }
/**
* find mode related to Yaml.FIND_MODE, default is Yaml.FIND_MODE.SQUARE_BRACKETS
*/
public static Yaml.FIND_MODE mode { get; set; default = Yaml.FIND_MODE.DOT; }
public static Yaml.FIND_MODE mode { get; set; default = Yaml.FIND_MODE.DOT; }
/**
* node type related to Yaml.NODE_TYPE
*/
public Yaml.NODE_TYPE node_type { get; internal set; }
public Yaml.NODE_TYPE node_type { get; internal set; }
/**
* current representation level
*/
public int level { get; internal set; }
public int level { get; internal set; }
/**
* parent node
@ -104,6 +107,16 @@ public class Pluie.Yaml.BaseNode : Object, Pluie.Yaml.Node
this.uuid = Yaml.uuid ();
}
/**
* test if specifiyed node is current node
* @param child the Yaml.Node node to test
*/
public virtual bool same_node (Yaml.Node? node)
{
return node != null && node.uuid != this.uuid;
}
/**
*
*/
@ -165,6 +178,38 @@ public class Pluie.Yaml.BaseNode : Object, Pluie.Yaml.Node
return false;
}
/**
*
*/
public bool is_last (Yaml.Node child) {
return true;
}
/**
*
*/
public bool is_first (Yaml.Node child) {
return true;
}
/**
*
*/
public virtual Yaml.Node? first_child ()
{
Yaml.Node? child = (this as Yaml.NodeCollection).first_child ();
return child;
}
/**
*
*/
public virtual Yaml.Node? last_child ()
{
Yaml.Node? child = (this as Yaml.NodeCollection).last_child ();
return child;
}
/**
* give the next sibling node
*/
@ -173,6 +218,7 @@ public class Pluie.Yaml.BaseNode : Object, Pluie.Yaml.Node
Yaml.Node? sibling = null;
if (this.parent != null) {
sibling = (this.parent as Yaml.NodeCollection).child_next_sibling (this);
if (sibling == this) sibling = null;
}
return sibling;
}
@ -203,6 +249,31 @@ public class Pluie.Yaml.BaseNode : Object, Pluie.Yaml.Node
return parent;
}
/**
* retriew the previous sibling of specifiyed child node
* @param child
*/
public virtual Yaml.Node? child_previous_sibling (Yaml.Node child)
{
return null;
}
/**
* retriew the next sibling of specifiyed child node
* @param child
*/
public virtual Yaml.Node? child_next_sibling (Yaml.Node child)
{
return null;
}
/**
*
*/
public virtual int get_size () {
return this.node_type.is_collection () ? (this as Yaml.NodeCollection).get_size () : 0;
}
/**
* check if node has child nodes
*/
@ -211,6 +282,22 @@ public class Pluie.Yaml.BaseNode : Object, Pluie.Yaml.Node
return this.node_type.is_collection () && (this as Yaml.NodeCollection).get_size () > 0;
}
/**
* check if first chikd
*/
public virtual bool is_first_child ()
{
return false;
}
/**
* check if last chikd
*/
public virtual bool is_last_child ()
{
return false;
}
/**
* check if current node contains the specifiyed child node
* @param child

View File

@ -1,48 +0,0 @@
/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
*
* @software : lib-yaml <https://git.pluie.org/pluie/lib-yaml>
* @version : 0.3
* @date : 2018
* @licence : GPLv3.0 <http://www.gnu.org/licenses/>
* @author : a-Sansara <[dev]at[pluie]dot[org]>
* @copyright : pluie.org <http://www.pluie.org/>
*
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
*
* This file is part of lib-yaml.
*
* lib-yaml is free software (free as in speech) : you can redistribute it
* and/or modify it under the terms of the GNU General Public License as
* published by the Free Software Foundation, either version 3 of the License,
* or (at your option) any later version.
*
* lib-yaml is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* You should have received a copy of the GNU General Public License
* along with lib-yaml. If not, see <http://www.gnu.org/licenses/>.
*
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
*/
using Pluie;
/**
* a class representing a single/pair mapping node
*/
public class Pluie.Yaml.Document : Yaml.NodeMap
{
/**
* construct a single/pair mapping node
* @param parent the parent node
* @param name the current name (key) of sequence node
* @param data the current scalar data
*/
public Document (Yaml.Node? parent = null, string? name = null, string? data = null)
{
this.standard (null, NODE_TYPE.ROOT);
this.name = "PluieYamlRootNode";
}
}

View File

@ -51,46 +51,6 @@ public class Pluie.Yaml.Finder : Object
this.context = context;
}
/**
* get a path definition depending of current Node.mode
* if path definition is Yaml.FIND_MODE.DOT the path is convert to a
* Yaml.FIND_MODE.SQUARE_BRACKETS path definition
* @path the path definition
* @return the find path definition according to current Node.mode
*/
private string find_path (string path)
{
MatchInfo? mi = null;
string search = "";
if (BaseNode.mode.is_dot ()) {
var stk = /([^.]*)\./.split (path);
foreach (var s in stk) {
if (s.strip() != "") {
if (/([^\{]+)(\{[0-9]+\})/.match (s, 0, out mi)) {
search = search + "[%s]%s".printf (mi.fetch (1), mi.fetch (2));
}
else {
search = search + "[%s]".printf (s);
}
}
}
}
else {
search = path;
}
return search;
}
/**
* indicates if specifiyed MatchInfo is related to a mapping node only or a collection node
* @param mi
*/
private bool is_collection_path (MatchInfo mi, bool mappingOnly = false)
{
return (mi.fetch (FIND_COLLECTION.OPEN) == "[" && mi.fetch (FIND_COLLECTION.CLOSE) == "]") || (!mappingOnly &&
(mi.fetch (FIND_COLLECTION.OPEN) == "{" && mi.fetch (FIND_COLLECTION.CLOSE) == "}"));
}
/**
* find a specific child Yaml.Node corresponding to path definition
* path definition has two mode.
@ -146,4 +106,45 @@ public class Pluie.Yaml.Finder : Object
if (!match) node = null;
return node;
}
/**
* get a path definition depending of current Node.mode
* if path definition is Yaml.FIND_MODE.DOT the path is convert to a
* Yaml.FIND_MODE.SQUARE_BRACKETS path definition
* @path the path definition
* @return the find path definition according to current Node.mode
*/
private string find_path (string path)
{
MatchInfo? mi = null;
string search = "";
if (BaseNode.mode.is_dot ()) {
var stk = /([^.]*)\./.split (path);
foreach (var s in stk) {
if (s.strip() != "") {
if (/([^\{]+)(\{[0-9]+\})/.match (s, 0, out mi)) {
search = search + "[%s]%s".printf (mi.fetch (1), mi.fetch (2));
}
else {
search = search + "[%s]".printf (s);
}
}
}
}
else {
search = path;
}
return search;
}
/**
* indicates if specifiyed MatchInfo is related to a mapping node only or a collection node
* @param mi
*/
private bool is_collection_path (MatchInfo mi, bool mappingOnly = false)
{
return (mi.fetch (FIND_COLLECTION.OPEN) == "[" && mi.fetch (FIND_COLLECTION.CLOSE) == "]") || (!mappingOnly &&
(mi.fetch (FIND_COLLECTION.OPEN) == "{" && mi.fetch (FIND_COLLECTION.CLOSE) == "}"));
}
}

View File

@ -84,25 +84,6 @@ public class Pluie.Yaml.Loader
return this.scanner.get_nodes ();
}
/**
* bypass_ellipse
*/
private bool bypass_ellipse (int errorLine, int line)
{
bool bypass = false;
if (errorLine > 0 && line > 0) {
if (line < errorLine - 7) bypass = true;
else if (line == errorLine - 7 && line > 1) {
of.echo ("%s%s%s".printf (
of.c (ECHO.MICROTIME ).s (" %03d ".printf (line-1)),
of.c (ECHO.DATE).s ("| "),
of.c (ECHO.COMMAND).s ("... ")
));
}
}
return bypass;
}
/**
* display original file
*/
@ -138,4 +119,24 @@ public class Pluie.Yaml.Loader
of.echo (errorLine == 0 ? "EOF" : "");
of.state (errorLine == 0);
}
/**
* bypass_ellipse
*/
private bool bypass_ellipse (int errorLine, int line)
{
bool bypass = false;
if (errorLine > 0 && line > 0) {
if (line < errorLine - 7) bypass = true;
else if (line == errorLine - 7 && line > 1) {
of.echo ("%s%s%s".printf (
of.c (ECHO.MICROTIME ).s (" %03d ".printf (line-1)),
of.c (ECHO.DATE).s ("| "),
of.c (ECHO.COMMAND).s ("... ")
));
}
}
return bypass;
}
}

View File

@ -30,7 +30,7 @@
using GLib;
using Pluie;
public interface Pluie.Yaml.Node : Object
public interface Pluie.Yaml.Node : Object, Yaml.NodeCollection
{
/**
* universal unique identifier
@ -59,6 +59,12 @@ public interface Pluie.Yaml.Node : Object
*/
public abstract string? name { get; internal set; default = null; }
/**
* test if specifiyed node is current node
* @param child the Yaml.Node node to test
*/
public abstract bool same_node (Yaml.Node? node);
/**
* add a child node to current collection (mapping or sequence) node
* @param child the Yaml.Node child to add
@ -94,6 +100,16 @@ public interface Pluie.Yaml.Node : Object
*/
public abstract bool has_child_nodes ();
/**
* check if first chikd
*/
public abstract bool is_first_child ();
/**
* check if last chikd
*/
public abstract bool is_last_child ();
/**
* give the next sibling node
*/

View File

@ -48,6 +48,28 @@ public interface Pluie.Yaml.NodeCollection
*/
public abstract Yaml.Node? child_next_sibling (Yaml.Node child);
/**
* retriew the previous sibling of specifiyed child node
* @param child
*/
public abstract Yaml.Node? first_child ();
/**
* retriew the next sibling of specifiyed child node
* @param child
*/
public abstract Yaml.Node? last_child ();
/**
* check if first chikd
*/
public abstract bool is_first (Yaml.Node child);
/**
* check if last chikd
*/
public abstract bool is_last (Yaml.Node child);
/**
* count childnodes
*/

View File

@ -39,7 +39,9 @@ public class Pluie.Yaml.NodeMap : Yaml.BaseNode, Yaml.NodeCollection
/**
* map collection for Yaml.NodeMap node
*/
public HashMap<string, Yaml.Node> map { get; internal set; }
public Gee.HashMap<string, Yaml.Node> map { get; internal set; }
private Gee.ArrayList<string> keys { get; internal set; }
/**
* construct a mapping node
@ -50,6 +52,7 @@ public class Pluie.Yaml.NodeMap : Yaml.BaseNode, Yaml.NodeCollection
{
base (parent, NODE_TYPE.MAPPING);
this.map = new HashMap<string, Yaml.Node> ();
this.keys = new ArrayList<string> ();
this.name = name;
}
@ -75,6 +78,13 @@ public class Pluie.Yaml.NodeMap : Yaml.BaseNode, Yaml.NodeCollection
node.on_change_parent ();
node.level = this.level + 1;
node.parent = this;
if (this.keys == null) {
this.keys = new ArrayList<string> ();
}
if (this.keys.contains(node.name)) {
this.keys.remove(node.name);
}
this.keys.add(node.name);
if (this.map == null) {
this.map = new HashMap<string, Yaml.Node> ();
}
@ -91,8 +101,8 @@ public class Pluie.Yaml.NodeMap : Yaml.BaseNode, Yaml.NodeCollection
of.action ("display childs\n");
}
of.echo (this.to_string ());
if (this.map.size > 0) {
foreach (string key in this.map.keys) {
if (this.keys != null && this.keys.size > 0) {
foreach (string key in this.keys) {
var n = this.map.get(key);
if (n.node_type.is_mapping ()) (n as Yaml.NodeMap).display_childs (false);
else if (n.node_type.is_sequence ()) (n as Yaml.NodeSequence).display_childs (false);
@ -111,7 +121,7 @@ public class Pluie.Yaml.NodeMap : Yaml.BaseNode, Yaml.NodeCollection
* count childnodes
*/
public int get_size () {
return this.map.size;
return this.keys.size;
}
/**
@ -129,51 +139,76 @@ public class Pluie.Yaml.NodeMap : Yaml.BaseNode, Yaml.NodeCollection
return has;
}
/**
*
*/
public bool is_last (Yaml.Node child) {
return this.keys.last() == child.name;
}
/**
*
*/
public bool is_first (Yaml.Node child) {
return this.keys.first() == child.name;
}
/**
*
*/
private string? next_key (string skey)
{
string? mkey = this.keys.last() != skey ? this.keys.get (this.keys.index_of (skey)+1) : null;
return mkey;
}
/**
*
*/
private string? previous_key (string skey)
{
string? mkey = this.keys.first() != skey ? this.keys.get (this.keys.index_of (skey)-1) : null;
return mkey;
}
/**
* retriew the next sibling of specifiyed child node
* @param child
*/
public virtual Yaml.Node? child_next_sibling (Yaml.Node child)
{
Yaml.Node? target = null;
bool match = false;
if (this.map.size > 0) {
foreach (string key in this.map.keys) {
if (child.name == key) {
match = true;
continue;
}
if (match) {
target = this.map.get(key);
}
}
}
var key = this.next_key (child.name);
var target = key != null ? this.map[key] : null;
return target;
}
/**
* retriew the previous sibling of specifiyed child node
* retriew the next sibling of specifiyed child node
* @param child
*/
public virtual Yaml.Node? child_previous_sibling (Yaml.Node child)
{
Yaml.Node? target = null;
bool match = false;
if (this.map.size > 0) {
foreach (string key in this.map.keys) {
if (child.name == key) {
match = true;
break;
}
target = this.map.get(key);
}
}
if (!match) {
target = null;
}
var key = this.previous_key (child.name);
var target = key != null ? this.map[key] : null;
return target;
}
/**
*
*/
public override Yaml.Node? first_child ()
{
return this.map[this.keys.first()];
}
/**
*
*/
public override Yaml.Node? last_child ()
{
return this.map[this.keys.last()];
}
/**
* clone current node
* @param the name of clone

View File

@ -102,11 +102,40 @@ public class Pluie.Yaml.NodeSequence : Yaml.BaseNode, Yaml.NodeCollection
return this.list.get (index);
}
/**
*
*/
public new bool is_last (Yaml.Node child) {
return child.same_node(this.last_child());
}
/**
*
*/
public new bool is_first (Yaml.Node child) {
return child.same_node(this.first_child());
}
/**
* count childnodes
*/
public new int get_size () {
return this.list == null ? 0 : this.list.size;
}
/**
* check if current node contains the specifiyed child node
* @param child
*/
public override bool contains (Yaml.Node child) {
return this.list.contains (child);
}
/**
* retriew the first child node
* @return the first child node
*/
public Yaml.Node first ()
public override Yaml.Node? first_child ()
{
return this.list.first ();
}
@ -116,7 +145,7 @@ public class Pluie.Yaml.NodeSequence : Yaml.BaseNode, Yaml.NodeCollection
* retriew the last child node
* @return the last child node
*/
public Yaml.Node last ()
public override Yaml.Node? last_child ()
{
return this.list.last ();
}
@ -148,20 +177,7 @@ public class Pluie.Yaml.NodeSequence : Yaml.BaseNode, Yaml.NodeCollection
}
}
/**
* count childnodes
*/
public int get_size () {
return this.list == null ? 0 : this.list.size;
}
/**
* check if current node contains the specifiyed child node
* @param child
*/
public override bool contains (Yaml.Node child) {
return this.list.contains (child);
}
/**
* retriew the next sibling of specifiyed child node

View File

@ -138,59 +138,6 @@ public class Pluie.Yaml.Processor
}
}
/**
* retriew the next Yaml Event
*/
private Yaml.Event? next_event ()
{
Yaml.Event? evt = null;
if (this.iterator.has_next () && this.iterator.next ()) {
evt = this.iterator.get ();
}
return evt;
}
/**
* retriew the next Yaml Value Event closest to Key Event
*/
private Yaml.Event? get_value_key_event ()
{
Yaml.Event? evt = null;
var e = this.iterator.get ();
if (e != null && e.evtype.is_key ()) {
evt = this.next_event ();
}
return evt;
}
/**
* retriew the next Yaml Value Event
*/
private Yaml.Event? get_value_event ()
{
Yaml.Event? evt = null;
var e = this.iterator.get ();
if (e != null && e.evtype.is_value ()) {
evt = this.next_event ();
}
return evt;
}
/**
*
*/
public void reset ()
{
this.root = new Yaml.NodeRoot ();
this.prev_node = this.root;
this.parent_node = this.root;
this.iterator = this.events.iterator ();
this.change = false;
this.ckey = null;
this.idAnchor = null;
this.beginFlowSeq = false;
}
/**
* processing the events list and generate the corresponding Yaml Nodes
*/
@ -238,6 +185,59 @@ public class Pluie.Yaml.Processor
return done;
}
/**
*
*/
private void reset ()
{
this.root = new Yaml.NodeRoot ();
this.prev_node = this.root;
this.parent_node = this.root;
this.iterator = this.events.iterator ();
this.change = false;
this.ckey = null;
this.idAnchor = null;
this.beginFlowSeq = false;
}
/**
* retriew the next Yaml Event
*/
private Yaml.Event? next_event ()
{
Yaml.Event? evt = null;
if (this.iterator.has_next () && this.iterator.next ()) {
evt = this.iterator.get ();
}
return evt;
}
/**
* retriew the next Yaml Value Event closest to Key Event
*/
private Yaml.Event? get_value_key_event ()
{
Yaml.Event? evt = null;
var e = this.iterator.get ();
if (e != null && e.evtype.is_key ()) {
evt = this.next_event ();
}
return evt;
}
/**
* retriew the next Yaml Value Event
*/
private Yaml.Event? get_value_event ()
{
Yaml.Event? evt = null;
var e = this.iterator.get ();
if (e != null && e.evtype.is_value ()) {
evt = this.next_event ();
}
return evt;
}
/**
*
*/

View File

@ -133,19 +133,6 @@ public class Pluie.Yaml.Scanner
return this.processor.error_event;
}
/**
*
*/
public void before_run (string? path)
{
if (path != null && this.reader.path != path) {
this.reader.load (path);
}
else {
this.reader.rewind(new Io.StreamLineMark(0, 0));
}
}
/**
* scan specifiyed file generated throught yaml.c
* @param optional file path to scan
@ -168,6 +155,19 @@ public class Pluie.Yaml.Scanner
return this.done;
}
/**
*
*/
private void before_run (string? path)
{
if (path != null && this.reader.path != path) {
this.reader.load (path);
}
else {
this.reader.rewind(new Io.StreamLineMark(0, 0));
}
}
/**
* register event version
* @param evtdata the current data event