actual/packages/node-libofx/libofx/ofxconnect/nodeparser.cpp
2022-04-28 22:44:38 -04:00

140 lines
4.4 KiB
C++

/***************************************************************************
nodeparser.cpp
-------------------
copyright : (C) 2005 by Ace Jones
email : acejones@users.sourceforge.net
***************************************************************************/
/**@file
* \brief Implementation of nodeparser object, which facilitiates searching
* for nodes in an XML file using a notation similiar to XPath.
*/
/***************************************************************************
* *
* This program is free software; 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 2 of the License, or *
* (at your option) any later version. *
* *
***************************************************************************/
#include "nodeparser.h"
using std::string;
using std::vector;
NodeParser::NodeParser(const xmlpp::Node::NodeList& list): xmlpp::Node::NodeList(list)
{
}
NodeParser::NodeParser(const xmlpp::Node* node)
{
push_back(const_cast<xmlpp::Node*>(node));
}
NodeParser::NodeParser(const xmlpp::DomParser& parser)
{
xmlpp::Node* node = parser.get_document()->get_root_node();
push_back(const_cast<xmlpp::Node*>(node));
}
NodeParser NodeParser::Path(const xmlpp::Node* node, const std::string& path)
{
//std::cout << __PRETTY_FUNCTION__ << std::endl;
NodeParser result;
// split path string into the 1st level, and the rest
std::string key = path;
std::string remainder;
std::string::size_type token_pos = path.find('/');
if ( token_pos != std::string::npos )
{
key = path.substr(0, token_pos );
remainder = path.substr( token_pos + 1 );
}
// find the first level nodes that match
xmlpp::Node::NodeList list = node->get_children();
for (xmlpp::Node::NodeList::iterator iter = list.begin(); iter != list.end(); ++iter)
{
if ( (*iter)->get_name() == key )
{
// if there is still some path left, ask for the rest of the path from those nodes.
if ( remainder.length() )
{
NodeParser remain_list = NodeParser(*iter).Path(remainder);
result.splice(result.end(), remain_list);
}
// otherwise add the node to the result list.
else
result.push_back(*iter);
}
}
return result;
}
NodeParser NodeParser::Path(const std::string& path) const
{
//std::cout << __PRETTY_FUNCTION__ << std::endl;
NodeParser result;
for (const_iterator iter = begin(); iter != end(); ++iter)
{
NodeParser iter_list = Path(*iter, path);
result.splice(result.end(), iter_list);
}
return result;
}
NodeParser NodeParser::Select(const std::string& key, const std::string& value) const
{
//std::cout << __PRETTY_FUNCTION__ << std::endl;
NodeParser result;
for (const_iterator iter = begin(); iter != end(); ++iter)
{
xmlpp::Node::NodeList list = (*iter)->get_children();
for (xmlpp::Node::NodeList::const_iterator iter3 = list.begin(); iter3 != list.end(); ++iter3)
{
if ( (*iter3)->get_name() == key )
{
xmlpp::Node::NodeList list = (*iter3)->get_children();
for (xmlpp::Node::NodeList::const_iterator iter4 = list.begin(); iter4 != list.end(); ++iter4)
{
const xmlpp::TextNode* nodeText = dynamic_cast<const xmlpp::TextNode*>(*iter4);
if ( nodeText && nodeText->get_content() == value )
result.push_back(*iter);
break;
}
}
}
}
return result;
}
vector<string> NodeParser::Text(void) const
{
vector<string> result;
// Go through the list of nodes
for (xmlpp::Node::NodeList::const_iterator iter = begin(); iter != end(); ++iter)
{
// Find the text child node, and print that
xmlpp::Node::NodeList list = (*iter)->get_children();
for (xmlpp::Node::NodeList::const_iterator iter2 = list.begin(); iter2 != list.end(); ++iter2)
{
const xmlpp::TextNode* nodeText = dynamic_cast<const xmlpp::TextNode*>(*iter2);
if ( nodeText )
{
result.push_back(nodeText->get_content());
}
}
}
if ( result.empty() )
result.push_back(string());
return result;
}
// vim:cin:si:ai:et:ts=2:sw=2: