Logo  0.95.0-final
Finite Element Embedded Library and Language in C++
Feel++ Feel++ on Github Feel++ community
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Groups Pages
xmlparser.hpp
1 /* -*- mode: c++; coding: utf-8; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4; show-trailing-whitespace: t -*- vim:fenc=utf-8:ft=tcl:et:sw=4:ts=4:sts=4
2 
3 
4  This file is part of the Feel library
5 
6  Author(s):
7  Florent Vielfaure <florent.vielfaure@gmail.com>
8 
9  Date: 2009-02-22
10 
11  Copyright (C) 2009 Université de Grenoble 1
12 
13  This library is free software; you can redistribute it and/or
14  modify it under the terms of the GNU Lesser General Public
15  License as published by the Free Software Foundation; either
16  version 3.0 of the License, or (at your option) any later version.
17 
18  This library is distributed in the hope that it will be useful,
19  but WITHOUT ANY WARRANTY; without even the implied warranty of
20  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
21  Lesser General Public License for more details.
22 
23  You should have received a copy of the GNU Lesser General Public
24  License along with this library; if not, write to the Free Software
25  Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
26 */
32 #if !defined(XML_PARSER_H)
33 #define XML_PARSER_H 1
34 
35 #include <vector>
36 #include <cstdio>
37 #include <iostream>
38 #include <string>
39 #include <cstring>
40 #include <sstream>
41 
42 #include <libxml/parser.h>
43 #include <libxml/tree.h>
44 #include <libxml/encoding.h>
45 #include <libxml/xmlwriter.h>
46 
47 #include <boost/parameter.hpp>
48 #include <feel/feelcore/parameter.hpp>
49 
50 #define MY_ENCODING "UTF-8"
51 
52 #define OUT_ATTR 0
53 #define DISC_ATTR 1
54 #define CONT_ATTR 2
55 
56 namespace Feel
57 {
58 
59 class Parameter_impl
60 {
61 private:
62  std::string* name;
63  int type;
64  std::string* cmdName;
65  std::string* latex;
66  std::string* values;
67 
68 public:
69  Parameter_impl() {}
70  template <class ArgumentPack>
71  Parameter_impl( ArgumentPack const& args )
72  {
73  name = new std::string( ( const char* )args[_name] );
74  type = ( int )args[_type];
75  cmdName = ( args[_cmdName | 0] ?
76  new std::string( ( const char* )args[_cmdName | ( const char* )0] ) :
77  new std::string( *name ) );
78  latex = ( args[_latex | 0] ? new std::string( ( const char* )args[_latex | ( const char* )0] ) : ( std::string* )0 );
79  values = ( args[_values | 0] ? new std::string( ( const char* )args[_values | ( const char* )0] ) : ( std::string* )0 );
80  }
85  inline std::vector<std::string> getAttrNames()
86  {
87  std::vector<std::string> attrNames;
88  attrNames.push_back( "name" );
89 
90  if ( type )
91  attrNames.push_back( "type" );
92 
93  if ( cmdName )
94  attrNames.push_back( "cmd_name" );
95 
96  if ( latex )
97  attrNames.push_back( "latex" );
98 
99  return attrNames;
100  }
107  inline std::vector<std::string> getAttrValues()
108  {
109  std::vector<std::string> attrValues;
110  attrValues.push_back( *name );
111 
112  if ( type )
113  attrValues.push_back( ( type == 1 ? "discrete" : "continuous" ) );
114 
115  if ( cmdName )
116  attrValues.push_back( *cmdName );
117 
118  if ( latex )
119  attrValues.push_back( *latex );
120 
121  return attrValues;
122  }
126  inline std::string getValues()
127  {
128  return *values;
129  }
133  inline std::string getName()
134  {
135  return *name;
136  }
137 };
138 
143 class Parameter : public Parameter_impl
144 {
145 public:
146  Parameter() {}
147  BOOST_PARAMETER_CONSTRUCTOR(
148  Parameter, ( Parameter_impl ), tag
149  , ( required ( name,* ) ) ( required ( type,* ) ) ( optional ( cmdName,* ) ) ( optional ( latex,* ) ) ( optional ( values,* ) ) )
150 };
151 
152 class Output_impl : public Parameter
153 {
154 private:
155  std::vector<Parameter> dependencies;
156  std::vector<std::string> funcs;
157 
158 public:
159  template <class ArgumentPack>
160  Output_impl( ArgumentPack const& args )
161  :
162  Parameter( _name=args[_name],
163  _type=0,
164  _latex=args[_latex ] )
165  {
166  dependencies=args[_dependencies | std::vector<Parameter>() ];
167  funcs=args[_funcs | std::vector<std::string>() ];
168  }
172  inline std::vector<Parameter> getDependencies()
173  {
174  return dependencies;
175  }
179  inline std::vector<std::string> getFuncs()
180  {
181  return funcs;
182  }
183 };
184 
189 class Output : public Output_impl
190 {
191 public:
192  BOOST_PARAMETER_CONSTRUCTOR(
193  Output,
194  ( Output_impl ),
195  tag,
196  ( required ( name,* ) )
197  ( optional ( latex,* ) )
198  ( optional ( dependencies,* ) )
199  ( optional ( funcs,* ) )
200  )
201 };
202 
203 class xmlParser
204 {
205 public:
211  static void writeResponse( std::string filename,std::string name,std::vector<Parameter> params,std::vector<Output> Outputs )
212  {
213  xmlDocPtr doc = xmlNewDoc( ( xmlChar* ) "1.0" );
214  xmlNodePtr rootNode = xmlNewNode( 0, ( xmlChar* ) "response" );
215  xmlDocSetRootElement( doc, rootNode );
216  xmlNodePtr progNode = createNode( "program_name",name );
217  xmlAddChild( rootNode,progNode );
218 
219  for ( unsigned int i=0; i<params.size(); ++i )
220  {
221  xmlNodePtr paramNode = createNode( "param",params[i].getAttrNames(),params[i].getAttrValues(),params[i].getValues() );
222  xmlAddChild( rootNode,paramNode );
223  }
224 
225  for ( unsigned int i=0; i<Outputs.size(); ++i )
226  {
227  xmlNodePtr paramNode = createNode( "output",Outputs[i].getAttrNames(),Outputs[i].getAttrValues() );
228 
229  for ( unsigned int j=0; j<Outputs[i].getDependencies().size(); ++j )
230  {
231  xmlNode* aNewNode = xmlNewNode( 0,( xmlChar* ) "depend" );
232  xmlSetProp( aNewNode, ( xmlChar* ) "value", ( xmlChar* ) Outputs[i].getDependencies()[j].getName().c_str() );
233  xmlNodeSetContent( aNewNode,( xmlChar* ) Outputs[i].getFuncs()[j].c_str() );
234  xmlAddChild( paramNode,aNewNode );
235  }
236 
237  xmlAddChild( rootNode,paramNode );
238  }
239 
240  xmlSaveFileEnc( filename.c_str(), doc, MY_ENCODING );
241 
242  xmlFreeDoc( doc );
243  }
244 
251  static void writeResult( std::string filename,
252  std::string name,
253  std::vector<Parameter> params,
254  std::vector<Output> Outputs,
255  std::vector<std::string> paramValues,
256  std::vector<std::string> OutputValues )
257  {
258  xmlDoc *doc = 0;
259  xmlNode *root_element = 0;
260 
261  doc = xmlReadFile( filename.c_str(), 0, 0 );
262 
263  if ( doc == 0 )
264  {
265  doc = xmlNewDoc( ( xmlChar* ) "1.0" );
266  root_element = xmlNewNode( 0, ( xmlChar* ) "result" );
267  xmlDocSetRootElement( doc, root_element );
268  printf( "[xmlParser] warning : the file %s has been generated\n", filename.c_str() );
269  }
270 
271  root_element = xmlDocGetRootElement( doc );
272 
273  if ( root_element == 0 )
274  {
275  printf( "[xmlParser] error : the file %s is empty\n", filename.c_str() );
276  return;
277  }
278 
279  xmlNode* aNode=findNode( root_element,"program", name.c_str() );
280  xmlNode* aNewNode;
281 
282  for ( unsigned int i=0; i<params.size(); ++i )
283  {
284  aNewNode=findNode( aNode, params[i].getName(), paramValues[i] );
285  aNode=aNewNode;
286  }
287 
288  for ( unsigned int i=0; i<Outputs.size(); ++i )
289  {
290  xmlNode *cur_node=0;
291 
292  for ( cur_node = aNode->children; cur_node; cur_node = cur_node->next )
293  {
294  if ( ( cur_node->type == XML_ELEMENT_NODE ) &&
295  ( std::strcmp( ( char* )cur_node->name,Outputs[i].getName().c_str() )==0 ) )
296  {
297  xmlUnlinkNode( cur_node );
298  xmlFreeNode( cur_node );
299  }
300  }
301 
302  aNewNode=createNode( Outputs[i].getName(), OutputValues[i] );
303  xmlAddChild( aNode,aNewNode );
304  }
305 
306  xmlSaveFileEnc( filename.c_str(), doc, MY_ENCODING );
307  }
308 private:
309  static xmlNode* findNode( xmlNode* aNode, std::string nodeName, std::string attrVal )
310  {
311  xmlNode *cur_node = 0;
312 
313  for ( cur_node = aNode->children; cur_node; cur_node = cur_node->next )
314  {
315  if ( ( cur_node->type == XML_ELEMENT_NODE ) &&
316  ( std::strcmp( ( char* )cur_node->name,nodeName.c_str() )==0 ) )
317  {
318  xmlChar* val=xmlGetProp( cur_node,( xmlChar* ) "value" );
319 
320  if ( ( val!=0 ) && ( std::strcmp( ( char* )val,attrVal.c_str() )==0 ) )
321  {
322  return cur_node;
323  }
324  }
325  }
326 
327  xmlNode* aNewNode = xmlNewNode( 0,( xmlChar* ) nodeName.c_str() );
328  xmlSetProp( aNewNode, ( xmlChar* ) "value", ( xmlChar* ) attrVal.c_str() );
329  xmlAddChild( aNode,aNewNode );
330  return aNewNode;
331  }
332 
333  static xmlNode* createNode( std::string nodeName, std::vector<std::string> attrNames, std::vector<std::string> attrValues, std::string value="" )
334  {
335  if ( attrNames.size()!=attrValues.size() )
336  {
337  printf( "[xmlParser] error : attributes names list size != attributes values list size\n" );
338  return 0;
339  }
340 
341  xmlNode* aNewNode = xmlNewNode( 0,( xmlChar* ) nodeName.c_str() );
342 
343  for ( unsigned int i=0; i<attrNames.size(); ++i )
344  xmlSetProp( aNewNode, ( xmlChar* ) attrNames[i].c_str(), ( xmlChar* ) attrValues[i].c_str() );
345 
346  if ( std::strcmp( value.c_str(),"" )!=0 )
347  xmlNodeSetContent( aNewNode,( xmlChar* ) value.c_str() );
348 
349  return aNewNode;
350  }
351 
352  static xmlNode* createNode( std::string nodeName, std::string value="" )
353  {
354  xmlNode* aNewNode = xmlNewNode( 0,( xmlChar* ) nodeName.c_str() );
355 
356  if ( std::strcmp( value.c_str(),"" )!=0 )
357  xmlNodeSetContent( aNewNode,( xmlChar* ) value.c_str() );
358 
359  return aNewNode;
360  }
361 };
362 }
363 
364 #endif /* XML_PARSER_H */

Generated on Sun Oct 20 2013 08:25:06 for Feel++ by doxygen 1.8.4