forked from bblanchon/ArduinoJson
Disabled lazy number deserialization (fixes #772)
This commit is contained in:
14
CHANGELOG.md
14
CHANGELOG.md
@ -1,6 +1,16 @@
|
|||||||
ArduinoJson: change log
|
ArduinoJson: change log
|
||||||
=======================
|
=======================
|
||||||
|
|
||||||
|
HEAD
|
||||||
|
----
|
||||||
|
|
||||||
|
* Disabled lazy number deserialization (issue #772)
|
||||||
|
|
||||||
|
> ### BREAKING CHANGES
|
||||||
|
>
|
||||||
|
> Non quoted strings are now forbidden in values, but they are still allowed in keys.
|
||||||
|
> For example, `{key:"value"}` is accepted, but `{key:value}` is not.
|
||||||
|
|
||||||
v6.1.0-beta
|
v6.1.0-beta
|
||||||
-----------
|
-----------
|
||||||
|
|
||||||
@ -15,7 +25,7 @@ v6.1.0-beta
|
|||||||
> JsonObject& obj = doc.to<JsonObject>();
|
> JsonObject& obj = doc.to<JsonObject>();
|
||||||
> JsonArray& arr = obj.createNestedArray("key");
|
> JsonArray& arr = obj.createNestedArray("key");
|
||||||
> if (!arr.success()) {
|
> if (!arr.success()) {
|
||||||
> Serial.println("No enough memory");
|
> Serial.println("Not enough memory");
|
||||||
> return;
|
> return;
|
||||||
> }
|
> }
|
||||||
> ```
|
> ```
|
||||||
@ -26,7 +36,7 @@ v6.1.0-beta
|
|||||||
> JsonObject obj = doc.to<JsonObject>();
|
> JsonObject obj = doc.to<JsonObject>();
|
||||||
> JsonArray arr = obj.createNestedArray("key");
|
> JsonArray arr = obj.createNestedArray("key");
|
||||||
> if (arr.isNull()) {
|
> if (arr.isNull()) {
|
||||||
> Serial.println("No enough memory");
|
> Serial.println("Not enough memory");
|
||||||
> return;
|
> return;
|
||||||
> }
|
> }
|
||||||
> ```
|
> ```
|
||||||
|
@ -121,7 +121,7 @@ class JsonDeserializer {
|
|||||||
for (;;) {
|
for (;;) {
|
||||||
// Parse key
|
// Parse key
|
||||||
const char *key;
|
const char *key;
|
||||||
err = parseString(&key);
|
err = parseKey(&key);
|
||||||
if (err) return err;
|
if (err) return err;
|
||||||
|
|
||||||
// Skip spaces
|
// Skip spaces
|
||||||
@ -152,48 +152,69 @@ class JsonDeserializer {
|
|||||||
}
|
}
|
||||||
|
|
||||||
DeserializationError parseValue(JsonVariant &variant) {
|
DeserializationError parseValue(JsonVariant &variant) {
|
||||||
bool hasQuotes = isQuote(current());
|
if (isQuote(current())) {
|
||||||
const char *value;
|
return parseStringValue(variant);
|
||||||
DeserializationError error = parseString(&value);
|
|
||||||
if (error) return error;
|
|
||||||
if (hasQuotes) {
|
|
||||||
variant = value;
|
|
||||||
} else {
|
} else {
|
||||||
variant = RawJson(value);
|
return parseNumericValue(variant);
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
DeserializationError parseKey(const char **key) {
|
||||||
|
if (isQuote(current())) {
|
||||||
|
return parseQuotedString(key);
|
||||||
|
} else {
|
||||||
|
return parseNonQuotedString(key);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
DeserializationError parseStringValue(JsonVariant &variant) {
|
||||||
|
const char *value;
|
||||||
|
DeserializationError err = parseQuotedString(&value);
|
||||||
|
if (err) return err;
|
||||||
|
variant = value;
|
||||||
return DeserializationError::Ok;
|
return DeserializationError::Ok;
|
||||||
}
|
}
|
||||||
|
|
||||||
DeserializationError parseString(const char **result) {
|
DeserializationError parseQuotedString(const char **result) {
|
||||||
|
typename remove_reference<TStringStorage>::type::String str =
|
||||||
|
_stringStorage.startString();
|
||||||
|
|
||||||
|
char stopChar = current();
|
||||||
|
|
||||||
|
move();
|
||||||
|
for (;;) {
|
||||||
|
char c = current();
|
||||||
|
move();
|
||||||
|
if (c == stopChar) break;
|
||||||
|
|
||||||
|
if (c == '\0') return DeserializationError::IncompleteInput;
|
||||||
|
|
||||||
|
if (c == '\\') {
|
||||||
|
c = current();
|
||||||
|
if (c == '\0') return DeserializationError::IncompleteInput;
|
||||||
|
if (c == 'u') return DeserializationError::NotSupported;
|
||||||
|
// replace char
|
||||||
|
c = EscapeSequence::unescapeChar(c);
|
||||||
|
if (c == '\0') return DeserializationError::InvalidInput;
|
||||||
|
move();
|
||||||
|
}
|
||||||
|
|
||||||
|
str.append(c);
|
||||||
|
}
|
||||||
|
|
||||||
|
*result = str.c_str();
|
||||||
|
if (*result == NULL) return DeserializationError::NoMemory;
|
||||||
|
return DeserializationError::Ok;
|
||||||
|
}
|
||||||
|
|
||||||
|
DeserializationError parseNonQuotedString(const char **result) {
|
||||||
typename remove_reference<TStringStorage>::type::String str =
|
typename remove_reference<TStringStorage>::type::String str =
|
||||||
_stringStorage.startString();
|
_stringStorage.startString();
|
||||||
|
|
||||||
char c = current();
|
char c = current();
|
||||||
if (c == '\0') return DeserializationError::IncompleteInput;
|
if (c == '\0') return DeserializationError::IncompleteInput;
|
||||||
|
|
||||||
if (isQuote(c)) { // quotes
|
if (canBeInNonQuotedString(c)) { // no quotes
|
||||||
move();
|
|
||||||
char stopChar = c;
|
|
||||||
for (;;) {
|
|
||||||
c = current();
|
|
||||||
move();
|
|
||||||
if (c == stopChar) break;
|
|
||||||
|
|
||||||
if (c == '\0') return DeserializationError::IncompleteInput;
|
|
||||||
|
|
||||||
if (c == '\\') {
|
|
||||||
c = current();
|
|
||||||
if (c == '\0') return DeserializationError::IncompleteInput;
|
|
||||||
if (c == 'u') return DeserializationError::NotSupported;
|
|
||||||
// replace char
|
|
||||||
c = EscapeSequence::unescapeChar(c);
|
|
||||||
if (c == '\0') return DeserializationError::InvalidInput;
|
|
||||||
move();
|
|
||||||
}
|
|
||||||
|
|
||||||
str.append(c);
|
|
||||||
}
|
|
||||||
} else if (canBeInNonQuotedString(c)) { // no quotes
|
|
||||||
do {
|
do {
|
||||||
move();
|
move();
|
||||||
str.append(c);
|
str.append(c);
|
||||||
@ -208,6 +229,34 @@ class JsonDeserializer {
|
|||||||
return DeserializationError::Ok;
|
return DeserializationError::Ok;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
DeserializationError parseNumericValue(JsonVariant &result) {
|
||||||
|
char buffer[64];
|
||||||
|
uint8_t n = 0;
|
||||||
|
|
||||||
|
char c = current();
|
||||||
|
while (canBeInNonQuotedString(c) && n < 63) {
|
||||||
|
move();
|
||||||
|
buffer[n++] = c;
|
||||||
|
c = current();
|
||||||
|
}
|
||||||
|
buffer[n] = 0;
|
||||||
|
|
||||||
|
if (isInteger(buffer)) {
|
||||||
|
result = parseInteger<JsonInteger>(buffer);
|
||||||
|
} else if (isFloat(buffer)) {
|
||||||
|
result = parseFloat<JsonFloat>(buffer);
|
||||||
|
} else if (!strcmp(buffer, "true")) {
|
||||||
|
result = true;
|
||||||
|
} else if (!strcmp(buffer, "false")) {
|
||||||
|
result = false;
|
||||||
|
} else if (!strcmp(buffer, "null")) {
|
||||||
|
result = static_cast<const char *>(0);
|
||||||
|
} else {
|
||||||
|
return DeserializationError::InvalidInput;
|
||||||
|
}
|
||||||
|
return DeserializationError::Ok;
|
||||||
|
}
|
||||||
|
|
||||||
static inline bool isBetween(char c, char min, char max) {
|
static inline bool isBetween(char c, char min, char max) {
|
||||||
return min <= c && c <= max;
|
return min <= c && c <= max;
|
||||||
}
|
}
|
||||||
@ -286,7 +335,7 @@ class JsonDeserializer {
|
|||||||
uint8_t _nestingLimit;
|
uint8_t _nestingLimit;
|
||||||
char _current;
|
char _current;
|
||||||
bool _loaded;
|
bool _loaded;
|
||||||
};
|
}; // namespace Internals
|
||||||
} // namespace Internals
|
} // namespace Internals
|
||||||
|
|
||||||
template <typename TDocument, typename TInput>
|
template <typename TDocument, typename TInput>
|
||||||
|
@ -10,7 +10,7 @@ namespace ArduinoJson {
|
|||||||
namespace Internals {
|
namespace Internals {
|
||||||
|
|
||||||
inline bool isInteger(const char* s) {
|
inline bool isInteger(const char* s) {
|
||||||
if (!s) return false;
|
if (!s || !*s) return false;
|
||||||
if (issign(*s)) s++;
|
if (issign(*s)) s++;
|
||||||
while (isdigit(*s)) s++;
|
while (isdigit(*s)) s++;
|
||||||
return *s == '\0';
|
return *s == '\0';
|
||||||
|
@ -67,13 +67,13 @@ endif()
|
|||||||
add_subdirectory(DynamicJsonBuffer)
|
add_subdirectory(DynamicJsonBuffer)
|
||||||
add_subdirectory(IntegrationTests)
|
add_subdirectory(IntegrationTests)
|
||||||
add_subdirectory(JsonArray)
|
add_subdirectory(JsonArray)
|
||||||
add_subdirectory(JsonObject)
|
|
||||||
add_subdirectory(JsonDeserializer)
|
add_subdirectory(JsonDeserializer)
|
||||||
|
add_subdirectory(JsonObject)
|
||||||
add_subdirectory(JsonSerializer)
|
add_subdirectory(JsonSerializer)
|
||||||
add_subdirectory(JsonVariant)
|
add_subdirectory(JsonVariant)
|
||||||
add_subdirectory(JsonWriter)
|
add_subdirectory(JsonWriter)
|
||||||
add_subdirectory(Misc)
|
add_subdirectory(Misc)
|
||||||
add_subdirectory(MsgPackDeserializer)
|
add_subdirectory(MsgPackDeserializer)
|
||||||
add_subdirectory(MsgPackSerializer)
|
add_subdirectory(MsgPackSerializer)
|
||||||
add_subdirectory(Polyfills)
|
add_subdirectory(Numbers)
|
||||||
add_subdirectory(StaticJsonBuffer)
|
add_subdirectory(StaticJsonBuffer)
|
||||||
|
@ -4,6 +4,7 @@
|
|||||||
|
|
||||||
add_executable(IntegrationTests
|
add_executable(IntegrationTests
|
||||||
gbathree.cpp
|
gbathree.cpp
|
||||||
|
issue772.cpp
|
||||||
round_trip.cpp
|
round_trip.cpp
|
||||||
)
|
)
|
||||||
|
|
||||||
|
27
test/IntegrationTests/issue772.cpp
Normal file
27
test/IntegrationTests/issue772.cpp
Normal file
@ -0,0 +1,27 @@
|
|||||||
|
// ArduinoJson - arduinojson.org
|
||||||
|
// Copyright Benoit Blanchon 2014-2018
|
||||||
|
// MIT License
|
||||||
|
|
||||||
|
#include <ArduinoJson.h>
|
||||||
|
#include <catch.hpp>
|
||||||
|
|
||||||
|
// https://github.com/bblanchon/ArduinoJson/issues/772
|
||||||
|
|
||||||
|
TEST_CASE("Issue772") {
|
||||||
|
DynamicJsonDocument doc1, doc2;
|
||||||
|
DeserializationError err;
|
||||||
|
std::string data =
|
||||||
|
"{\"state\":{\"reported\":{\"timestamp\":\"2018-07-02T09:40:12Z\","
|
||||||
|
"\"mac\":\"2C3AE84FC076\",\"firmwareVersion\":\"v0.2.7-5-gf4d4d78\","
|
||||||
|
"\"visibleLight\":261,\"infraRed\":255,\"ultraViolet\":0.02,"
|
||||||
|
"\"Temperature\":26.63,\"Pressure\":101145.7,\"Humidity\":54.79883,"
|
||||||
|
"\"Vbat\":4.171261,\"soilMoisture\":0,\"ActB\":0}}}";
|
||||||
|
err = deserializeJson(doc1, data);
|
||||||
|
REQUIRE(err == DeserializationError::Ok);
|
||||||
|
|
||||||
|
data = "";
|
||||||
|
serializeMsgPack(doc1, data);
|
||||||
|
err = deserializeMsgPack(doc2, data);
|
||||||
|
|
||||||
|
REQUIRE(err == DeserializationError::Ok);
|
||||||
|
}
|
@ -128,12 +128,7 @@ TEST_CASE("deserialize JSON array") {
|
|||||||
|
|
||||||
SECTION("No quotes") {
|
SECTION("No quotes") {
|
||||||
DeserializationError err = deserializeJson(doc, "[ hello , world ]");
|
DeserializationError err = deserializeJson(doc, "[ hello , world ]");
|
||||||
JsonArray arr = doc.as<JsonArray>();
|
REQUIRE(err == DeserializationError::InvalidInput);
|
||||||
|
|
||||||
REQUIRE(err == DeserializationError::Ok);
|
|
||||||
REQUIRE(2 == arr.size());
|
|
||||||
REQUIRE(arr[0] == "hello");
|
|
||||||
REQUIRE(arr[1] == "world");
|
|
||||||
}
|
}
|
||||||
|
|
||||||
SECTION("Double quotes (empty strings)") {
|
SECTION("Double quotes (empty strings)") {
|
||||||
|
@ -39,7 +39,7 @@ TEST_CASE("deserialize JSON object") {
|
|||||||
}
|
}
|
||||||
|
|
||||||
SECTION("No quotes") {
|
SECTION("No quotes") {
|
||||||
DeserializationError err = deserializeJson(doc, "{key:value}");
|
DeserializationError err = deserializeJson(doc, "{key:'value'}");
|
||||||
JsonObject obj = doc.as<JsonObject>();
|
JsonObject obj = doc.as<JsonObject>();
|
||||||
|
|
||||||
REQUIRE(err == DeserializationError::Ok);
|
REQUIRE(err == DeserializationError::Ok);
|
||||||
|
@ -21,7 +21,7 @@ TEST_CASE("deserializeJson(std::istream&)") {
|
|||||||
}
|
}
|
||||||
|
|
||||||
SECTION("object") {
|
SECTION("object") {
|
||||||
std::istringstream json(" { hello : world // comment\n }");
|
std::istringstream json(" { hello : 'world' // comment\n }");
|
||||||
|
|
||||||
DeserializationError err = deserializeJson(doc, json);
|
DeserializationError err = deserializeJson(doc, json);
|
||||||
JsonObject obj = doc.as<JsonObject>();
|
JsonObject obj = doc.as<JsonObject>();
|
||||||
|
@ -2,12 +2,12 @@
|
|||||||
# Copyright Benoit Blanchon 2014-2018
|
# Copyright Benoit Blanchon 2014-2018
|
||||||
# MIT License
|
# MIT License
|
||||||
|
|
||||||
add_executable(PolyfillsTests
|
add_executable(NumbersTests
|
||||||
isFloat.cpp
|
isFloat.cpp
|
||||||
isInteger.cpp
|
isInteger.cpp
|
||||||
parseFloat.cpp
|
parseFloat.cpp
|
||||||
parseInteger.cpp
|
parseInteger.cpp
|
||||||
)
|
)
|
||||||
|
|
||||||
target_link_libraries(PolyfillsTests catch)
|
target_link_libraries(NumbersTests catch)
|
||||||
add_test(Polyfills PolyfillsTests)
|
add_test(Numbers NumbersTests)
|
80
test/Numbers/isFloat.cpp
Normal file
80
test/Numbers/isFloat.cpp
Normal file
@ -0,0 +1,80 @@
|
|||||||
|
// ArduinoJson - arduinojson.org
|
||||||
|
// Copyright Benoit Blanchon 2014-2018
|
||||||
|
// MIT License
|
||||||
|
|
||||||
|
#include <ArduinoJson/Numbers/isFloat.hpp>
|
||||||
|
#include <catch.hpp>
|
||||||
|
|
||||||
|
using namespace ArduinoJson::Internals;
|
||||||
|
|
||||||
|
TEST_CASE("isFloat()") {
|
||||||
|
SECTION("Input is NULL") {
|
||||||
|
REQUIRE(isFloat(NULL) == false);
|
||||||
|
}
|
||||||
|
|
||||||
|
SECTION("Empty string") {
|
||||||
|
REQUIRE(isFloat("") == false);
|
||||||
|
}
|
||||||
|
|
||||||
|
SECTION("NoExponent") {
|
||||||
|
REQUIRE(isFloat("3.14") == true);
|
||||||
|
REQUIRE(isFloat("-3.14") == true);
|
||||||
|
REQUIRE(isFloat("+3.14") == true);
|
||||||
|
}
|
||||||
|
|
||||||
|
SECTION("IntegralPartMissing") {
|
||||||
|
REQUIRE(isFloat(".14") == true);
|
||||||
|
REQUIRE(isFloat("-.14") == true);
|
||||||
|
REQUIRE(isFloat("+.14") == true);
|
||||||
|
}
|
||||||
|
|
||||||
|
SECTION("FractionalPartMissing") {
|
||||||
|
REQUIRE(isFloat("3.") == true);
|
||||||
|
REQUIRE(isFloat("-3.e14") == true);
|
||||||
|
REQUIRE(isFloat("+3.e-14") == true);
|
||||||
|
}
|
||||||
|
|
||||||
|
SECTION("NoDot") {
|
||||||
|
REQUIRE(isFloat("3e14") == true);
|
||||||
|
REQUIRE(isFloat("3e-14") == true);
|
||||||
|
REQUIRE(isFloat("3e+14") == true);
|
||||||
|
}
|
||||||
|
|
||||||
|
SECTION("Integer") {
|
||||||
|
REQUIRE(isFloat("14") == true);
|
||||||
|
REQUIRE(isFloat("-14") == true);
|
||||||
|
REQUIRE(isFloat("+14") == true);
|
||||||
|
}
|
||||||
|
|
||||||
|
SECTION("ExponentMissing") {
|
||||||
|
REQUIRE(isFloat("3.14e") == false);
|
||||||
|
REQUIRE(isFloat("3.14e-") == false);
|
||||||
|
REQUIRE(isFloat("3.14e+") == false);
|
||||||
|
}
|
||||||
|
|
||||||
|
SECTION("JustASign") {
|
||||||
|
REQUIRE(isFloat("-") == false);
|
||||||
|
REQUIRE(isFloat("+") == false);
|
||||||
|
}
|
||||||
|
|
||||||
|
SECTION("Empty") {
|
||||||
|
REQUIRE(isFloat("") == false);
|
||||||
|
}
|
||||||
|
|
||||||
|
SECTION("NaN") {
|
||||||
|
REQUIRE(isFloat("NaN") == true);
|
||||||
|
REQUIRE(isFloat("n") == false);
|
||||||
|
REQUIRE(isFloat("N") == false);
|
||||||
|
REQUIRE(isFloat("nan") == false);
|
||||||
|
REQUIRE(isFloat("-NaN") == false);
|
||||||
|
REQUIRE(isFloat("+NaN") == false);
|
||||||
|
}
|
||||||
|
|
||||||
|
SECTION("Infinity") {
|
||||||
|
REQUIRE(isFloat("Infinity") == true);
|
||||||
|
REQUIRE(isFloat("+Infinity") == true);
|
||||||
|
REQUIRE(isFloat("-Infinity") == true);
|
||||||
|
REQUIRE(isFloat("infinity") == false);
|
||||||
|
REQUIRE(isFloat("Inf") == false);
|
||||||
|
}
|
||||||
|
}
|
40
test/Numbers/isInteger.cpp
Normal file
40
test/Numbers/isInteger.cpp
Normal file
@ -0,0 +1,40 @@
|
|||||||
|
// ArduinoJson - arduinojson.org
|
||||||
|
// Copyright Benoit Blanchon 2014-2018
|
||||||
|
// MIT License
|
||||||
|
|
||||||
|
#include <ArduinoJson/Numbers/isInteger.hpp>
|
||||||
|
#include <catch.hpp>
|
||||||
|
|
||||||
|
using namespace ArduinoJson::Internals;
|
||||||
|
|
||||||
|
TEST_CASE("isInteger()") {
|
||||||
|
SECTION("Null") {
|
||||||
|
REQUIRE(isInteger(NULL) == false);
|
||||||
|
}
|
||||||
|
|
||||||
|
SECTION("Empty string") {
|
||||||
|
REQUIRE(isInteger("") == false);
|
||||||
|
}
|
||||||
|
|
||||||
|
SECTION("FloatNotInteger") {
|
||||||
|
REQUIRE(isInteger("3.14") == false);
|
||||||
|
REQUIRE(isInteger("-3.14") == false);
|
||||||
|
REQUIRE(isInteger("+3.14") == false);
|
||||||
|
}
|
||||||
|
|
||||||
|
SECTION("Spaces") {
|
||||||
|
REQUIRE(isInteger("42 ") == false);
|
||||||
|
REQUIRE(isInteger(" 42") == false);
|
||||||
|
}
|
||||||
|
|
||||||
|
SECTION("Valid") {
|
||||||
|
REQUIRE(isInteger("42") == true);
|
||||||
|
REQUIRE(isInteger("-42") == true);
|
||||||
|
REQUIRE(isInteger("+42") == true);
|
||||||
|
}
|
||||||
|
|
||||||
|
SECTION("ExtraSign") {
|
||||||
|
REQUIRE(isInteger("--42") == false);
|
||||||
|
REQUIRE(isInteger("++42") == false);
|
||||||
|
}
|
||||||
|
}
|
@ -1,76 +0,0 @@
|
|||||||
// ArduinoJson - arduinojson.org
|
|
||||||
// Copyright Benoit Blanchon 2014-2018
|
|
||||||
// MIT License
|
|
||||||
|
|
||||||
#include <ArduinoJson/Numbers/isFloat.hpp>
|
|
||||||
#include <catch.hpp>
|
|
||||||
|
|
||||||
using namespace ArduinoJson::Internals;
|
|
||||||
|
|
||||||
TEST_CASE("isFloat()") {
|
|
||||||
SECTION("Input is NULL") {
|
|
||||||
REQUIRE(isFloat(NULL) == false);
|
|
||||||
}
|
|
||||||
|
|
||||||
SECTION("NoExponent") {
|
|
||||||
REQUIRE(isFloat("3.14"));
|
|
||||||
REQUIRE(isFloat("-3.14"));
|
|
||||||
REQUIRE(isFloat("+3.14"));
|
|
||||||
}
|
|
||||||
|
|
||||||
SECTION("IntegralPartMissing") {
|
|
||||||
REQUIRE(isFloat(".14"));
|
|
||||||
REQUIRE(isFloat("-.14"));
|
|
||||||
REQUIRE(isFloat("+.14"));
|
|
||||||
}
|
|
||||||
|
|
||||||
SECTION("FractionalPartMissing") {
|
|
||||||
REQUIRE(isFloat("3."));
|
|
||||||
REQUIRE(isFloat("-3.e14"));
|
|
||||||
REQUIRE(isFloat("+3.e-14"));
|
|
||||||
}
|
|
||||||
|
|
||||||
SECTION("NoDot") {
|
|
||||||
REQUIRE(isFloat("3e14"));
|
|
||||||
REQUIRE(isFloat("3e-14"));
|
|
||||||
REQUIRE(isFloat("3e+14"));
|
|
||||||
}
|
|
||||||
|
|
||||||
SECTION("Integer") {
|
|
||||||
REQUIRE(isFloat("14"));
|
|
||||||
REQUIRE(isFloat("-14"));
|
|
||||||
REQUIRE(isFloat("+14"));
|
|
||||||
}
|
|
||||||
|
|
||||||
SECTION("ExponentMissing") {
|
|
||||||
REQUIRE_FALSE(isFloat("3.14e"));
|
|
||||||
REQUIRE_FALSE(isFloat("3.14e-"));
|
|
||||||
REQUIRE_FALSE(isFloat("3.14e+"));
|
|
||||||
}
|
|
||||||
|
|
||||||
SECTION("JustASign") {
|
|
||||||
REQUIRE_FALSE(isFloat("-"));
|
|
||||||
REQUIRE_FALSE(isFloat("+"));
|
|
||||||
}
|
|
||||||
|
|
||||||
SECTION("Empty") {
|
|
||||||
REQUIRE_FALSE(isFloat(""));
|
|
||||||
}
|
|
||||||
|
|
||||||
SECTION("NaN") {
|
|
||||||
REQUIRE(isFloat("NaN"));
|
|
||||||
REQUIRE_FALSE(isFloat("n"));
|
|
||||||
REQUIRE_FALSE(isFloat("N"));
|
|
||||||
REQUIRE_FALSE(isFloat("nan"));
|
|
||||||
REQUIRE_FALSE(isFloat("-NaN"));
|
|
||||||
REQUIRE_FALSE(isFloat("+NaN"));
|
|
||||||
}
|
|
||||||
|
|
||||||
SECTION("Infinity") {
|
|
||||||
REQUIRE(isFloat("Infinity"));
|
|
||||||
REQUIRE(isFloat("+Infinity"));
|
|
||||||
REQUIRE(isFloat("-Infinity"));
|
|
||||||
REQUIRE_FALSE(isFloat("infinity"));
|
|
||||||
REQUIRE_FALSE(isFloat("Inf"));
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,36 +0,0 @@
|
|||||||
// ArduinoJson - arduinojson.org
|
|
||||||
// Copyright Benoit Blanchon 2014-2018
|
|
||||||
// MIT License
|
|
||||||
|
|
||||||
#include <ArduinoJson/Numbers/isInteger.hpp>
|
|
||||||
#include <catch.hpp>
|
|
||||||
|
|
||||||
using namespace ArduinoJson::Internals;
|
|
||||||
|
|
||||||
TEST_CASE("isInteger()") {
|
|
||||||
SECTION("Null") {
|
|
||||||
REQUIRE_FALSE(isInteger(NULL));
|
|
||||||
}
|
|
||||||
|
|
||||||
SECTION("FloatNotInteger") {
|
|
||||||
REQUIRE_FALSE(isInteger("3.14"));
|
|
||||||
REQUIRE_FALSE(isInteger("-3.14"));
|
|
||||||
REQUIRE_FALSE(isInteger("+3.14"));
|
|
||||||
}
|
|
||||||
|
|
||||||
SECTION("Spaces") {
|
|
||||||
REQUIRE_FALSE(isInteger("42 "));
|
|
||||||
REQUIRE_FALSE(isInteger(" 42"));
|
|
||||||
}
|
|
||||||
|
|
||||||
SECTION("Valid") {
|
|
||||||
REQUIRE(isInteger("42"));
|
|
||||||
REQUIRE(isInteger("-42"));
|
|
||||||
REQUIRE(isInteger("+42"));
|
|
||||||
}
|
|
||||||
|
|
||||||
SECTION("ExtraSign") {
|
|
||||||
REQUIRE_FALSE(isInteger("--42"));
|
|
||||||
REQUIRE_FALSE(isInteger("++42"));
|
|
||||||
}
|
|
||||||
}
|
|
Reference in New Issue
Block a user