/*
* DOMParser.cpp
*****************************************************************************
* Copyright (C) 2010 - 2011 Klagenfurt University
*
* Created on: Aug 10, 2010
* Authors: Christopher Mueller <christopher.mueller@itec.uni-klu.ac.at>
* Christian Timmerer <christian.timmerer@itec.uni-klu.ac.at>
*
* This program is free software; you can redistribute it and/or modify it
* under the terms of the GNU Lesser General Public License as published
* by the Free Software Foundation; either version 2.1 of the License, or
* (at your option) any later version.
*
* This program 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 Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public License
* along with this program; if not, write to the Free Software Foundation,
* Inc., 51 Franklin Street, Fifth Floor, Boston MA 02110-1301, USA.
*****************************************************************************/
#ifdef HAVE_CONFIG_H
# include "config.h"
#endif
#include "DOMParser.h"
#include <vector>
#include <stack>
#include <cstring>
#include <vlc_xml.h>
using namespace adaptive::xml;
DOMParser::DOMParser() :
root( nullptr ),
stream( nullptr ),
vlc_reader( nullptr )
{
}
DOMParser::DOMParser (stream_t *stream) :
root( nullptr ),
stream( stream ),
vlc_reader( nullptr )
{
}
DOMParser::~DOMParser ()
{
delete this->root;
if(this->vlc_reader)
xml_ReaderDelete(this->vlc_reader);
}
Node* DOMParser::getRootNode ()
{
return this->root;
}
bool DOMParser::parse (bool b)
{
if(!stream)
return false;
if(!vlc_reader && !(vlc_reader = xml_ReaderCreate(stream, stream)))
return false;
struct vlc_logger *const logger = vlc_reader->obj.logger;
if(!b)
vlc_reader->obj.logger = nullptr;
root = processNode(b);
vlc_reader->obj.logger = logger;
if ( root == nullptr )
return false;
return true;
}
bool DOMParser::reset(stream_t *s)
{
stream = s;
if(!vlc_reader)
return true;
delete root;
root = nullptr;
xml_ReaderDelete(vlc_reader);
vlc_reader = xml_ReaderCreate(s, s);
return !!vlc_reader;
}
Node* DOMParser::processNode(bool b_strict)
{
const char *data, *ns;
int type;
std::stack<Node *> lifo;
while( (type = xml_ReaderNextNodeNS(vlc_reader, &data, &ns)) > 0 )
{
switch(type)
{
case XML_READER_STARTELEM:
{
Namespaces::Ptr ptr = nss.registerNamespace(ns);
bool empty = xml_ReaderIsEmptyElement(vlc_reader);
const char *unprefixed = std::strchr(data, ':');
data = unprefixed ? unprefixed + 1 : data;
auto name = std::make_unique<std::string>(data);
Node *node = new (std::nothrow) Node(std::move(name), ptr);
if(node)
{
if(!lifo.empty())
lifo.top()->addSubNode(node);
lifo.push(node);
addAttributesToNode(node);
}
if(empty && lifo.size() > 1)
lifo.pop();
break;
}
case XML_READER_TEXT:
{
if(!lifo.empty())
lifo.top()->setText(std::string(data));
break;
}
case XML_READER_ENDELEM:
{
if(lifo.empty())
return nullptr;
Node *node = lifo.top();
lifo.pop();
if(lifo.empty())
return node;
}
default:
break;
}
}
while( lifo.size() > 1 )
lifo.pop();
Node *node = (!lifo.empty()) ? lifo.top() : nullptr;
if(b_strict && node)
{
delete node;
return nullptr;
}
return node;
}
void DOMParser::addAttributesToNode (Node *node)
{
const char *attrValue;
const char *attrName;
const char *ns;
while((attrName = xml_ReaderNextAttrNS(this->vlc_reader, &attrValue, &ns)) != nullptr)
{
Namespaces::Ptr ptr = nss.registerNamespace(ns ? ns : "");
std::string key = attrName;
std::string value = attrValue;
node->addAttribute(key, ptr, value);
}
}
void DOMParser::print (Node *node, int offset)
{
for(int i = 0; i < offset; i++)
msg_Dbg(this->stream, " ");
msg_Dbg(this->stream, "%s", node->getName().c_str());
const Node::Attributes &attributes = node->getAttributes();
for(auto & attr : attributes)
msg_Dbg(this->stream, " %s=%s", attr.name.c_str(), attr.value.c_str());
msg_Dbg(this->stream, "\n");
offset++;
for(size_t i = 0; i < node->getSubNodes().size(); i++)
{
this->print(node->getSubNodes().at(i), offset);
}
}
void DOMParser::print ()
{
this->print(this->root, 0);
}
¤ Dauer der Verarbeitung: 0.1 Sekunden
(vorverarbeitet am 2026-11-04)
¤
*© Formatika GbR, Deutschland