00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021 #ifndef XMLSOMReader_H
00022 #define XMLSOMReader_H
00023
00024 #include <libxml/xmlreader.h>
00025
00026 #include <stdlib.h>
00027 #include <string>
00028 #include <stdexcept>
00029 #include <map>
00030
00031 using std::exception;
00032
00033 namespace xmlsom {
00034
00035
00036 class XMLSOMReader {
00037
00038 public:
00039
00040 XMLSOMReader(std::string filename) throw(std::exception);
00041
00042 ~XMLSOMReader() {};
00043
00044 protected:
00045
00046 void doParse() throw(std::exception);
00047
00048 virtual void processElement( const std::string& name,
00049 const std::string& value,
00050 const std::map<std::string,std::string>& attrs )
00051 throw(exception) = 0;
00052
00053 virtual void processEndElement(const std::string& name) {};
00054
00055 private:
00056
00057 void prepareNode();
00058
00059 void prepareAttrs();
00060
00061 xmlTextReaderPtr reader;
00062
00063 std::string filename;
00064
00065 std::map<std::string,std::string> atribs;
00066
00067 const xmlChar* name;
00068
00069 const xmlChar* value;
00070
00071 std::string sname;
00072
00073 std::string svalue;
00074
00075 bool handleEmptyElement;
00076 };
00077
00078
00079
00080
00081 XMLSOMReader::XMLSOMReader(std::string fileName) throw(std::exception)
00082 : filename(fileName) {
00083
00084 reader = xmlNewTextReaderFilename(filename.data());
00085
00086 if (reader == NULL)
00087 throw std::invalid_argument("Invalid filename path");
00088
00089 handleEmptyElement = false;
00090
00091 };
00092
00093
00094
00095
00096
00097 void XMLSOMReader::doParse() throw (std::exception) {
00098
00099 int ret = xmlTextReaderRead(reader);
00100
00101
00102 while (ret == 1) {
00103
00104 prepareNode();
00105
00106
00107 ret = xmlTextReaderRead(reader);
00108 }
00109
00110 xmlFreeTextReader(reader);
00111
00112 if (ret != 0)
00113 throw std::invalid_argument("failed to parse " + filename);
00114 };
00115
00116
00117
00118
00119 void XMLSOMReader::prepareNode() {
00120
00121
00122 int nodeType = xmlTextReaderNodeType(reader);
00123
00124 switch(nodeType) {
00125
00126 case XML_READER_TYPE_ELEMENT: {
00127
00128 if (handleEmptyElement) {
00129 processElement(sname, "", atribs);
00130 handleEmptyElement = false;
00131 }
00132
00133 name = xmlTextReaderConstName(reader);
00134
00135 sname = std::string( (char*) name);
00136
00137
00138 prepareAttrs();
00139
00140 handleEmptyElement = true;
00141
00142 break;
00143 }
00144
00145
00146 case XML_READER_TYPE_TEXT: {
00147
00148 value = xmlTextReaderConstValue(reader);
00149
00150 if (value != NULL) {
00151 svalue = std::string( (char*) value );
00152 } else {
00153 svalue = "";
00154 }
00155
00156
00157 processElement(sname, svalue, atribs);
00158 handleEmptyElement = false;
00159
00160 break;
00161 }
00162
00163
00164 case XML_READER_TYPE_END_ELEMENT: {
00165 processEndElement( sname );
00166 break;
00167 }
00168 }
00169
00170 }
00171
00172
00173
00174
00175
00176 void XMLSOMReader::prepareAttrs() {
00177
00178 const xmlChar* name;
00179 const xmlChar* value;
00180
00181 atribs.clear();
00182
00183 int count = xmlTextReaderAttributeCount(reader);
00184
00185 for(register int i = 0 ; i < count ; i++) {
00186
00187 if (xmlTextReaderMoveToAttributeNo(reader, i) == 1) {
00188 name = xmlTextReaderConstName(reader);
00189 value = xmlTextReaderConstValue(reader);
00190
00191 std::string sname( (char *) name );
00192 std::string svalue( (char *) value );
00193
00194
00195 atribs[sname] = svalue;
00196
00197 }
00198 }
00199 };
00200
00201
00202 };
00203
00204 #endif
00205
00206