hce-node application  1.4.3
HCE Hierarchical Cluster Engine node application
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros
ASMXMLParser.hpp
Go to the documentation of this file.
1 
17 #ifndef HCEXML_PARSER_HPP
18 #define HCEXML_PARSER_HPP
19 
20 #include <Poco/JSON/Object.h>
21 #include <Poco/SAX/SAXParser.h>
22 #include <Poco/SAX/ContentHandler.h>
23 #include <Poco/SAX/LexicalHandler.h>
24 #include <Poco/SAX/Attributes.h>
25 #include <Poco/SAX/Locator.h>
26 #include <Poco/Exception.h>
27 #include <iostream>
28 #include <stack>
29 
31 
32 using Poco::XML::SAXParser;
33 using Poco::XML::XMLReader;
34 using Poco::XML::XMLString;
35 using Poco::XML::XMLChar;
36 using Poco::XML::ContentHandler;
37 using Poco::XML::LexicalHandler;
38 using Poco::XML::Attributes;
39 using Poco::XML::Locator;
40 
41 using namespace HCE::exception;
42 
43 namespace HCE
44 {
45  namespace utils
46  {
47  class HCEXMLParser: public ContentHandler, public LexicalHandler
48  {
49  protected:
50  std::stack<Poco::JSON::Object::Ptr> objStack;
51  std::stack<XMLString> attrNamesStack;
52  std::string tagVal;
53  Poco::JSON::Object::Ptr rootObject;
54  std::vector<XMLString> attrTagNames;
55  public:
56  HCEXMLParser():_pLocator(0)
57  {
58  tagVal = "";
59  rootObject = NULL;
60  }
61 
62  void addAttrTag(std::string tagName)
63  {
64  attrTagNames.push_back(tagName);
65  }
66 
67  // ContentHandler
68  void setDocumentLocator(const Locator* loc)
69  {
70  _pLocator = loc;
71  }
72 
73  void startDocument()
74  {
75  }
76 
77  void endDocument()
78  {
79  }
80 
81  void startElement(const XMLString& uri, const XMLString& localName, const XMLString& qname, const Attributes& attributes)
82  {
83  objStack.push(new Poco::JSON::Object());
84  attrNamesStack.push(localName);
85  tagVal = "";
86  if(attributes.getLength() > 0)
87  {
88  for(unsigned int i = 0; i < attrTagNames.size(); i++)
89  {
90  if(!attributes.getValue(attrTagNames[i]).empty())
91  {
92  attrNamesStack.top() = attributes.getValue(attrTagNames[i]);
93  break;
94  }
95  }
96  bool isFind = false;
97  Poco::JSON::Object::Ptr localObjPtr = Poco::JSON::Object::Ptr(new Poco::JSON::Object());
98  Poco::JSON::Object::Ptr localObjPtrParent = objStack.top();
99  for(unsigned int i = 0; i < static_cast<unsigned int>(attributes.getLength()) ; i++)
100  {
101  isFind = false;
102  for(unsigned int j = 0; j < attrTagNames.size(); j++)
103  {
104  if(attributes.getLocalName(i).compare(attrTagNames[j]) == 0)
105  {
106  isFind = true;
107  break;
108  }
109  }
110  if(!isFind)
111  {
112  tagVal = attributes.getValue(i);
113  insertAtEndElement(attributes.getLocalName(i), localObjPtr, localObjPtrParent);
114  }
115  }
116  tagVal = "";
117  }
118  }
119 
120  void insertAtEndElement(const XMLString& localName, Poco::JSON::Object::Ptr localObjPtr, Poco::JSON::Object::Ptr localObjPtrParent)
121  {
122  const XMLString &tagAttrName = ((attrNamesStack.empty() || attrNamesStack.top().empty()) ? localName : attrNamesStack.top());
123  if(tagAttrName.empty())
124  {
125  throw XMLEmptyNameException("Empty Tag Name");
126  }
127  else if(tagAttrName != localName)
128  {
129  throw XMLEmptyNameException("Wrong Close Tag Name");
130  }
131  Poco::Dynamic::Var localVar;
132  if(localObjPtr->size() > 0)
133  {
134  localVar = localObjPtr;
135  }
136  else
137  {
138  localVar = tagVal;
139  }
140  if(!localObjPtrParent->has(tagAttrName))
141  {
142  localObjPtrParent->set(tagAttrName, localVar);
143  }
144  else if(localObjPtrParent->isArray(tagAttrName))
145  {
146  Poco::JSON::Array::Ptr localArray = localObjPtrParent->getArray(tagAttrName);
147  if(!localArray.isNull())
148  {
149  localArray->add(localVar);
150  }
151  }
152  else
153  {
154  Poco::JSON::Array::Ptr localArray = Poco::JSON::Array::Ptr(new Poco::JSON::Array());
155  localArray->add(localObjPtrParent->get(tagAttrName));
156  localArray->add(localVar);
157  localObjPtrParent->remove(tagAttrName);
158  localObjPtrParent->set(tagAttrName, localArray);
159  }
160  }
161 
162  void endElement(const XMLString& uri, const XMLString& localName, const XMLString& qname)
163  {
164  Poco::JSON::Object::Ptr localObjPtr;
165  if(!objStack.empty())
166  {
167  localObjPtr = objStack.top();
168  objStack.pop();
169  if(objStack.size() > 0)
170  {
171  Poco::JSON::Object::Ptr localObjPtrParent = objStack.top();
172  if(!localObjPtr.isNull() && !localObjPtrParent.isNull())
173  {
174  insertAtEndElement(localName, localObjPtr, localObjPtrParent);
175  }
176  }
177  else
178  {
179  rootObject = localObjPtr;
180  }
181  attrNamesStack.pop();
182  tagVal = "";
183  }
184  }
185 
186  void characters(const XMLChar ch[], int start, int length)
187  {
188  tagVal.append(ch + start, length);
189  }
190 
191  void ignorableWhitespace(const XMLChar ch[], int start, int length)
192  {
193  }
194 
195  void processingInstruction(const XMLString& target, const XMLString& data)
196  {
197  }
198 
199  void startPrefixMapping(const XMLString& prefix, const XMLString& uri)
200  {
201  }
202 
203  void endPrefixMapping(const XMLString& prefix)
204  {
205  }
206 
207  void skippedEntity(const XMLString& name)
208  {
209  }
210 
211  // LexicalHandler
212  void startDTD(const XMLString& name, const XMLString& publicId, const XMLString& systemId)
213  {
214  }
215 
216  void endDTD()
217  {
218  }
219 
220  void startEntity(const XMLString& name)
221  {
222  }
223 
224  void endEntity(const XMLString& name)
225  {
226  }
227 
228  void startCDATA()
229  {
230  }
231 
232  void endCDATA()
233  {
234  }
235 
236  void comment(const XMLChar ch[], int start, int length)
237  {
238  }
239 
240  Poco::JSON::Object::Ptr getObject()
241  {
242  return rootObject;
243  }
244 
245  private:
246  const Locator* _pLocator;
247  };
248  }
249 }
250 
251 #endif