Avoid treating null RPC arguments different from missing arguments

This changes RPC methods to treat null arguments the same as missing arguments,
instead of throwing type errors. Specifically:

- `getbalance` method now returns the wallet balance when the `account` param
  is null instead of throwing a type error (same as when parameter is missing).
  It is still an error to supply `minconf` or `watchonly` options when the
  account is null.

- `addnode` and `setban` methods now return help text instead of type errors if
  `command` params are null (same as when params are missing).

- `sendrawtransaction`, `setaccount`, `movecmd`, `sendfrom`,
  `addmultisigaddress`, `listaccounts`, `lockunspent` methods accept null
  default values where missing values were previously allowed, and treat them
  the same.
This commit is contained in:
Russell Yanofsky 2017-08-14 19:44:02 -04:00
parent e666efcdba
commit e067673f4e
3 changed files with 15 additions and 16 deletions

View file

@ -193,7 +193,7 @@ UniValue getpeerinfo(const JSONRPCRequest& request)
UniValue addnode(const JSONRPCRequest& request)
{
std::string strCommand;
if (request.params.size() == 2)
if (!request.params[1].isNull())
strCommand = request.params[1].get_str();
if (request.fHelp || request.params.size() != 2 ||
(strCommand != "onetry" && strCommand != "add" && strCommand != "remove"))
@ -490,7 +490,7 @@ UniValue getnetworkinfo(const JSONRPCRequest& request)
UniValue setban(const JSONRPCRequest& request)
{
std::string strCommand;
if (request.params.size() >= 2)
if (!request.params[1].isNull())
strCommand = request.params[1].get_str();
if (request.fHelp || request.params.size() < 2 ||
(strCommand != "add" && strCommand != "remove"))

View file

@ -922,7 +922,7 @@ UniValue sendrawtransaction(const JSONRPCRequest& request)
const uint256& hashTx = tx->GetHash();
CAmount nMaxRawTxFee = maxTxFee;
if (request.params.size() > 1 && request.params[1].get_bool())
if (!request.params[1].isNull() && request.params[1].get_bool())
nMaxRawTxFee = 0;
CCoinsViewCache &view = *pcoinsTip;

View file

@ -280,7 +280,7 @@ UniValue setaccount(const JSONRPCRequest& request)
throw JSONRPCError(RPC_INVALID_ADDRESS_OR_KEY, "Invalid Bitcoin address");
std::string strAccount;
if (request.params.size() > 1)
if (!request.params[1].isNull())
strAccount = AccountFromValue(request.params[1]);
// Only add the account if the address is yours.
@ -768,7 +768,7 @@ UniValue getbalance(const JSONRPCRequest& request)
LOCK2(cs_main, pwallet->cs_wallet);
if (request.params.size() == 0)
if (request.params[0].isNull() && request.params[1].isNull() && request.params[2].isNull())
return ValueFromAmount(pwallet->GetBalance());
const std::string& account_param = request.params[0].get_str();
@ -838,11 +838,11 @@ UniValue movecmd(const JSONRPCRequest& request)
CAmount nAmount = AmountFromValue(request.params[2]);
if (nAmount <= 0)
throw JSONRPCError(RPC_TYPE_ERROR, "Invalid amount for send");
if (request.params.size() > 3)
if (!request.params[3].isNull())
// unused parameter, used to be nMinDepth, keep type-checking it though
(void)request.params[3].get_int();
std::string strComment;
if (request.params.size() > 4)
if (!request.params[4].isNull())
strComment = request.params[4].get_str();
if (!pwallet->AccountMove(strFrom, strTo, nAmount, strComment)) {
@ -899,7 +899,7 @@ UniValue sendfrom(const JSONRPCRequest& request)
if (nAmount <= 0)
throw JSONRPCError(RPC_TYPE_ERROR, "Invalid amount for send");
int nMinDepth = 1;
if (request.params.size() > 3)
if (!request.params[3].isNull())
nMinDepth = request.params[3].get_int();
CWalletTx wtx;
@ -1105,7 +1105,7 @@ UniValue addmultisigaddress(const JSONRPCRequest& request)
LOCK2(cs_main, pwallet->cs_wallet);
std::string strAccount;
if (request.params.size() > 2)
if (!request.params[2].isNull())
strAccount = AccountFromValue(request.params[2]);
// Construct using pay-to-script-hash:
@ -1711,10 +1711,10 @@ UniValue listaccounts(const JSONRPCRequest& request)
LOCK2(cs_main, pwallet->cs_wallet);
int nMinDepth = 1;
if (request.params.size() > 0)
if (!request.params[0].isNull())
nMinDepth = request.params[0].get_int();
isminefilter includeWatchonly = ISMINE_SPENDABLE;
if(request.params.size() > 1)
if(!request.params[1].isNull())
if(request.params[1].get_bool())
includeWatchonly = includeWatchonly | ISMINE_WATCH_ONLY;
@ -2361,19 +2361,18 @@ UniValue lockunspent(const JSONRPCRequest& request)
LOCK2(cs_main, pwallet->cs_wallet);
if (request.params.size() == 1)
RPCTypeCheck(request.params, {UniValue::VBOOL});
else
RPCTypeCheck(request.params, {UniValue::VBOOL, UniValue::VARR});
RPCTypeCheckArgument(request.params[0], UniValue::VBOOL);
bool fUnlock = request.params[0].get_bool();
if (request.params.size() == 1) {
if (request.params[1].isNull()) {
if (fUnlock)
pwallet->UnlockAllCoins();
return true;
}
RPCTypeCheckArgument(request.params[1], UniValue::VARR);
UniValue outputs = request.params[1].get_array();
for (unsigned int idx = 0; idx < outputs.size(); idx++) {
const UniValue& output = outputs[idx];