From ec5548301e2549fc0f8d2f962aade24cb6f90d1b Mon Sep 17 00:00:00 2001 From: Adam Dickmeiss Date: Mon, 9 Jan 2006 13:43:59 +0000 Subject: [PATCH] RouterFleXML now reads XML simple config and make proper runtime routing. Program ex_router_flexml ../etc/config0.xml works as expected. The router now creates a state object, RoutePos, for each managed package. This object serves as a cursor/iterator for it. --- etc/config0.xml | 20 ++++ etc/config1.xml | 2 +- src/Makefile.am | 5 +- src/ex_filter_frontend_net.cpp | 5 +- src/ex_router_flexml.cpp | 90 ++++++++++++------ src/filter.hpp | 3 +- src/filter_frontend_net.cpp | 34 ++++++- src/filter_frontend_net.hpp | 3 +- src/filter_z3950_client.cpp | 3 +- src/package.cpp | 43 ++++++++- src/package.hpp | 14 ++- src/router.hpp | 23 ++++- src/router_chain.cpp | 51 +++++++++- src/router_chain.hpp | 8 +- src/router_flexml.cpp | 201 +++++++++++++++++++++++++++------------- src/router_flexml.hpp | 11 ++- src/test_filter2.cpp | 6 +- src/test_router_flexml.cpp | 10 +- src/xmlutil.cpp | 44 +++++++++ src/xmlutil.hpp | 32 +++++++ 20 files changed, 486 insertions(+), 122 deletions(-) create mode 100644 etc/config0.xml create mode 100644 src/xmlutil.cpp create mode 100644 src/xmlutil.hpp diff --git a/etc/config0.xml b/etc/config0.xml new file mode 100644 index 0000000..fc16f43 --- /dev/null +++ b/etc/config0.xml @@ -0,0 +1,20 @@ + + + + + + + @:9000 + + + + + + + + + + + + + diff --git a/etc/config1.xml b/etc/config1.xml index e828908..24c7f46 100644 --- a/etc/config1.xml +++ b/etc/config1.xml @@ -10,7 +10,7 @@ - 210 + @:210 out.log diff --git a/src/Makefile.am b/src/Makefile.am index 8e86495..bc0262b 100644 --- a/src/Makefile.am +++ b/src/Makefile.am @@ -1,4 +1,4 @@ -## $Id: Makefile.am,v 1.40 2006-01-04 14:30:51 adam Exp $ +## $Id: Makefile.am,v 1.41 2006-01-09 13:43:59 adam Exp $ MAINTAINERCLEANFILES = Makefile.in config.in config.hpp @@ -27,7 +27,8 @@ libyp2_la_SOURCES = \ filter_template.cpp filter_template.hpp \ factory_static.cpp factory_static.hpp \ pipe.cpp pipe.hpp \ - util.cpp util.hpp + util.cpp util.hpp \ + xmlutil.cpp xmlutil.hpp # Rules for programs.. diff --git a/src/ex_filter_frontend_net.cpp b/src/ex_filter_frontend_net.cpp index b77a063..44e12f2 100644 --- a/src/ex_filter_frontend_net.cpp +++ b/src/ex_filter_frontend_net.cpp @@ -1,9 +1,11 @@ -/* $Id: ex_filter_frontend_net.cpp,v 1.20 2006-01-04 11:19:04 adam Exp $ +/* $Id: ex_filter_frontend_net.cpp,v 1.21 2006-01-09 13:43:59 adam Exp $ Copyright (c) 2005, Index Data. %LICENSE% */ +#include "config.hpp" + #include #include #include @@ -11,7 +13,6 @@ #include namespace po = boost::program_options; -#include "config.hpp" #include "util.hpp" #include "filter_frontend_net.hpp" diff --git a/src/ex_router_flexml.cpp b/src/ex_router_flexml.cpp index 6fdb856..3793ea2 100644 --- a/src/ex_router_flexml.cpp +++ b/src/ex_router_flexml.cpp @@ -1,46 +1,82 @@ -/* $Id: ex_router_flexml.cpp,v 1.5 2006-01-04 14:30:51 adam Exp $ +/* $Id: ex_router_flexml.cpp,v 1.6 2006-01-09 13:43:59 adam Exp $ Copyright (c) 2005, Index Data. %LICENSE% */ +#include "config.hpp" + +#include +namespace po = boost::program_options; + #include #include -#include "config.hpp" #include "filter.hpp" +#include "package.hpp" #include "router_flexml.hpp" +#include "factory_static.hpp" int main(int argc, char **argv) { try { + + po::options_description desc("Allowed options"); + desc.add_options() + ("help", "produce help message") + ("config", po::value< std::vector >(), "xml config") + ; + + po::positional_options_description p; + p.add("config", -1); - std::string xmlconf = "\n" - "\n" - "\n" - "\n" - "\n" - "210\n" - "\n" - "\n" - "mylog.log\n" - "\n" - "\n" - "\n" - "\n" - "\n" - "\n" - "\n" - "\n" - "\n"; - - yp2::FactoryFilter factory; - yp2::RouterFleXML rflexml(xmlconf, factory); - - - - } + po::variables_map vm; + po::store(po::command_line_parser(argc, argv). + options(desc).positional(p).run(), vm); + po::notify(vm); + + if (vm.count("help")) { + std::cout << desc << "\n"; + return 1; + } + + xmlDocPtr doc = 0; + if (vm.count("config")) + { + std::vector config_fnames = + vm["config"].as< std::vector >(); + + if (config_fnames.size() != 1) + { + std::cerr << "Only one configuration must be given\n"; + std::exit(1); + } + + doc = xmlParseFile(config_fnames[0].c_str()); + if (!doc) + { + std::cerr << "xmlParseFile failed\n"; + std::exit(1); + } + } + else + { + std::cerr << "No configuration given\n"; + std::exit(1); + } + if (doc) + { + yp2::FactoryStatic factory; + yp2::RouterFleXML router(doc, factory); + + yp2::Package pack; + + pack.router(router).move(); + + xmlFreeDoc(doc); + } + } catch ( ... ) { std::cerr << "Unknown Exception" << std::endl; throw; diff --git a/src/filter.hpp b/src/filter.hpp index 5635eaf..b135553 100644 --- a/src/filter.hpp +++ b/src/filter.hpp @@ -1,4 +1,4 @@ -/* $Id: filter.hpp,v 1.11 2006-01-04 11:19:04 adam Exp $ +/* $Id: filter.hpp,v 1.12 2006-01-09 13:43:59 adam Exp $ Copyright (c) 2005, Index Data. %LICENSE% @@ -15,6 +15,7 @@ namespace yp2 { class Package; + namespace filter { class Base { public: diff --git a/src/filter_frontend_net.cpp b/src/filter_frontend_net.cpp index bf26441..38c6306 100644 --- a/src/filter_frontend_net.cpp +++ b/src/filter_frontend_net.cpp @@ -1,4 +1,4 @@ -/* $Id: filter_frontend_net.cpp,v 1.11 2006-01-04 11:55:31 adam Exp $ +/* $Id: filter_frontend_net.cpp,v 1.12 2006-01-09 13:43:59 adam Exp $ Copyright (c) 2005, Index Data. %LICENSE% @@ -7,6 +7,7 @@ #include "config.hpp" +#include "xmlutil.hpp" #include "pipe.hpp" #include "filter.hpp" #include "router.hpp" @@ -242,6 +243,9 @@ void yp2::My_Timer_Thread::socketNotify(int event) } void yp2::filter::FrontendNet::process(Package &package) const { + if (m_ports.size() == 0) + return; + yazpp_1::SocketManager mySocketManager; My_Timer_Thread *tt = 0; @@ -275,6 +279,34 @@ void yp2::filter::FrontendNet::process(Package &package) const { delete tt; } +void yp2::filter::FrontendNet::configure(const xmlNode * ptr) +{ + if (!ptr || !ptr->children) + { + throw yp2::filter::FilterException("No ports for Frontend"); + } + std::vector ports; + for (ptr = ptr->children; ptr; ptr = ptr->next) + { + if (ptr->type == XML_ELEMENT_NODE) + { + if (!strcmp((const char *) ptr->name, "port")) + { + std::string port = yp2::xml::get_text(ptr); + ports.push_back(port); + + } + else + { + throw yp2::filter::FilterException("Bad element " + + std::string((const char *) + ptr->name)); + } + } + } + m_ports = ports; +} + std::vector &yp2::filter::FrontendNet::ports() { return m_ports; diff --git a/src/filter_frontend_net.hpp b/src/filter_frontend_net.hpp index f90d69b..ff168ff 100644 --- a/src/filter_frontend_net.hpp +++ b/src/filter_frontend_net.hpp @@ -1,4 +1,4 @@ -/* $Id: filter_frontend_net.hpp,v 1.10 2006-01-04 11:55:31 adam Exp $ +/* $Id: filter_frontend_net.hpp,v 1.11 2006-01-09 13:43:59 adam Exp $ Copyright (c) 2005, Index Data. %LICENSE% @@ -19,6 +19,7 @@ namespace yp2 { public: FrontendNet::FrontendNet(); void process(yp2::Package & package) const; + void configure(const xmlNode * ptr); private: int m_no_threads; std::vector m_ports; diff --git a/src/filter_z3950_client.cpp b/src/filter_z3950_client.cpp index 178a3b8..cca4b8a 100644 --- a/src/filter_z3950_client.cpp +++ b/src/filter_z3950_client.cpp @@ -1,4 +1,4 @@ -/* $Id: filter_z3950_client.cpp,v 1.15 2006-01-04 11:55:32 adam Exp $ +/* $Id: filter_z3950_client.cpp,v 1.16 2006-01-09 13:43:59 adam Exp $ Copyright (c) 2005, Index Data. %LICENSE% @@ -113,7 +113,6 @@ void yf::Z3950Client::Assoc::failNotify() void yf::Z3950Client::Assoc::timeoutNotify() { - std::cout << "TIMEOUT NOTIFY\n"; m_ticks++; if (m_ticks == 30) { diff --git a/src/package.cpp b/src/package.cpp index a008e45..0802e29 100644 --- a/src/package.cpp +++ b/src/package.cpp @@ -1,4 +1,4 @@ -/* $Id: package.cpp,v 1.3 2006-01-05 16:39:06 adam Exp $ +/* $Id: package.cpp,v 1.4 2006-01-09 13:43:59 adam Exp $ Copyright (c) 2005, Index Data. %LICENSE% @@ -9,29 +9,60 @@ #include "package.hpp" yp2::Package::Package() - : m_filter(0), m_router(0), m_data(0) + : +#if ROUTE_POS + m_route_pos(0), +#else + m_filter(0), m_router(0), +#endif + m_data(0) { } +yp2::Package::~Package() +{ +#if ROUTE_POS + delete m_route_pos; +#endif +} + yp2::Package::Package(yp2::Session &session, yp2::Origin &origin) : m_session(session), m_origin(origin), - m_filter(0), m_router(0), m_data(0) +#if ROUTE_POS + m_route_pos(0), +#else + m_filter(0), m_router(0), +#endif + m_data(0) { } yp2::Package & yp2::Package::copy_filter(const Package &p) { +#if ROUTE_POS + m_route_pos = p.m_route_pos->clone(); +#else m_router = p.m_router; m_filter = p.m_filter; +#endif return *this; } void yp2::Package::move() { +#if ROUTE_POS + if (m_route_pos) + { + const filter::Base *next_filter = m_route_pos->move(); + if (next_filter) + next_filter->process(*this); + } +#else m_filter = m_router->move(m_filter, this); if (m_filter) m_filter->process(*this); +#endif } yp2::Session & yp2::Package::session() @@ -74,8 +105,12 @@ yp2::Package & yp2::Package::origin(const Origin & origin) yp2::Package & yp2::Package::router(const yp2::Router &router) { +#if ROUTE_POS + m_route_pos = router.createpos(); +#else m_filter = 0; m_router = &router; +#endif return *this; } @@ -87,7 +122,7 @@ yazpp_1::GDU &yp2::Package::request() yazpp_1::GDU &yp2::Package::response() { - return m_response_gdu; + return m_response_gdu; } yp2::Session yp2::Package::session() const diff --git a/src/package.hpp b/src/package.hpp index b104c85..d03b53b 100644 --- a/src/package.hpp +++ b/src/package.hpp @@ -1,4 +1,4 @@ -/* $Id: package.hpp,v 1.11 2006-01-04 11:19:04 adam Exp $ +/* $Id: package.hpp,v 1.12 2006-01-09 13:43:59 adam Exp $ Copyright (c) 2005, Index Data. %LICENSE% @@ -28,10 +28,12 @@ namespace yp2 { public: Origin() : type(API) {}; }; - + class Package { public: - Package() ; + Package(); + + ~Package(); Package(yp2::Session &session, yp2::Origin &origin); @@ -73,9 +75,13 @@ namespace yp2 { private: Session m_session; Origin m_origin; - + +#if ROUTE_POS + RoutePos *m_route_pos; +#else const filter::Base *m_filter; const Router *m_router; +#endif int m_data; yazpp_1::GDU m_request_gdu; diff --git a/src/router.hpp b/src/router.hpp index 31836ae..480fe1f 100644 --- a/src/router.hpp +++ b/src/router.hpp @@ -1,4 +1,4 @@ -/* $Id: router.hpp,v 1.7 2006-01-05 16:39:37 adam Exp $ +/* $Id: router.hpp,v 1.8 2006-01-09 13:43:59 adam Exp $ Copyright (c) 2005, Index Data. %LICENSE% @@ -11,12 +11,18 @@ #include #include +#define ROUTE_POS 1 + namespace yp2 { namespace filter { class Base; } +#if ROUTE_POS + class RoutePos; +#else class Package; +#endif class RouterException : public std::runtime_error { public: @@ -29,10 +35,25 @@ namespace yp2 Router(){}; virtual ~Router(){}; +#if ROUTE_POS + virtual RoutePos *createpos() const = 0; +#else /// determines next Filter to use from current Filter and Package virtual const filter::Base *move(const filter::Base *filter, const Package *package) const = 0; +#endif }; + + +#if ROUTE_POS + class RoutePos { + public: + virtual const filter::Base *move() = 0; + virtual RoutePos *clone() = 0; + virtual ~RoutePos() {}; + }; +#endif + } #endif /* diff --git a/src/router_chain.cpp b/src/router_chain.cpp index c9a85fd..cf49544 100644 --- a/src/router_chain.cpp +++ b/src/router_chain.cpp @@ -1,4 +1,4 @@ -/* $Id: router_chain.cpp,v 1.2 2005-11-10 23:10:42 adam Exp $ +/* $Id: router_chain.cpp,v 1.3 2006-01-09 13:43:59 adam Exp $ Copyright (c) 2005, Index Data. %LICENSE% @@ -10,10 +10,24 @@ namespace yp2 { + class ChainPos; + class RouterChain::Rep { friend class RouterChain; + friend class RouterChain::Pos; std::list m_filter_list; }; + +#if ROUTE_POS + class RouterChain::Pos : public RoutePos { + public: + virtual const filter::Base *move(); + virtual RoutePos *clone(); + virtual ~Pos(); + std::list::const_iterator it; + yp2::RouterChain::Rep *m_p; + }; +#endif }; yp2::RouterChain::RouterChain() : m_p(new yp2::RouterChain::Rep) @@ -24,7 +38,39 @@ yp2::RouterChain::~RouterChain() { } -const yp2::filter::Base * yp2::RouterChain::move(const filter::Base *filter, const Package *package) const { +#if ROUTE_POS +const yp2::filter::Base *yp2::RouterChain::Pos::move() +{ + if (it == m_p->m_filter_list.end()) + return 0; + const yp2::filter::Base *f = *it; + it++; + return f; +} + +yp2::RoutePos *yp2::RouterChain::createpos() const +{ + yp2::RouterChain::Pos *p = new yp2::RouterChain::Pos; + p->it = m_p->m_filter_list.begin(); + p->m_p = m_p.get(); + return p; +} + +yp2::RoutePos *yp2::RouterChain::Pos::clone() +{ + yp2::RouterChain::Pos *p = new yp2::RouterChain::Pos; + p->it = it; + p->m_p = m_p; + return p; +} + + +yp2::RouterChain::Pos::~Pos() +{ +} +#else +const yp2::filter::Base *yp2::RouterChain::move(const filter::Base *filter, + const Package *package) const { std::list::const_iterator it; it = m_p->m_filter_list.begin(); if (filter) @@ -43,6 +89,7 @@ const yp2::filter::Base * yp2::RouterChain::move(const filter::Base *filter, } return *it; } +#endif yp2::RouterChain & yp2::RouterChain::append(const filter::Base &filter) { diff --git a/src/router_chain.hpp b/src/router_chain.hpp index 033b277..a59afde 100644 --- a/src/router_chain.hpp +++ b/src/router_chain.hpp @@ -1,4 +1,4 @@ -/* $Id: router_chain.hpp,v 1.3 2005-11-10 23:10:42 adam Exp $ +/* $Id: router_chain.hpp,v 1.4 2006-01-09 13:43:59 adam Exp $ Copyright (c) 2005, Index Data. %LICENSE% @@ -16,12 +16,16 @@ namespace yp2 { class RouterChain : public Router { class Rep; + class Pos; public: RouterChain(); virtual ~RouterChain(); +#if ROUTE_POS + virtual RoutePos *createpos() const; +#else virtual const filter::Base *move(const filter::Base *filter, const Package *package) const; - +#endif RouterChain & append(const filter::Base &filter); private: boost::scoped_ptr m_p; diff --git a/src/router_flexml.cpp b/src/router_flexml.cpp index d4e24d7..09c24fa 100644 --- a/src/router_flexml.cpp +++ b/src/router_flexml.cpp @@ -1,10 +1,11 @@ -/* $Id: router_flexml.cpp,v 1.10 2006-01-05 16:39:37 adam Exp $ +/* $Id: router_flexml.cpp,v 1.11 2006-01-09 13:43:59 adam Exp $ Copyright (c) 2005, Index Data. %LICENSE% */ #include "config.hpp" +#include "xmlutil.hpp" #include "router_flexml.hpp" #include "factory_filter.hpp" #include "factory_static.hpp" @@ -23,12 +24,17 @@ namespace yp2 { class RouterFleXML::Route { friend class RouterFleXML::Rep; + friend class RouterFleXML::Pos; + friend class RouterFleXML; std::list > m_list; }; class RouterFleXML::Rep { friend class RouterFleXML; + friend class RouterFleXML::Pos; Rep(); + void base(xmlDocPtr doc, yp2::FactoryFilter &factory); + typedef std::map > IdFilterMap ; @@ -37,14 +43,16 @@ namespace yp2 { std::map m_routes; - void parse_xml_config_dom(xmlDocPtr doc); + std::string m_start_route; - bool is_element(const xmlNode *ptr, - const std::string &ns, - const std::string &name); - - bool is_element_yp2(const xmlNode *ptr, - const std::string &name); +#if ROUTE_POS +#else + std::map::iterator m_cur_route_it; + + std::list >::iterator m_cur_filter_it; +#endif + void parse_xml_config_dom(xmlDocPtr doc); bool check_element_yp2(const xmlNode *ptr, const std::string &name); @@ -61,6 +69,20 @@ namespace yp2 { private: FactoryFilter *m_factory; // TODO shared_ptr }; + +#if ROUTE_POS + class RouterFleXML::Pos : public RoutePos { + public: + virtual const filter::Base *move(); + virtual RoutePos *clone(); + virtual ~Pos(); + yp2::RouterFleXML::Rep *m_p; + + std::map::iterator m_route_it; + std::list >::iterator m_filter_it; + }; +#endif } const xmlNode* yp2::RouterFleXML::Rep::jump_to_children(const xmlNode* node, @@ -89,27 +111,10 @@ const xmlNode* yp2::RouterFleXML::Rep::jump_to(const xmlNode* node, return node; } -bool yp2::RouterFleXML::Rep::is_element(const xmlNode *ptr, - const std::string &ns, - const std::string &name) -{ - if (ptr && ptr->type == XML_ELEMENT_NODE && ptr->ns && ptr->ns->href - && !xmlStrcmp(BAD_CAST ns.c_str(), ptr->ns->href) - && !xmlStrcmp(BAD_CAST name.c_str(), ptr->name)) - return true; - return false; -} - -bool yp2::RouterFleXML::Rep::is_element_yp2(const xmlNode *ptr, - const std::string &name) -{ - return is_element(ptr, "http://indexdata.dk/yp2/config/1", name); -} - bool yp2::RouterFleXML::Rep::check_element_yp2(const xmlNode *ptr, const std::string &name) { - if (!is_element_yp2(ptr, name)) + if (!yp2::xml::is_element_yp2(ptr, name)) throw XMLError("Expected element name " + name); return true; } @@ -122,8 +127,6 @@ void yp2::RouterFleXML::Rep::parse_xml_filters(xmlDocPtr doc, while(node && check_element_yp2(node, "filter")) { filter_nr++; - std::cout << "processing /yp2/filters/filter[" - << filter_nr << "]" << std::endl; const struct _xmlAttr *attr; std::string id_value; @@ -143,8 +146,6 @@ void yp2::RouterFleXML::Rep::parse_xml_filters(xmlDocPtr doc, else throw XMLError("Only attribute id or type allowed" " in filter element. Got " + name); - - std::cout << "attr " << name << "=" << value << "\n"; } yp2::filter::Base* filter_base = m_factory->create(type_value); @@ -167,7 +168,7 @@ void yp2::RouterFleXML::Rep::parse_xml_routes(xmlDocPtr doc, check_element_yp2(node, "route"); unsigned int route_nr = 0; - while(is_element_yp2(node, "route")) + while(yp2::xml::is_element_yp2(node, "route")) { route_nr++; @@ -184,18 +185,14 @@ void yp2::RouterFleXML::Rep::parse_xml_routes(xmlDocPtr doc, if (name == "id") id_value = value; else - throw XMLError("Only attribute refid allowed route element. Got " + name); - - std::cout << "attr " << name << "=" << value << "\n"; + throw XMLError("Only attribute 'id' allowed for element" + "'route'." + " Got " + name); } Route route; - std::cout << "processing /yp2/routes/route[" - << route_nr << "]" << std::endl; - // process nodes in third level - const xmlNode* node3 = jump_to_children(node, XML_ELEMENT_NODE); unsigned int filter3_nr = 0; @@ -219,10 +216,9 @@ void yp2::RouterFleXML::Rep::parse_xml_routes(xmlDocPtr doc, else if (name == "type") type_value = value; else - throw XMLError("Only attribute refid or type" - " allowed in filter element. Got " + name); - - std::cout << "attr " << name << "=" << value << "\n"; + throw XMLError("Only attribute 'refid' or 'type'" + " allowed for element 'filter'." + " Got " + name); } if (refid_value.length()) { @@ -243,10 +239,6 @@ void yp2::RouterFleXML::Rep::parse_xml_routes(xmlDocPtr doc, route.m_list.push_back( boost::shared_ptr(filter_base)); } - std::cout << "processing /yp2/routes/route[" - << route_nr << "]/filter[" - << filter3_nr << "]" << std::endl; - node3 = jump_to_next(node3, XML_ELEMENT_NODE); } @@ -269,28 +261,36 @@ void yp2::RouterFleXML::Rep::parse_xml_config_dom(xmlDocPtr doc) check_element_yp2(root, "yp2"); - std::cout << "processing /yp2" << std::endl; - // process node which is expected first element node const xmlNode* node = jump_to_children(root, XML_ELEMENT_NODE); - //for (; node && node->type != XML_ELEMENT_NODE; node = node->next) - // ; + if (check_element_yp2(node, "start")) + { + const struct _xmlAttr *attr; + std::string id_value; + for (attr = node->properties; attr; attr = attr->next) + { + std::string name = std::string((const char *) attr->name); + std::string value; - check_element_yp2(node, "start"); + if (attr->children && attr->children->type == XML_TEXT_NODE) + value = std::string((const char *)attr->children->content); - std::cout << "processing /yp2/start" << std::endl; - + if (name == "route") + m_start_route = value; + else + throw XMLError("Only attribute start allowed" + " in element 'start'. Got " + name); + } + node = jump_to_next(node, XML_ELEMENT_NODE); + } // process node which is expected second element node - node = jump_to_next(node, XML_ELEMENT_NODE); check_element_yp2(node, "filters"); - std::cout << "processing /yp2/filters" << std::endl; parse_xml_filters(doc, jump_to_children(node, XML_ELEMENT_NODE)); // process node which is expected third element node node = jump_to_next(node, XML_ELEMENT_NODE); check_element_yp2(node, "routes"); - std::cout << "processing /yp2/routes" << std::endl; parse_xml_routes(doc, jump_to_children(node, XML_ELEMENT_NODE)); } @@ -299,12 +299,22 @@ yp2::RouterFleXML::Rep::Rep() : m_xinclude(false) { } +void yp2::RouterFleXML::Rep::base(xmlDocPtr doc, yp2::FactoryFilter &factory) +{ + m_factory = &factory; + parse_xml_config_dom(doc); + m_start_route = "start"; +} + +yp2::RouterFleXML::RouterFleXML(xmlDocPtr doc, yp2::FactoryFilter &factory) + : m_p(new Rep) +{ + m_p->base(doc, factory); +} + yp2::RouterFleXML::RouterFleXML(std::string xmlconf, yp2::FactoryFilter &factory) : m_p(new Rep) { - - m_p->m_factory = &factory; - LIBXML_TEST_VERSION; xmlDocPtr doc = xmlParseMemory(xmlconf.c_str(), @@ -313,7 +323,7 @@ yp2::RouterFleXML::RouterFleXML(std::string xmlconf, yp2::FactoryFilter &factory throw XMLError("xmlParseMemory failed"); else { - m_p->parse_xml_config_dom(doc); + m_p->base(doc, factory); xmlFreeDoc(doc); } } @@ -322,13 +332,80 @@ yp2::RouterFleXML::~RouterFleXML() { } +#if ROUTE_POS +const yp2::filter::Base *yp2::RouterFleXML::Pos::move() +{ + if (m_filter_it == m_route_it->second.m_list.end()) + return 0; + const yp2::filter::Base *f = (*m_filter_it).get(); + m_filter_it++; + return f; +} + +yp2::RoutePos *yp2::RouterFleXML::createpos() const +{ + yp2::RouterFleXML::Pos *p = new yp2::RouterFleXML::Pos; + + p->m_route_it = m_p->m_routes.find(m_p->m_start_route); + if (p->m_route_it == m_p->m_routes.end()) + { + delete p; + return 0; + } + p->m_filter_it = p->m_route_it->second.m_list.begin(); + p->m_p = m_p.get(); + return p; +} + +yp2::RoutePos *yp2::RouterFleXML::Pos::clone() +{ + yp2::RouterFleXML::Pos *p = new yp2::RouterFleXML::Pos; + p->m_filter_it = m_filter_it; + p->m_route_it = m_route_it; + p->m_p = m_p; + return p; +} + +yp2::RouterFleXML::Pos::~Pos() +{ +} + +#else const yp2::filter::Base * yp2::RouterFleXML::move(const yp2::filter::Base *filter, const yp2::Package *package) const { - return 0; + if (!filter) + { // Initial move. find start route + m_p->m_cur_route_it = m_p->m_routes.find("start"); + if (m_p->m_cur_route_it == m_p->m_routes.end()) + return 0; + m_p->m_cur_filter_it = m_p->m_cur_route_it->second.m_list.begin(); + } + else + { + const yp2::filter::Base *f = (*m_p->m_cur_filter_it).get(); + if (f != filter) + (m_p->m_cur_filter_it)++; + else + { + // TOTO: should search all routes (not only start)! + m_p->m_cur_filter_it = m_p->m_cur_route_it->second.m_list.begin(); + while (m_p->m_cur_filter_it != + m_p->m_cur_route_it->second.m_list.end()) + { + const yp2::filter::Base *f = (*m_p->m_cur_filter_it).get(); + (m_p->m_cur_filter_it)++; + if (filter == f) + break; + } + } + } + if (m_p->m_cur_filter_it == m_p->m_cur_route_it->second.m_list.end()) + return 0; + return (*m_p->m_cur_filter_it).get(); } - +#endif /* * Local variables: diff --git a/src/router_flexml.hpp b/src/router_flexml.hpp index be7b66d..d040664 100644 --- a/src/router_flexml.hpp +++ b/src/router_flexml.hpp @@ -1,4 +1,4 @@ -/* $Id: router_flexml.hpp,v 1.10 2006-01-05 16:39:37 adam Exp $ +/* $Id: router_flexml.hpp,v 1.11 2006-01-09 13:43:59 adam Exp $ Copyright (c) 2005, Index Data. %LICENSE% @@ -18,13 +18,20 @@ namespace yp2 { class Rep; class Route; + class Pos; public: RouterFleXML(std::string xmlconf, yp2::FactoryFilter &factory); + RouterFleXML(xmlDocPtr doc, yp2::FactoryFilter &factory); ~RouterFleXML(); - + +#if ROUTE_POS + virtual RoutePos *createpos() const; +#else + /// determines next Filter to use from current Filter and Package virtual const filter::Base *move(const filter::Base *filter, const Package *package) const; +#endif class XMLError : public std::runtime_error { public: XMLError(const std::string msg) : diff --git a/src/test_filter2.cpp b/src/test_filter2.cpp index fb34da0..12d6ef5 100644 --- a/src/test_filter2.cpp +++ b/src/test_filter2.cpp @@ -1,4 +1,4 @@ -/* $Id: test_filter2.cpp,v 1.16 2005-12-02 12:21:07 adam Exp $ +/* $Id: test_filter2.cpp,v 1.17 2006-01-09 13:43:59 adam Exp $ Copyright (c) 2005, Index Data. %LICENSE% @@ -138,7 +138,7 @@ BOOST_AUTO_UNIT_TEST( testfilter2_1 ) pack.router(router1).move(); - BOOST_CHECK (pack.data() == 2468); + BOOST_CHECK_EQUAL(pack.data(), 2468); } @@ -154,7 +154,7 @@ BOOST_AUTO_UNIT_TEST( testfilter2_1 ) pack.router(router2).move(); - BOOST_CHECK (pack.data() == 1234); + BOOST_CHECK_EQUAL(pack.data(), 1234); } diff --git a/src/test_router_flexml.cpp b/src/test_router_flexml.cpp index 5bed848..1a30019 100644 --- a/src/test_router_flexml.cpp +++ b/src/test_router_flexml.cpp @@ -1,4 +1,4 @@ -/* $Id: test_router_flexml.cpp,v 1.12 2006-01-05 16:39:37 adam Exp $ +/* $Id: test_router_flexml.cpp,v 1.13 2006-01-09 13:43:59 adam Exp $ Copyright (c) 2005, Index Data. %LICENSE% @@ -40,7 +40,7 @@ BOOST_AUTO_UNIT_TEST( test_router_flexml_1 ) " \n" " \n" " \n" - " 210\n" + " @:210\n" " \n" " \n" " mylog1.log\n" @@ -90,7 +90,7 @@ BOOST_AUTO_UNIT_TEST( test_router_flexml_2 ) " \n" " \n" " \n" - " 210\n"; + " @:210\n"; yp2::FactoryFilter factory; yp2::RouterFleXML rflexml(xmlconf_invalid, factory); @@ -118,7 +118,7 @@ BOOST_AUTO_UNIT_TEST( test_router_flexml_3 ) " \n" " \n" " \n" - " 210\n" + " @:210\n" " \n" " \n" " mylog.log\n" @@ -155,7 +155,7 @@ BOOST_AUTO_UNIT_TEST( test_router_flexml_4 ) " \n" " \n" " \n" - " 210\n" + " @:210\n" " \n" " \n" " \n" diff --git a/src/xmlutil.cpp b/src/xmlutil.cpp new file mode 100644 index 0000000..c2aef1a --- /dev/null +++ b/src/xmlutil.cpp @@ -0,0 +1,44 @@ +/* $Id: xmlutil.cpp,v 1.1 2006-01-09 13:43:59 adam Exp $ + Copyright (c) 2005, Index Data. + +%LICENSE% + */ + +#include "xmlutil.hpp" + +std::string yp2::xml::get_text(const xmlNode *ptr) +{ + std::string c; + for (ptr = ptr->children; ptr; ptr = ptr->next) + if (ptr->type == XML_TEXT_NODE) + c += std::string((const char *) (ptr->content)); + return c; +} + + +bool yp2::xml::is_element(const xmlNode *ptr, + const std::string &ns, + const std::string &name) +{ + if (ptr && ptr->type == XML_ELEMENT_NODE && ptr->ns && ptr->ns->href + && !xmlStrcmp(BAD_CAST ns.c_str(), ptr->ns->href) + && !xmlStrcmp(BAD_CAST name.c_str(), ptr->name)) + return true; + return false; +} + +bool yp2::xml::is_element_yp2(const xmlNode *ptr, + const std::string &name) +{ + return yp2::xml::is_element(ptr, "http://indexdata.dk/yp2/config/1", name); +} + + +/* + * Local variables: + * c-basic-offset: 4 + * indent-tabs-mode: nil + * c-file-style: "stroustrup" + * End: + * vim: shiftwidth=4 tabstop=8 expandtab + */ diff --git a/src/xmlutil.hpp b/src/xmlutil.hpp new file mode 100644 index 0000000..ac0409c --- /dev/null +++ b/src/xmlutil.hpp @@ -0,0 +1,32 @@ +/* $Id: xmlutil.hpp,v 1.1 2006-01-09 13:43:59 adam Exp $ + Copyright (c) 2005, Index Data. + +%LICENSE% + */ + +#ifndef XML_UTIL_HPP +#define XML_UTIL_HPP + +#include +#include +#include + +namespace yp2 { + namespace xml { + std::string get_text(const xmlNode *ptr); + bool is_element(const xmlNode *ptr, + const std::string &ns, + const std::string &name); + bool is_element_yp2(const xmlNode *ptr, const std::string &name); + } +} + +#endif +/* + * Local variables: + * c-basic-offset: 4 + * indent-tabs-mode: nil + * c-file-style: "stroustrup" + * End: + * vim: shiftwidth=4 tabstop=8 expandtab + */ -- 1.7.10.4