20 #include <ripple/basics/StringUtilities.h>
21 #include <ripple/basics/contract.h>
22 #include <ripple/basics/safe_cast.h>
23 #include <ripple/beast/core/LexicalCast.h>
24 #include <ripple/protocol/ErrorCodes.h>
25 #include <ripple/protocol/LedgerFormats.h>
26 #include <ripple/protocol/SField.h>
27 #include <ripple/protocol/STAccount.h>
28 #include <ripple/protocol/STAmount.h>
29 #include <ripple/protocol/STArray.h>
30 #include <ripple/protocol/STBitString.h>
31 #include <ripple/protocol/STBlob.h>
32 #include <ripple/protocol/STInteger.h>
33 #include <ripple/protocol/STIssue.h>
34 #include <ripple/protocol/STParsedJSON.h>
35 #include <ripple/protocol/STPathSet.h>
36 #include <ripple/protocol/STVector256.h>
37 #include <ripple/protocol/STXChainBridge.h>
38 #include <ripple/protocol/TER.h>
39 #include <ripple/protocol/TxFormats.h>
40 #include <ripple/protocol/UintTypes.h>
41 #include <ripple/protocol/XChainAttestations.h>
42 #include <ripple/protocol/impl/STVar.h>
50 namespace STParsedJSONDetail {
51 template <
typename U,
typename S>
57 Throw<std::runtime_error>(
"Value out of range");
58 return static_cast<U
>(value);
61 template <
typename U1,
typename U2>
67 Throw<std::runtime_error>(
"Value out of range");
68 return static_cast<U1
>(value);
77 return object +
"." + field;
85 "Field '" +
make_name(
object, field) +
"' is not a JSON object.");
106 "Field '" +
make_name(
object, field) +
"' is unknown.");
114 "Field '" +
make_name(
object, field) +
"' is out of range.");
122 "Field '" +
make_name(
object, field) +
"' has bad type.");
130 "Field '" +
make_name(
object, field) +
"' has invalid data.");
144 "Field '" +
make_name(
object, field) +
"' must be a JSON array.");
152 "Field '" +
make_name(
object, field) +
"' must be a string.");
160 "Field '" +
object +
"' exceeds nesting depth limit.");
169 "]' must be an object with a single key/object value.");
177 "Object '" + sField.
getName() +
178 "' contents did not meet requirements for that type.");
187 " is not an object. Arrays may only contain objects.");
210 switch (field.fieldType)
215 constexpr
auto minValue =
217 constexpr
auto maxValue =
223 if (!strValue.
empty() &&
224 ((strValue[0] <
'0') || (strValue[0] >
'9')))
230 if (!ter ||
TERtoInt(*ter) < minValue ||
237 ret = detail::make_stvar<STUInt8>(
243 error =
bad_type(json_name, fieldName);
249 ret = detail::make_stvar<STUInt8>(
251 beast::lexicalCastThrow<std::uint8_t>(strValue));
254 else if (value.
isInt())
256 if (value.
asInt() < minValue || value.
asInt() > maxValue)
262 ret = detail::make_stvar<STUInt8>(
267 if (value.
asUInt() > maxValue)
273 ret = detail::make_stvar<STUInt8>(
278 error =
bad_type(json_name, fieldName);
296 if (!strValue.
empty() &&
297 ((strValue[0] <
'0') || (strValue[0] >
'9')))
301 ret = detail::make_stvar<STUInt16>(
312 ret = detail::make_stvar<STUInt16>(
329 ret = detail::make_stvar<STUInt16>(
331 beast::lexicalCastThrow<std::uint16_t>(strValue));
334 else if (value.
isInt())
336 ret = detail::make_stvar<STUInt16>(
337 field, to_unsigned<std::uint16_t>(value.
asInt()));
341 ret = detail::make_stvar<STUInt16>(
342 field, to_unsigned<std::uint16_t>(value.
asUInt()));
346 error =
bad_type(json_name, fieldName);
363 ret = detail::make_stvar<STUInt32>(
365 beast::lexicalCastThrow<std::uint32_t>(
368 else if (value.
isInt())
370 ret = detail::make_stvar<STUInt32>(
371 field, to_unsigned<std::uint32_t>(value.
asInt()));
375 ret = detail::make_stvar<STUInt32>(
376 field, safe_cast<std::uint32_t>(value.
asUInt()));
380 error =
bad_type(json_name, fieldName);
402 str.data(), str.data() + str.size(), val, 16);
404 if (ec !=
std::errc() || (p != str.data() + str.size()))
405 Throw<std::invalid_argument>(
"invalid data");
407 ret = detail::make_stvar<STUInt64>(field, val);
409 else if (value.
isInt())
411 ret = detail::make_stvar<STUInt64>(
412 field, to_unsigned<std::uint64_t>(value.
asInt()));
416 ret = detail::make_stvar<STUInt64>(
417 field, safe_cast<std::uint64_t>(value.
asUInt()));
421 error =
bad_type(json_name, fieldName);
436 error =
bad_type(json_name, fieldName);
453 ret = detail::make_stvar<STUInt128>(field, num);
460 error =
bad_type(json_name, fieldName);
477 ret = detail::make_stvar<STUInt160>(field, num);
484 error =
bad_type(json_name, fieldName);
501 ret = detail::make_stvar<STUInt256>(field, num);
508 error =
bad_type(json_name, fieldName);
516 ret = detail::make_stvar<STBlob>(
517 field, vBlob->data(), vBlob->size());
521 Throw<std::invalid_argument>(
"invalid data");
560 Throw<std::invalid_argument>(
"invalid data");
563 ret = detail::make_stvar<STVector256>(std::move(tail));
588 if (!value[i].isArrayOrNull())
591 ss << fieldName <<
"[" << i <<
"]";
599 ss << fieldName <<
"[" << i <<
"][" << j <<
"]";
601 json_name +
"." + ss.
str());
617 bool hasCurrency =
false;
624 if (!account.isString())
633 if (!uAccount.
parseHex(account.asString()))
636 parseBase58<AccountID>(account.asString());
683 parseBase58<AccountID>(issuer.
asString());
695 uAccount, uCurrency, uIssuer, hasCurrency);
700 ret = detail::make_stvar<STPathSet>(std::move(tail));
713 error =
bad_type(json_name, fieldName);
721 if (
AccountID account; account.parseHex(strValue))
722 return detail::make_stvar<STAccount>(field, account);
724 if (
auto result = parseBase58<AccountID>(strValue))
725 return detail::make_stvar<STAccount>(field, *result);
741 ret = detail::make_stvar<STIssue>(
issueFromJson(field, value));
750 case STI_XCHAIN_BRIDGE:
753 ret = detail::make_stvar<STXChainBridge>(
764 error =
bad_type(json_name, fieldName);
818 switch (field.fieldType)
822 case STI_TRANSACTION:
823 case STI_LEDGERENTRY:
834 json_name +
"." + fieldName,
841 data.emplace_back(std::move(*ret));
856 json_name +
"." + fieldName,
861 if (!array.has_value())
863 data.emplace_back(std::move(*array));
876 parseLeaf(json_name, fieldName, &inName, value, error);
881 data.emplace_back(std::move(*leaf));
889 data.applyTemplateFromSField(inName);
931 bool const isObjectOrNull(json[i].isObjectOrNull());
932 bool const singleKey(isObjectOrNull ? json[i].size() == 1 :
true);
934 if (!isObjectOrNull || !singleKey)
944 std::string const objectName(json[i].getMemberNames()[0]);
954 Json::Value const objectFields(json[i][objectName]);
957 ss << json_name <<
"."
958 <<
"[" << i <<
"]." << objectName;
961 ss.
str(), objectFields, nameField, depth + 1, error);
964 std::string errMsg = error[
"error_message"].asString();
965 error[
"error_message"] =
966 "Error at '" + ss.
str() +
"'. " + errMsg;
970 if (ret->getFName().fieldType != STI_OBJECT)
972 ss <<
"Field type: " << ret->getFName().fieldType <<
" ";
980 return detail::make_stvar<STArray>(std::move(tail));
997 using namespace STParsedJSONDetail;
1007 using namespace STParsedJSONDetail;
1013 auto p =
dynamic_cast<STArray*
>(&arr->get());
1017 array = std::move(*p);