template <>
struct DynamicConverter<std::string> {
static std::string convert(const dynamic& d) {
- return d.asString().toStdString();
+ return d.asString();
}
};
//////////////////////////////////////////////////////////////////////
-fbstring codePointToUtf8(char32_t cp) {
- fbstring result;
+std::string codePointToUtf8(char32_t cp) {
+ std::string result;
// Based on description from http://en.wikipedia.org/wiki/UTF-8.
#pragma once
-#include <folly/FBString.h>
+#include <string>
namespace folly {
*
* Return value is undefined if `cp' is an invalid code point.
*/
-fbstring codePointToUtf8(char32_t cp);
+std::string codePointToUtf8(char32_t cp);
//////////////////////////////////////////////////////////////////////
// This is a higher-order preprocessor macro to aid going from runtime
// types to the compile time type system.
-#define FB_DYNAMIC_APPLY(type, apply) do { \
- switch ((type)) { \
- case NULLT: apply(void*); break; \
- case ARRAY: apply(Array); break; \
- case BOOL: apply(bool); break; \
- case DOUBLE: apply(double); break; \
- case INT64: apply(int64_t); break; \
- case OBJECT: apply(ObjectImpl); break; \
- case STRING: apply(fbstring); break; \
- default: CHECK(0); abort(); \
- } \
-} while (0)
+#define FB_DYNAMIC_APPLY(type, apply) \
+ do { \
+ switch ((type)) { \
+ case NULLT: \
+ apply(void*); \
+ break; \
+ case ARRAY: \
+ apply(Array); \
+ break; \
+ case BOOL: \
+ apply(bool); \
+ break; \
+ case DOUBLE: \
+ apply(double); \
+ break; \
+ case INT64: \
+ apply(int64_t); \
+ break; \
+ case OBJECT: \
+ apply(ObjectImpl); \
+ break; \
+ case STRING: \
+ apply(std::string); \
+ break; \
+ default: \
+ CHECK(0); \
+ abort(); \
+ } \
+ } while (0)
//////////////////////////////////////////////////////////////////////
inline dynamic::dynamic(StringPiece s)
: type_(STRING)
{
- new (&u_.string) fbstring(s.data(), s.size());
+ new (&u_.string) std::string(s.data(), s.size());
}
inline dynamic::dynamic(char const* s)
: type_(STRING)
{
- new (&u_.string) fbstring(s);
+ new (&u_.string) std::string(s);
}
inline dynamic::dynamic(std::string const& s)
: type_(STRING)
{
- new (&u_.string) fbstring(s);
+ new (&u_.string) std::string(s);
}
-inline dynamic::dynamic(fbstring const& s)
- : type_(STRING)
-{
- new (&u_.string) fbstring(s);
-}
-
-inline dynamic::dynamic(fbstring&& s)
- : type_(STRING)
-{
- new (&u_.string) fbstring(std::move(s));
+inline dynamic::dynamic(std::string&& s) : type_(STRING) {
+ new (&u_.string) std::string(std::move(s));
}
inline dynamic::dynamic(std::initializer_list<dynamic> il)
return &(get<ObjectImpl>());
}
-inline bool dynamic::isString() const { return get_nothrow<fbstring>(); }
+inline bool dynamic::isString() const {
+ return get_nothrow<std::string>();
+}
inline bool dynamic::isObject() const { return get_nothrow<ObjectImpl>(); }
inline bool dynamic::isBool() const { return get_nothrow<bool>(); }
inline bool dynamic::isArray() const { return get_nothrow<Array>(); }
return type_;
}
-inline fbstring dynamic::asString() const { return asImpl<fbstring>(); }
-inline double dynamic::asDouble() const { return asImpl<double>(); }
-inline int64_t dynamic::asInt() const { return asImpl<int64_t>(); }
-inline bool dynamic::asBool() const { return asImpl<bool>(); }
+inline std::string dynamic::asString() const {
+ return asImpl<std::string>();
+}
+inline double dynamic::asDouble() const {
+ return asImpl<double>();
+}
+inline int64_t dynamic::asInt() const {
+ return asImpl<int64_t>();
+}
+inline bool dynamic::asBool() const {
+ return asImpl<bool>();
+}
-inline const fbstring& dynamic::getString() const& { return get<fbstring>(); }
+inline const std::string& dynamic::getString() const& {
+ return get<std::string>();
+}
inline double dynamic::getDouble() const& { return get<double>(); }
inline int64_t dynamic::getInt() const& { return get<int64_t>(); }
inline bool dynamic::getBool() const& { return get<bool>(); }
-inline fbstring& dynamic::getString() & { return get<fbstring>(); }
+inline std::string& dynamic::getString()& {
+ return get<std::string>();
+}
inline double& dynamic::getDouble() & { return get<double>(); }
inline int64_t& dynamic::getInt() & { return get<int64_t>(); }
inline bool& dynamic::getBool() & { return get<bool>(); }
-inline fbstring dynamic::getString() && { return std::move(get<fbstring>()); }
+inline std::string dynamic::getString()&& {
+ return std::move(get<std::string>());
+}
inline double dynamic::getDouble() && { return get<double>(); }
inline int64_t dynamic::getInt() && { return get<int64_t>(); }
inline bool dynamic::getBool() && { return get<bool>(); }
-inline const char* dynamic::data() const& { return get<fbstring>().data(); }
-inline const char* dynamic::c_str() const& { return get<fbstring>().c_str(); }
-inline StringPiece dynamic::stringPiece() const { return get<fbstring>(); }
+inline const char* dynamic::data() const& {
+ return get<std::string>().data();
+}
+inline const char* dynamic::c_str() const& {
+ return get<std::string>().c_str();
+}
+inline StringPiece dynamic::stringPiece() const {
+ return get<std::string>();
+}
template<class T>
struct dynamic::CompareOp {
inline dynamic& dynamic::operator+=(dynamic const& o) {
if (type() == STRING && o.type() == STRING) {
- *getAddress<fbstring>() += *o.getAddress<fbstring>();
+ *getAddress<std::string>() += *o.getAddress<std::string>();
return *this;
}
*this = detail::numericOp<std::plus>(*this, o);
FOLLY_DYNAMIC_DEC_TYPEINFO(void*, "null", dynamic::NULLT)
FOLLY_DYNAMIC_DEC_TYPEINFO(bool, "boolean", dynamic::BOOL)
-FOLLY_DYNAMIC_DEC_TYPEINFO(fbstring, "string", dynamic::STRING)
+FOLLY_DYNAMIC_DEC_TYPEINFO(std::string, "string", dynamic::STRING)
FOLLY_DYNAMIC_DEC_TYPEINFO(dynamic::Array, "array", dynamic::ARRAY)
FOLLY_DYNAMIC_DEC_TYPEINFO(double, "double", dynamic::DOUBLE)
FOLLY_DYNAMIC_DEC_TYPEINFO(int64_t, "int64", dynamic::INT64)
case INT64: return to<T>(*get_nothrow<int64_t>());
case DOUBLE: return to<T>(*get_nothrow<double>());
case BOOL: return to<T>(*get_nothrow<bool>());
- case STRING: return to<T>(*get_nothrow<fbstring>());
+ case STRING:
+ return to<T>(*get_nothrow<std::string>());
default:
throw TypeError("int/double/bool/string", type());
}
template<> struct dynamic::GetAddrImpl<double> {
static double* get(Data& d) noexcept { return &d.doubl; }
};
-template<> struct dynamic::GetAddrImpl<fbstring> {
- static fbstring* get(Data& d) noexcept { return &d.string; }
+template <>
+struct dynamic::GetAddrImpl<std::string> {
+ static std::string* get(Data& d) noexcept {
+ return &d.string;
+ }
};
template<> struct dynamic::GetAddrImpl<dynamic::ObjectImpl> {
static_assert(sizeof(ObjectImpl) <= sizeof(Data::objectBuffer),
FormatValue<int64_t>(val_.asInt()).format(arg, cb);
break;
case dynamic::STRING:
- FormatValue<fbstring>(val_.asString()).format(arg, cb);
+ FormatValue<std::string>(val_.asString()).format(arg, cb);
break;
case dynamic::DOUBLE:
FormatValue<double>(val_.asDouble()).format(arg, cb);
FormatValue(val_.at(arg.splitIntKey())).format(arg, cb);
break;
case dynamic::OBJECT:
- FormatValue(val_.at(arg.splitKey().toFbstring())).format(arg, cb);
+ FormatValue(val_.at(arg.splitKey().toString())).format(arg, cb);
break;
}
}
*/
#include <folly/dynamic.h>
+#include <folly/Hash.h>
namespace folly {
FOLLY_DYNAMIC_DEF_TYPEINFO(void*)
FOLLY_DYNAMIC_DEF_TYPEINFO(bool)
-FOLLY_DYNAMIC_DEF_TYPEINFO(fbstring)
+FOLLY_DYNAMIC_DEF_TYPEINFO(std::string)
FOLLY_DYNAMIC_DEF_TYPEINFO(dynamic::Array)
FOLLY_DYNAMIC_DEF_TYPEINFO(double)
FOLLY_DYNAMIC_DEF_TYPEINFO(int64_t)
// This is a higher-order preprocessor macro to aid going from runtime
// types to the compile time type system.
-#define FB_DYNAMIC_APPLY(type, apply) do { \
- switch ((type)) { \
- case NULLT: apply(void*); break; \
- case ARRAY: apply(Array); break; \
- case BOOL: apply(bool); break; \
- case DOUBLE: apply(double); break; \
- case INT64: apply(int64_t); break; \
- case OBJECT: apply(ObjectImpl); break; \
- case STRING: apply(fbstring); break; \
- default: CHECK(0); abort(); \
- } \
-} while (0)
+#define FB_DYNAMIC_APPLY(type, apply) \
+ do { \
+ switch ((type)) { \
+ case NULLT: \
+ apply(void*); \
+ break; \
+ case ARRAY: \
+ apply(Array); \
+ break; \
+ case BOOL: \
+ apply(bool); \
+ break; \
+ case DOUBLE: \
+ apply(double); \
+ break; \
+ case INT64: \
+ apply(int64_t); \
+ break; \
+ case OBJECT: \
+ apply(ObjectImpl); \
+ break; \
+ case STRING: \
+ apply(std::string); \
+ break; \
+ default: \
+ CHECK(0); \
+ abort(); \
+ } \
+ } while (0)
bool dynamic::operator<(dynamic const& o) const {
if (UNLIKELY(type_ == OBJECT || o.type_ == OBJECT)) {
if (auto* obj = get_nothrow<ObjectImpl>()) {
return obj->size();
}
- if (auto* str = get_nothrow<fbstring>()) {
+ if (auto* str = get_nothrow<std::string>()) {
return str->size();
}
throw TypeError("array/object", type());
case NULLT:
throw TypeError("not null/object/array", type());
case INT64:
- return std::hash<int64_t>()(asInt());
+ return std::hash<int64_t>()(getInt());
case DOUBLE:
- return std::hash<double>()(asDouble());
+ return std::hash<double>()(getDouble());
case BOOL:
- return std::hash<bool>()(asBool());
- case STRING:
- return std::hash<fbstring>()(asString());
+ return std::hash<bool>()(getBool());
+ case STRING: {
+ // keep it compatible with FBString
+ const auto& str = getString();
+ return ::folly::hash::fnv32_buf(str.data(), str.size());
+ }
default:
CHECK(0); abort();
}
#include <boost/operators.hpp>
-#include <folly/FBString.h>
#include <folly/Range.h>
#include <folly/Traits.h>
/* implicit */ dynamic(StringPiece val);
/* implicit */ dynamic(char const* val);
/* implicit */ dynamic(std::string const& val);
- /* implicit */ dynamic(fbstring const& val);
- /* implicit */ dynamic(fbstring&& val);
+ /* implicit */ dynamic(std::string&& val);
/*
* This is part of the plumbing for array() and object(), above.
* since arrays and objects are generally best dealt with as a
* dynamic.
*/
- fbstring asString() const;
+ std::string asString() const;
double asDouble() const;
int64_t asInt() const;
bool asBool() const;
*
* These will throw a TypeError if the dynamic has a different type.
*/
- const fbstring& getString() const&;
+ const std::string& getString() const&;
double getDouble() const&;
int64_t getInt() const&;
bool getBool() const&;
- fbstring& getString() &;
+ std::string& getString() &;
double& getDouble() &;
int64_t& getInt() &;
bool& getBool() &;
- fbstring getString() &&;
+ std::string getString() &&;
double getDouble() &&;
int64_t getInt() &&;
bool getBool() &&;
bool boolean;
double doubl;
int64_t integer;
- fbstring string;
+ std::string string;
/*
* Objects are placement new'd here. We have to use a char buffer
// std::string
template <typename Fn> EnableForArgTypes<Fn, std::string>
invokeForKeyValue(Fn fn, const folly::dynamic&, const folly::dynamic& v) {
- fn(v.asString().toStdString());
+ fn(v.asString());
}
//
// folly::dynamic, std::string
template <typename Fn> EnableForArgTypes<Fn, folly::dynamic, std::string>
invokeForKeyValue(Fn fn, const folly::dynamic& k, const folly::dynamic& v) {
- fn(k, v.asString().toStdString());
+ fn(k, v.asString());
}
// Convert the key to std::string.
// std::string, folly::dynamic (no conversion of value)
template <typename Fn> EnableForArgTypes<Fn, std::string, folly::dynamic>
invokeForKeyValue(Fn fn, const folly::dynamic& k, const folly::dynamic& v) {
- fn(k.asString().toStdString(), v);
+ fn(k.asString(), v);
}
// std::string, int64_t
template <typename Fn> EnableForArgTypes<Fn, std::string, int64_t>
invokeForKeyValue(Fn fn, const folly::dynamic& k, const folly::dynamic& v) {
- fn(k.asString().toStdString(), v.asInt());
+ fn(k.asString(), v.asInt());
}
// std::string, bool
template <typename Fn> EnableForArgTypes<Fn, std::string, bool>
invokeForKeyValue(Fn fn, const folly::dynamic& k, const folly::dynamic& v) {
- fn(k.asString().toStdString(), v.asBool());
+ fn(k.asString(), v.asBool());
}
// std::string, double
template <typename Fn> EnableForArgTypes<Fn, std::string, double>
invokeForKeyValue(Fn fn, const folly::dynamic& k, const folly::dynamic& v) {
- fn(k.asString().toStdString(), v.asDouble());
+ fn(k.asString(), v.asDouble());
}
// std::string, std::string
template <typename Fn> EnableForArgTypes<Fn, std::string, std::string>
invokeForKeyValue(Fn fn, const folly::dynamic& k, const folly::dynamic& v) {
- fn(k.asString().toStdString(), v.asString().toStdString());
+ fn(k.asString(), v.asString());
}
// Convert the key to int64_t (good for arrays).
// int64_t, std::string
template <typename Fn> EnableForArgTypes<Fn, int64_t, std::string>
invokeForKeyValue(Fn fn, const folly::dynamic& k, const folly::dynamic& v) {
- fn(k.asInt(), v.asString().toStdString());
+ fn(k.asInt(), v.asString());
}
} // namespace detail
* NB: The key alone should be rarely needed, but these callback styles
* provide it with no conversion overhead, and only minimal verbosity:
* [&](const std::string& k, const folly::dynamic&) {}
- * [&]() { auto k = p.key().asString().toStdString(); }
+ * [&]() { auto k = p.key().asString(); }
*
* == How `releaseErrors()` can make your parse lossless ==
*
explicit SchemaValidatorContext(const dynamic& s) : schema(s) {}
const dynamic& schema;
- std::unordered_map<fbstring, IValidator*> refs;
+ std::unordered_map<std::string, IValidator*> refs;
};
/**
struct StringPatternValidator final : IValidator {
explicit StringPatternValidator(const dynamic& schema) {
if (schema.isString()) {
- regex_ = boost::regex(schema.getString().toStdString());
+ regex_ = boost::regex(schema.getString());
}
}
if (!value.isString() || regex_.empty()) {
return none;
}
- if (!boost::regex_search(value.getString().toStdString(), regex_)) {
+ if (!boost::regex_search(value.getString(), regex_)) {
return makeError("string matching regex", value);
}
return none;
}
private:
- std::vector<fbstring> properties_;
+ std::vector<std::string> properties_;
};
struct PropertiesValidator final : IValidator {
for (const auto& pair : patternProperties->items()) {
if (pair.first.isString()) {
patternPropertyValidators_.emplace_back(
- boost::regex(pair.first.getString().toStdString()),
+ boost::regex(pair.first.getString()),
SchemaValidator::make(context, pair.second));
}
}
if (!pair.first.isString()) {
continue;
}
- const fbstring& key = pair.first.getString();
+ const std::string& key = pair.first.getString();
auto it = propertyValidators_.find(key);
bool matched = false;
if (it != propertyValidators_.end()) {
matched = true;
}
- const std::string& strkey = key.toStdString();
+ const std::string& strkey = key;
for (const auto& ppv : patternPropertyValidators_) {
if (boost::regex_search(strkey, ppv.first)) {
if (auto se = vc.validate(ppv.second.get(), pair.second)) {
return none;
}
- std::unordered_map<fbstring, std::unique_ptr<IValidator>> propertyValidators_;
+ std::unordered_map<std::string, std::unique_ptr<IValidator>>
+ propertyValidators_;
std::vector<std::pair<boost::regex, std::unique_ptr<IValidator>>>
patternPropertyValidators_;
std::unique_ptr<IValidator> additionalPropertyValidator_;
continue;
}
if (pair.second.isArray()) {
- auto p = make_pair(pair.first.getString(), std::vector<fbstring>());
+ auto p = make_pair(pair.first.getString(), std::vector<std::string>());
for (const auto& item : pair.second) {
if (item.isString()) {
p.second.push_back(item.getString());
return none;
}
- std::vector<std::pair<fbstring, std::vector<fbstring>>> propertyDep_;
- std::vector<std::pair<fbstring, std::unique_ptr<IValidator>>> schemaDep_;
+ std::vector<std::pair<std::string, std::vector<std::string>>> propertyDep_;
+ std::vector<std::pair<std::string, std::unique_ptr<IValidator>>> schemaDep_;
};
struct EnumValidator final : IValidator {
using Base::at;
using Base::find;
+ using Base::count;
template <class... Args>
std::pair<iterator, bool> emplace(StringPiece key, Args&&... args) {
}
}
-static fbstring decodeString(Cursor& curs) {
+static std::string decodeString(Cursor& curs) {
auto len = decodeInt(curs);
- folly::fbstring str;
+ std::string str;
if (len < 0) {
throw std::range_error("string length must not be negative");
}
struct Printer {
- explicit Printer(fbstring& out,
- unsigned* indentLevel,
- serialization_opts const* opts)
- : out_(out)
- , indentLevel_(indentLevel)
- , opts_(*opts)
- {}
+ explicit Printer(
+ std::string& out,
+ unsigned* indentLevel,
+ serialization_opts const* opts)
+ : out_(out), indentLevel_(indentLevel), opts_(*opts) {}
void operator()(dynamic const& v) const {
switch (v.type()) {
void newline() const {
if (indentLevel_) {
- out_ += to<fbstring>('\n', fbstring(*indentLevel_ * 2, ' '));
+ out_ += to<std::string>('\n', std::string(*indentLevel_ * 2, ' '));
}
}
}
private:
- fbstring& out_;
- unsigned* const indentLevel_;
- serialization_opts const& opts_;
+ std::string& out_;
+ unsigned* const indentLevel_;
+ serialization_opts const& opts_;
};
//////////////////////////////////////////////////////////////////////
};
dynamic parseValue(Input& in);
-fbstring parseString(Input& in);
+std::string parseString(Input& in);
dynamic parseNumber(Input& in);
dynamic parseObject(Input& in) {
return val;
}
-fbstring decodeUnicodeEscape(Input& in) {
+std::string decodeUnicodeEscape(Input& in) {
auto hexVal = [&] (char c) -> unsigned {
return c >= '0' && c <= '9' ? c - '0' :
c >= 'a' && c <= 'f' ? c - 'a' + 10 :
return codePointToUtf8(codePoint);
}
-fbstring parseString(Input& in) {
+std::string parseString(Input& in) {
assert(*in == '\"');
++in;
- fbstring ret;
+ std::string ret;
for (;;) {
auto range = in.skipWhile(
[] (char c) { return c != '\"' && c != '\\'; }
case 'r': ret.push_back('\r'); ++in; break;
case 't': ret.push_back('\t'); ++in; break;
case 'u': ++in; ret += decodeUnicodeEscape(in); break;
- default: in.error(to<fbstring>("unknown escape ", *in,
- " in string").c_str());
+ default:
+ in.error(to<std::string>("unknown escape ", *in, " in string").c_str());
}
continue;
}
//////////////////////////////////////////////////////////////////////
-fbstring serialize(dynamic const& dyn, serialization_opts const& opts) {
- fbstring ret;
+std::string serialize(dynamic const& dyn, serialization_opts const& opts) {
+ std::string ret;
unsigned indentLevel = 0;
Printer p(ret, opts.pretty_formatting ? &indentLevel : nullptr, &opts);
p(dyn);
}
// Escape a string so that it is legal to print it in JSON text.
-void escapeString(StringPiece input,
- fbstring& out,
- const serialization_opts& opts) {
+void escapeString(
+ StringPiece input,
+ std::string& out,
+ const serialization_opts& opts) {
auto hexDigit = [] (int c) -> char {
return c < 10 ? c + '0' : c - 10 + 'a';
};
out.push_back('\"');
}
-fbstring stripComments(StringPiece jsonC) {
- fbstring result;
+std::string stripComments(StringPiece jsonC) {
+ std::string result;
enum class State {
None,
InString,
return ret;
}
-fbstring toJson(dynamic const& dyn) {
+std::string toJson(dynamic const& dyn) {
return json::serialize(dyn, json::serialization_opts());
}
-fbstring toPrettyJson(dynamic const& dyn) {
+std::string toPrettyJson(dynamic const& dyn) {
json::serialization_opts opts;
opts.pretty_formatting = true;
return json::serialize(dyn, opts);
#pragma once
#include <iosfwd>
+#include <string>
#include <folly/dynamic.h>
-#include <folly/FBString.h>
#include <folly/Range.h>
namespace folly {
* For the most common use cases there are simpler functions in the
* main folly namespace below.
*/
- fbstring serialize(dynamic const&, serialization_opts const&);
+ std::string serialize(dynamic const&, serialization_opts const&);
/*
* Escape a string so that it is legal to print it in JSON text and
* append the result to out.
*/
- void escapeString(StringPiece input,
- fbstring& out,
- const serialization_opts& opts);
+ void escapeString(
+ StringPiece input,
+ std::string& out,
+ const serialization_opts& opts);
/*
* Strip all C99-like comments (i.e. // and / * ... * /)
*/
- fbstring stripComments(StringPiece jsonC);
+ std::string stripComments(StringPiece jsonC);
}
//////////////////////////////////////////////////////////////////////
/*
* Serialize a dynamic into a json string.
*/
-fbstring toJson(dynamic const&);
+std::string toJson(dynamic const&);
/*
* Same as the above, except format the json with some minimal
* indentation.
*/
-fbstring toPrettyJson(dynamic const&);
+std::string toPrettyJson(dynamic const&);
/*
* Printer for GTest.
EXPECT_EQ(*newObject.keys().begin(), newObject.items().begin()->first);
EXPECT_EQ(*newObject.values().begin(), newObject.items().begin()->second);
- std::vector<std::pair<folly::fbstring, dynamic>> found;
+ std::vector<std::pair<std::string, dynamic>> found;
found.emplace_back(newObject.keys().begin()->asString(),
*newObject.values().begin());
}
}
-folly::fbstring make_long_string() {
- return folly::fbstring(100, 'a');
+std::string make_long_string() {
+ return std::string(100, 'a');
}
TEST(Dynamic, GetDefault) {
TEST(Json, JavascriptSafe) {
auto badDouble = (1ll << 63ll) + 1;
dynamic badDyn = badDouble;
- EXPECT_EQ(folly::toJson(badDouble), folly::to<folly::fbstring>(badDouble));
+ EXPECT_EQ(folly::toJson(badDouble), folly::to<std::string>(badDouble));
folly::json::serialization_opts opts;
opts.javascript_safe = true;
EXPECT_ANY_THROW(folly::json::serialize(badDouble, opts));
auto okDouble = 1ll << 63ll;
dynamic okDyn = okDouble;
- EXPECT_EQ(folly::toJson(okDouble), folly::to<folly::fbstring>(okDouble));
+ EXPECT_EQ(folly::toJson(okDouble), folly::to<std::string>(okDouble));
}
TEST(Json, Produce) {
// Check Infinity/Nan
folly::json::serialization_opts opts;
opts.allow_nan_inf = true;
- EXPECT_EQ("Infinity",
- folly::json::serialize(parseJson("Infinity"), opts).toStdString());
- EXPECT_EQ("NaN",
- folly::json::serialize(parseJson("NaN"), opts).toStdString());
+ EXPECT_EQ("Infinity", folly::json::serialize(parseJson("Infinity"), opts));
+ EXPECT_EQ("NaN", folly::json::serialize(parseJson("NaN"), opts));
}
TEST(Json, JsonEscape) {
TEST(Json, UTF8Retention) {
// test retention with valid utf8 strings
- folly::fbstring input = "\u2665";
- folly::fbstring jsonInput = folly::toJson(input);
- folly::fbstring output = folly::parseJson(jsonInput).asString();
- folly::fbstring jsonOutput = folly::toJson(output);
+ std::string input = "\u2665";
+ std::string jsonInput = folly::toJson(input);
+ std::string output = folly::parseJson(jsonInput).asString();
+ std::string jsonOutput = folly::toJson(output);
EXPECT_EQ(input, output);
EXPECT_EQ(jsonInput, jsonOutput);
opts.encode_non_ascii = true;
// test encode_non_ascii valid utf8 strings
- folly::fbstring input = "\u2665";
- folly::fbstring jsonInput = folly::json::serialize(input, opts);
- folly::fbstring output = folly::parseJson(jsonInput).asString();
- folly::fbstring jsonOutput = folly::json::serialize(output, opts);
+ std::string input = "\u2665";
+ std::string jsonInput = folly::json::serialize(input, opts);
+ std::string output = folly::parseJson(jsonInput).asString();
+ std::string jsonOutput = folly::json::serialize(output, opts);
EXPECT_EQ(input, output);
EXPECT_EQ(jsonInput, jsonOutput);
TEST(Json, ParseNumbersAsStrings) {
folly::json::serialization_opts opts;
opts.parse_numbers_as_strings = true;
- auto parse = [&](folly::fbstring number) {
+ auto parse = [&](std::string number) {
return parseJson(number, opts).asString();
};