source: XIOS2/trunk/src/xml_parser.cpp

Last change on this file was 2615, checked in by ymipsl, 4 months ago
  • Permit now usage of contex_group into xml file for more modularity
  • Src path is now relative to parent file, except if path is an absolute path

YM

  • Property copyright set to
    Software name : XIOS (Xml I/O Server)
    http://forge.ipsl.jussieu.fr/ioserver
    Creation date : January 2009
    Licence : CeCCIL version2
    see license file in root directory : Licence_CeCILL_V2-en.txt
    or http://www.cecill.info/licences/Licence_CeCILL_V2-en.html
    Holder : CEA/LSCE (Laboratoire des Sciences du CLimat et de l'Environnement)
    CNRS/IPSL (Institut Pierre Simon Laplace)
    Project Manager : Yann Meurdesoif
    yann.meurdesoif@cea.fr
File size: 5.4 KB
Line 
1#include "xml_parser.hpp"
2
3#include "context.hpp"
4
5#include "attribute_template.hpp"
6#include "object_template.hpp"
7#include "group_template.hpp"
8#include "string_tools.hpp"
9
10namespace xios
11{
12   namespace xml
13   {
14     
15      string CXMLParser::currentIncludePath_="." ;
16
17      string CXMLParser::updateIncludePath(const string& filePath)
18      {
19        string path = strTrim(filePath) ;
20        vector<string> match=splitRegex(path+'/',"/" ) ;
21
22        // check if empty path
23        bool isEmpty=true ;
24        for(auto& m : match) 
25          if (!m.empty())
26          {
27            isEmpty=false ;
28            break ;
29          }
30
31        if (isEmpty) ERROR("string CXMLParser::updatePath(const string& filePath)",
32                     << "File path to include an new XML is empty :'"<<filePath<<"'" );
33
34        if (match.back().empty()) ERROR("string CXMLParser::updatePath(const string& filePath)",
35                     << "File path to include an new XML must not be a directory but a file :'"<<filePath<<"'" );
36        bool isAbsolutePath = match.front().empty() ;
37       
38        if (isAbsolutePath) currentIncludePath_="" ;
39        for(int i=0; i<match.size()-1; ++i) if (! match[i].empty()) currentIncludePath_ = currentIncludePath_ + "/" + match[i] ;
40       
41        string finalPath = currentIncludePath_ + "/" + match.back() ;
42
43        return finalPath ;
44      }
45
46
47      /// ////////////////////// Définitions ////////////////////// ///
48
49      void CXMLParser::ParseFile(const StdString & filename, const std::set<StdString>& parseContextList)
50      TRY
51      {
52         StdIFStream ifs ( filename.c_str() , StdIFStream::in );
53         if ( (ifs.rdstate() & std::ifstream::failbit ) != 0 )
54           ERROR("void CXMLParser::ParseFile(const StdString & filename)",
55                  <<endl<< "Can not open <"<<filename<<"> file" );
56
57         CXMLParser::ParseStream(ifs, filename, parseContextList);
58      }
59      CATCH
60
61      void CXMLParser::ParseString(const StdString & xmlContent)
62      {
63         StdIStringStream iss ( xmlContent /*, StdIStringStream::in*/ );
64         std::set<StdString> contxtList;
65         CXMLParser::ParseStream(iss,"string", contxtList);
66      }
67
68      void CXMLParser::ParseStream(StdIStream & stream, const string& fluxId, const std::set<StdString>& parseContextList)
69      {
70         if (!stream.good())
71            ERROR("CXMLParser::ParseStream(const StdIStream & stream)",
72                  << "Bad xml stream !");
73         StdOStringStream oss;
74         while(!stream.eof() && !stream.fail ()) oss.put(stream.get());
75         const StdString xmlcontent( oss.str(), 0, oss.str().size()-1 );
76         try
77         {
78            rapidxml::xml_document<char> doc;
79            doc.parse<0>(const_cast<char*>(xmlcontent.c_str()));
80
81            CXMLNode node(doc.first_node());
82            THashAttributes attributes;
83
84            if (node.getElementName().compare(CXMLNode::GetRootName()) != 0)
85               ERROR("CXMLParser::ParseStream(StdIStream & stream)",
86                     << "Root element should be named simulation (actual = \'"
87                     << node.getElementName() << "\')!");
88            try
89            {
90              CContextGroup* rootContext = CContext::getRoot() ;
91              rootContext->parse(node, true, parseContextList) ;
92            }
93            catch(CException& e)
94            {
95              CException::StackInfo stk;
96              stk.info.append("Exception occurred while parsing XML file \"");
97              stk.info.append(attributes["src"]);
98              stk.info.append("\".\n");
99              stk.file = FILE_NAME;
100              stk.function = FUNCTION_NAME;
101              stk.line = __LINE__;
102              e.stack.push_back(stk);
103              if (CXios::xiosStack)
104                throw;
105             else
106               throw 0;
107            }
108            catch(...)
109            {
110              CException exc;
111              CException::StackInfo stk;
112              stk.info.append("Exception occurred while parsing XML file \"");
113              stk.info.append(attributes["src"]);
114              stk.info.append("\".\n");
115              stk.file = FILE_NAME;
116              stk.function = FUNCTION_NAME;
117              stk.line = __LINE__;
118              exc.stack.push_back(stk);
119              if (CXios::xiosStack)
120                throw exc;
121             else
122               throw 0;
123            }
124
125         }
126         catch (rapidxml::parse_error & exc)
127         {
128            const char* ptr = exc.where<char>() ;
129            const char* begin = xmlcontent.c_str() ;
130            const char* content=oss.str().c_str() ;
131            size_t pos=ptr-begin ;
132            int lineNumber = 1 ;
133            int columnNumber = 0 ;
134            const char* line;
135            const char* endLine;
136
137            for(const char* i=content;i<content+pos; ++i, ++columnNumber) if (*i=='\n') { lineNumber++ ; line=i ; columnNumber=0 ;}
138            for(endLine=content+pos; *endLine!='\n' && *endLine!='\0' ; ++endLine) ;
139            string strLine(line,endLine-line) ;
140
141            ERROR("CXMLParser::ParseStream(StdIStream & stream)", << endl
142                  << "Error is occuring when parsing XML flux from <"<<fluxId<<"> at character "<< pos<<" line "<<lineNumber<<" column "<< columnNumber<< endl
143                  << strLine<<endl
144                  << string(columnNumber-1,'x')<<'^'<<endl)
145//                  <<" Error : " << exc.what() )
146         }
147      }
148
149   }// namespace xml
150} // namespace xios
Note: See TracBrowser for help on using the repository browser.