From addf63c2337bc1c5e31cad5790c46ac8ae13a724 Mon Sep 17 00:00:00 2001 From: Benjamin Paassen Date: Fri, 13 Feb 2015 13:58:21 +0100 Subject: added VariantReader::parseTyped --- src/core/common/VariantReader.cpp | 84 ++++++++++++++++++++++++++++++++++++++- 1 file changed, 82 insertions(+), 2 deletions(-) (limited to 'src/core/common/VariantReader.cpp') diff --git a/src/core/common/VariantReader.cpp b/src/core/common/VariantReader.cpp index cac29b9..3f02226 100644 --- a/src/core/common/VariantReader.cpp +++ b/src/core/common/VariantReader.cpp @@ -484,8 +484,8 @@ std::pair VariantReader::parseUnescapedString( return std::make_pair(true, res.str()); } -std::pair VariantReader::parseBool( - CharReader &reader, Logger &logger) +std::pair VariantReader::parseBool(CharReader &reader, + Logger &logger) { // first we consume all whitespaces. reader.consumePeek(); @@ -867,5 +867,85 @@ std::pair VariantReader::parseGenericString( v.setLocation({sourceId, offs, offs + str.size()}); return std::make_pair(true, v); } + +std::pair VariantReader::parseTyped( + VariantType type, CharReader &reader, Logger &logger, + const std::unordered_set &delims) +{ + switch (type) { + case VariantType::BOOL: { + auto res = parseBool(reader, logger); + return std::make_pair(res.first, Variant{res.second}); + } + case VariantType::INT: { + auto res = parseInteger(reader, logger, delims); + if (res.second < std::numeric_limits::min() || + res.second > std::numeric_limits::max()) { + logger.error("Number exceeds type limits.", reader); + return std::make_pair(false, Variant{}); + } + return std::make_pair( + res.first, Variant{static_cast(res.second)}); + } + case VariantType::DOUBLE: { + auto res = parseDouble(reader, logger, delims); + return std::make_pair(res.first, Variant{res.second}); + } + case VariantType::STRING: { + auto res = parseString(reader, logger, delims); + return std::make_pair(res.first, Variant::fromString(res.second)); + } + case VariantType::ARRAY: { + char delim = 0; + if (delims.size() == 1) { + delim = *delims.begin(); + } + auto res = parseArray(reader, logger, delim); + return std::make_pair(res.first, Variant{res.second}); + } + + case VariantType::MAP: + case VariantType::OBJECT: { + char delim = 0; + if (delims.size() == 1) { + delim = *delims.begin(); + } + auto res = parseObject(reader, logger, delim); + return std::make_pair(res.first, Variant{res.second}); + } + case VariantType::CARDINALITY: { + auto res = parseCardinality(reader, logger); + return std::make_pair(res.first, Variant{res.second}); + } + default: + break; + } + + return std::make_pair(false, Variant{}); +} + +std::pair VariantReader::parseTyped(VariantType type, + const std::string &str, + Logger &logger, + SourceId sourceId, + size_t offs) +{ + // create a char reader and forward the method. + CharReader reader{str, sourceId, offs}; + LoggerFork loggerFork = logger.fork(); + std::pair res = + parseTyped(type, reader, loggerFork, std::unordered_set{}); + + // If all content could be parsed, commit the result. + if (reader.atEnd()) { + loggerFork.commit(); + return res; + } + + // otherwise do not. + logger.error("Not all input could be processed", + {sourceId, offs, offs + str.size()}); + return std::make_pair(false, Variant{}); +} } -- cgit v1.2.3