Var Query::find(const std::string& path) const { Var result = _source; StringTokenizer tokenizer(path, "."); for(StringTokenizer::Iterator token = tokenizer.begin(); token != tokenizer.end(); token++) { if ( !result.isEmpty() ) { std::vector<int> indexes; RegularExpression::MatchVec matches; int firstOffset = -1; int offset = 0; RegularExpression regex("\\[([0-9]+)\\]"); while(regex.match(*token, offset, matches) > 0 ) { if ( firstOffset == -1 ) { firstOffset = static_cast<int>(matches[0].offset); } std::string num = token->substr(matches[1].offset, matches[1].length); indexes.push_back(NumberParser::parse(num)); offset = static_cast<int>(matches[0].offset + matches[0].length); } std::string name(*token); if ( firstOffset != -1 ) { name = name.substr(0, firstOffset); } if ( name.length() > 0 ) { if ( result.type() == typeid(Object::Ptr) ) { Object::Ptr o = result.extract<Object::Ptr>(); result = o->get(name); } } if ( !result.isEmpty() && !indexes.empty() ) { for(std::vector<int>::iterator it = indexes.begin(); it != indexes.end(); ++it ) { if ( result.type() == typeid(Array::Ptr) ) { Array::Ptr array = result.extract<Array::Ptr>(); result = array->get(*it); if ( result.isEmpty() ) { break; } } } } } } return result; }
void Utility::detectPrefixAndIncludes(const std::string& origHFile, std::vector<std::string>& lines, std::string& prefix) { std::ifstream istr(origHFile.c_str()); try { if (istr.good()) { std::string x; istr >> x; while (x.find("#ifndef") == std::string::npos) istr >> x; StringTokenizer tokenizer(x, " \t", StringTokenizer::TOK_IGNORE_EMPTY | StringTokenizer::TOK_TRIM); poco_assert (tokenizer.count() == 2); StringTokenizer::Iterator itTmp = tokenizer.begin(); ++itTmp; std::string defValue = *itTmp; istr >> x; // now find the corresponding #define while (x.find(defValue) == std::string::npos) istr >> x; //now parse until a class def is found without a ; at the end bool stop = false; std::string prefixHint; do { istr >> x; // we add EVERYTHING to lines: reason: used macros/preprocessor defines, conditional includes should all be present in the generated code // just think about fwd declarations inside a NS_BEGIN ... NS_END block if (x.find("class") != std::string::npos && x.find(";") == std::string::npos) { StringTokenizer tok(x, " \t", StringTokenizer::TOK_IGNORE_EMPTY | StringTokenizer::TOK_TRIM); StringTokenizer::Iterator it = tok.begin(); while (*it != "class" && it != tok.end()) ++it; // the next after class must be *_API or in case of a template it must be the class name ++it; std::size_t apiPos = it->find("_API"); if (apiPos != std::string::npos) { prefixHint = it->substr(0, apiPos); } stop = true; } else { lines.push_back(x); } } while (!stop && !istr.eof()); if (!stop) { lines.clear(); prefix.clear(); //throw Poco::SyntaxException("Failed to parse file " + origHFile + ".No class declared?"); return; } // now search the prefix if (lines.empty()) { prefix.clear(); return; } // the prefix for that file std::vector<std::string>::const_iterator it = lines.end(); --it; std::vector<std::string>::const_iterator itBegin = lines.begin(); for (; it != itBegin; --it) { std::size_t prefixPos = it->find("_BEGIN"); if (prefixPos != std::string::npos) { prefix = it->substr(0, prefixPos); if (prefix != prefixHint && !prefixHint.empty()) { throw Poco::SyntaxException("Conflicting prefixes detected: " + prefixHint + "<->" + prefix); } } } } else throw Poco::OpenFileException(origHFile); }