Improve syntax of submit_multisigned [RIPD-182]

In usage it was determined that the submit_multisigned RPC
command could be improved by moving the Signers array inside the
tx_json in the submitted form of the command.  This has the
advantage that the RPC command is more similar to the native form.
Also the returned JSON looks more like the submitted JSON.
This commit is contained in:
Scott Schurr
2015-09-14 10:25:40 -07:00
committed by Vinnie Falco
parent 434a63fa07
commit 19903674af
2 changed files with 195 additions and 207 deletions

View File

@@ -989,44 +989,35 @@ Json::Value transactionSubmitMultiSigned (
}
}
// Check Signers for valid entries.
STArray signers;
{
// Verify that the Signers field is present and an array.
char const* signersArrayName {sfSigners.getJsonName ().c_str ()};
if (! jvRequest.isMember (signersArrayName))
return RPC::missing_field_error (signersArrayName);
// Verify that the Signers field is present.
if (! stpTrans->isFieldPresent (sfSigners))
return RPC::missing_field_error ("tx_json.Signers");
Json::Value& signersValue (
jvRequest [signersArrayName]);
if (! signersValue.isArray ())
{
std::ostringstream err;
err << "Expected "
<< signersArrayName << " to be an array.";
return RPC::make_param_error (err.str ());
}
// Convert signers into SerializedTypes.
STParsedJSONArray parsedSigners (signersArrayName, signersValue);
if (!parsedSigners.array)
{
Json::Value jvResult;
jvResult ["error"] = parsedSigners.error ["error"];
jvResult ["error_code"] = parsedSigners.error ["error_code"];
jvResult ["error_message"] = parsedSigners.error ["error_message"];
return jvResult;
}
signers = std::move (parsedSigners.array.get());
}
// If the Signers field is present the SField guarantees it to be an array.
// Get a reference to the Signers array so we can verify and sort it.
auto& signers = stpTrans->peekFieldArray (sfSigners);
if (signers.empty ())
return RPC::make_param_error ("Signers array may not be empty.");
return RPC::make_param_error("tx_json.Signers array may not be empty.");
// the Signers array may only contain Signer objects.
if (std::find_if_not(signers.begin(), signers.end(), [](STObject const& obj)
{
return (
// A Signer object always contains these fields and no others.
obj.isFieldPresent (sfAccount) &&
obj.isFieldPresent (sfSigningPubKey) &&
obj.isFieldPresent (sfTxnSignature) &&
obj.getCount() == 3);
}) != signers.end())
{
return RPC::make_param_error (
"Signers array may only contain Signer entries.");
}
// Signers must be sorted by Account.
signers.sort ([] (STObject const& a, STObject const& b)
std::sort (signers.begin(), signers.end(),
[](STObject const& a, STObject const& b)
{
return (a.getAccountID (sfAccount) < b.getAccountID (sfAccount));
});
@@ -1061,9 +1052,6 @@ Json::Value transactionSubmitMultiSigned (
return RPC::make_param_error(err.str ());
}
// Insert signers into the transaction.
stpTrans->setFieldArray (sfSigners, std::move(signers));
// Make sure the SerializedTransaction makes a legitimate Transaction.
std::pair <Json::Value, Transaction::pointer> txn =
transactionConstructImpl (stpTrans, app);