mirror of
https://github.com/pocoproject/poco.git
synced 2025-02-15 10:55:25 +01:00
Try to save the type for Var with Json serialize/deserialize (#1703)
* Fix JSON to Var parsing (save the type) * fix formatting * remove redundant include <iostream> * fix c++98 compatibility
This commit is contained in:
parent
3ec9316ab0
commit
7f193697db
@ -404,7 +404,63 @@ Var Var::parse(const std::string& val, std::string::size_type& pos)
|
|||||||
case '"':
|
case '"':
|
||||||
return parseJSONString(val, pos);
|
return parseJSONString(val, pos);
|
||||||
default:
|
default:
|
||||||
return parseString(val, pos);
|
{
|
||||||
|
std::string str = parseString(val, pos);
|
||||||
|
if (str == "false")
|
||||||
|
return false;
|
||||||
|
|
||||||
|
if (str == "true")
|
||||||
|
return true;
|
||||||
|
|
||||||
|
bool isNumber = false;
|
||||||
|
bool isSigned = false;
|
||||||
|
int separators = 0;
|
||||||
|
int separator = 0;
|
||||||
|
int index = 0;
|
||||||
|
size_t size = str.size();
|
||||||
|
for (size_t i = 0; i < size ; ++i)
|
||||||
|
{
|
||||||
|
int ch = str[i];
|
||||||
|
if ((ch == '-' || ch == '+') && index == 0)
|
||||||
|
{
|
||||||
|
if (ch == '-')
|
||||||
|
isSigned = true;
|
||||||
|
}
|
||||||
|
else if (Ascii::isDigit(ch))
|
||||||
|
{
|
||||||
|
isNumber |= true;
|
||||||
|
}
|
||||||
|
else if (ch == '.' || ch == ',')
|
||||||
|
{
|
||||||
|
separator = ch;
|
||||||
|
++separators;
|
||||||
|
if (separators > 1)
|
||||||
|
return str;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
return str;
|
||||||
|
|
||||||
|
++index;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (separator && isNumber)
|
||||||
|
{
|
||||||
|
const double number = NumberParser::parseFloat(str, separator);
|
||||||
|
return Var(number);
|
||||||
|
}
|
||||||
|
else if (separator == 0 && isNumber && isSigned)
|
||||||
|
{
|
||||||
|
const Poco::Int64 number = NumberParser::parse64(str);
|
||||||
|
return number;
|
||||||
|
}
|
||||||
|
else if (separator == 0 && isNumber && !isSigned)
|
||||||
|
{
|
||||||
|
const Poco::UInt64 number = NumberParser::parseUnsigned64(str);
|
||||||
|
return number;
|
||||||
|
}
|
||||||
|
|
||||||
|
return str;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
std::string empty;
|
std::string empty;
|
||||||
|
@ -2203,11 +2203,11 @@ void VarTest::testJSONDeserializeString()
|
|||||||
char cc = b2.convert<char>();
|
char cc = b2.convert<char>();
|
||||||
assert (cc == 'c');
|
assert (cc == 'c');
|
||||||
|
|
||||||
tst = "{ \"a\" : 1, \"b\" : 2 \n}";
|
tst = "{ \"a\" : \"1\", \"b\" : \"2\" \n}";
|
||||||
a = Var::parse(tst);
|
a = Var::parse(tst);
|
||||||
assert(a.toString() == "{ \"a\" : \"1\", \"b\" : \"2\" }");
|
assert(a.toString() == "{ \"a\" : \"1\", \"b\" : \"2\" }");
|
||||||
|
|
||||||
tst = "{ \"a\" : 1, \"b\" : 2\n}";
|
tst = "{ \"a\" : \"1\", \"b\" : \"2\"\n}";
|
||||||
a = Var::parse(tst);
|
a = Var::parse(tst);
|
||||||
assert(a.toString() == "{ \"a\" : \"1\", \"b\" : \"2\" }");
|
assert(a.toString() == "{ \"a\" : \"1\", \"b\" : \"2\" }");
|
||||||
}
|
}
|
||||||
@ -2373,15 +2373,43 @@ void VarTest::testJSONDeserializeStruct()
|
|||||||
|
|
||||||
std::string sStr = Var::toString(aStr);
|
std::string sStr = Var::toString(aStr);
|
||||||
Var a = Var::parse(sStr);
|
Var a = Var::parse(sStr);
|
||||||
assert (aStr["i8"] == i8);
|
assert (a["i8"] == i8);
|
||||||
assert (aStr["u16"] == u16);
|
assert (a["u16"] == u16);
|
||||||
assert (aStr["i32"] == i32);
|
assert (a["i32"] == i32);
|
||||||
assert (aStr["u64"] == u64);
|
assert (a["u64"] == u64);
|
||||||
assert (aStr["b"] == b);
|
assert (a["b"] == b);
|
||||||
assert (aStr["f"] == f);
|
assert (a["f"] == f);
|
||||||
assert (aStr["d"] == d);
|
assert (a["d"] == d);
|
||||||
assert (aStr["s"] == s);
|
assert (a["s"] == s);
|
||||||
assert (aStr["c"] == c);
|
assert (a["c"] == c);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
void VarTest::testJSONRoundtripStruct()
|
||||||
|
{
|
||||||
|
Poco::Int64 i64(-1234567890);
|
||||||
|
Poco::UInt64 u64(1234567890);
|
||||||
|
u64 *= u64;
|
||||||
|
bool b = false;
|
||||||
|
double d = 3.1415;
|
||||||
|
std::string s("test string");
|
||||||
|
DynamicStruct aStr;
|
||||||
|
aStr["i64"] = i64;
|
||||||
|
aStr["u64"] = u64;
|
||||||
|
aStr["b"] = b;
|
||||||
|
aStr["d"] = d;
|
||||||
|
aStr["s"] = s;
|
||||||
|
|
||||||
|
std::string sStr = Var::toString(aStr);
|
||||||
|
Var a = Var::parse(sStr);
|
||||||
|
assert (a["i64"].isInteger());
|
||||||
|
assert (!a["u64"].isSigned());
|
||||||
|
assert (a["b"].isBoolean());
|
||||||
|
assert (a["d"].isNumeric());
|
||||||
|
assert (a["s"].isString());
|
||||||
|
|
||||||
|
std::string serialized = Var::toString(a);
|
||||||
|
assert (sStr == serialized);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@ -2642,6 +2670,7 @@ CppUnit::Test* VarTest::suite()
|
|||||||
CppUnit_addTest(pSuite, VarTest, testJSONDeserializeArray);
|
CppUnit_addTest(pSuite, VarTest, testJSONDeserializeArray);
|
||||||
CppUnit_addTest(pSuite, VarTest, testJSONDeserializeStruct);
|
CppUnit_addTest(pSuite, VarTest, testJSONDeserializeStruct);
|
||||||
CppUnit_addTest(pSuite, VarTest, testJSONDeserializeComplex);
|
CppUnit_addTest(pSuite, VarTest, testJSONDeserializeComplex);
|
||||||
|
CppUnit_addTest(pSuite, VarTest, testJSONRoundtripStruct);
|
||||||
CppUnit_addTest(pSuite, VarTest, testDate);
|
CppUnit_addTest(pSuite, VarTest, testDate);
|
||||||
CppUnit_addTest(pSuite, VarTest, testEmpty);
|
CppUnit_addTest(pSuite, VarTest, testEmpty);
|
||||||
CppUnit_addTest(pSuite, VarTest, testIterator);
|
CppUnit_addTest(pSuite, VarTest, testIterator);
|
||||||
|
@ -67,6 +67,7 @@ public:
|
|||||||
void testJSONDeserializePrimitives();
|
void testJSONDeserializePrimitives();
|
||||||
void testJSONDeserializeArray();
|
void testJSONDeserializeArray();
|
||||||
void testJSONDeserializeStruct();
|
void testJSONDeserializeStruct();
|
||||||
|
void testJSONRoundtripStruct();
|
||||||
void testJSONDeserializeComplex();
|
void testJSONDeserializeComplex();
|
||||||
void testDate();
|
void testDate();
|
||||||
void testEmpty();
|
void testEmpty();
|
||||||
|
Loading…
x
Reference in New Issue
Block a user