rpc: added getaddressbalance method using addressindex

This commit is contained in:
Braydon Fuller 2016-03-17 16:06:08 -04:00 committed by Braydon Fuller
parent 7dbbb79cec
commit 5bb6d69ff8
4 changed files with 80 additions and 17 deletions

View File

@ -44,6 +44,10 @@ class AddressIndexTest(BitcoinTestFramework):
assert_equal(self.nodes[1].getbalance(), 0) assert_equal(self.nodes[1].getbalance(), 0)
assert_equal(self.nodes[2].getbalance(), 0) assert_equal(self.nodes[2].getbalance(), 0)
# Check that balances are correct
balance0 = self.nodes[1].getaddressbalance("2N2JD6wb56AfK4tfmM6PwdVmoYk2dCKf4Br")
assert_equal(balance0['balance'], 0);
# Check p2pkh and p2sh address indexes # Check p2pkh and p2sh address indexes
print "Testing p2pkh and p2sh address index..." print "Testing p2pkh and p2sh address index..."
@ -89,6 +93,10 @@ class AddressIndexTest(BitcoinTestFramework):
assert_equal(multitxids[4], txid2); assert_equal(multitxids[4], txid2);
assert_equal(multitxids[5], txidb2); assert_equal(multitxids[5], txidb2);
# Check that balances are correct
balance0 = self.nodes[1].getaddressbalance("2N2JD6wb56AfK4tfmM6PwdVmoYk2dCKf4Br")
assert_equal(balance0['balance'], 45 * 100000000);
# Check that outputs with the same address will only return one txid # Check that outputs with the same address will only return one txid
print "Testing for txid uniqueness..." print "Testing for txid uniqueness..."
addressHash = "6349a418fc4578d10a372b54b45c280cc8c4382f".decode("hex") addressHash = "6349a418fc4578d10a372b54b45c280cc8c4382f".decode("hex")
@ -109,6 +117,10 @@ class AddressIndexTest(BitcoinTestFramework):
assert_equal(len(txidsmany), 4); assert_equal(len(txidsmany), 4);
assert_equal(txidsmany[3], sent_txid); assert_equal(txidsmany[3], sent_txid);
# Check that balances are correct
balance0 = self.nodes[1].getaddressbalance("2N2JD6wb56AfK4tfmM6PwdVmoYk2dCKf4Br")
assert_equal(balance0['balance'], 45 * 100000000 + 21);
print "Passed\n" print "Passed\n"

View File

@ -397,23 +397,9 @@ UniValue setmocktime(const UniValue& params, bool fHelp)
return NullUniValue; return NullUniValue;
} }
UniValue getaddresstxids(const UniValue& params, bool fHelp) bool getAddressesFromParams(const UniValue& params, std::vector<std::pair<uint160, int> > &addresses)
{ {
if (fHelp || params.size() != 1)
throw runtime_error(
"getaddresstxids\n"
"\nReturns the txids for an address (requires addressindex to be enabled).\n"
"\nResult\n"
"[\n"
" \"transactionid\" (string) The transaction id\n"
" ,...\n"
"]\n"
);
std::vector<std::pair<uint160, int> > addresses;
if (params[0].isStr()) { if (params[0].isStr()) {
CBitcoinAddress address(params[0].get_str()); CBitcoinAddress address(params[0].get_str());
uint160 hashBytes; uint160 hashBytes;
int type = 0; int type = 0;
@ -421,7 +407,6 @@ UniValue getaddresstxids(const UniValue& params, bool fHelp)
throw JSONRPCError(RPC_INVALID_ADDRESS_OR_KEY, "Invalid address"); throw JSONRPCError(RPC_INVALID_ADDRESS_OR_KEY, "Invalid address");
} }
addresses.push_back(std::make_pair(hashBytes, type)); addresses.push_back(std::make_pair(hashBytes, type));
} else if (params[0].isObject()) { } else if (params[0].isObject()) {
UniValue addressValues = find_value(params[0].get_obj(), "addresses"); UniValue addressValues = find_value(params[0].get_obj(), "addresses");
@ -445,9 +430,73 @@ UniValue getaddresstxids(const UniValue& params, bool fHelp)
throw JSONRPCError(RPC_INVALID_ADDRESS_OR_KEY, "Invalid address"); throw JSONRPCError(RPC_INVALID_ADDRESS_OR_KEY, "Invalid address");
} }
return true;
}
UniValue getaddressbalance(const UniValue& params, bool fHelp)
{
if (fHelp || params.size() != 1)
throw runtime_error(
"getaddressbalance\n"
"\nReturns the balance for an address (requires addressindex to be enabled).\n"
"\nResult\n"
"{\n"
" \"balance\" (string) The current balance\n"
" ,...\n"
"}\n"
);
std::vector<std::pair<uint160, int> > addresses;
if (!getAddressesFromParams(params, addresses)) {
throw JSONRPCError(RPC_INVALID_ADDRESS_OR_KEY, "Invalid address");
}
std::vector<std::pair<CAddressIndexKey, CAmount> > addressIndex; std::vector<std::pair<CAddressIndexKey, CAmount> > addressIndex;
for (std::vector<std::pair<uint160, int> >::iterator it = addresses.begin(); it != addresses.end(); ++it) { for (std::vector<std::pair<uint160, int> >::iterator it = addresses.begin(); it != addresses.end(); it++) {
if (!GetAddressIndex((*it).first, (*it).second, addressIndex)) {
throw JSONRPCError(RPC_INVALID_ADDRESS_OR_KEY, "No information available for address");
}
}
CAmount balance = 0;
for (std::vector<std::pair<CAddressIndexKey, CAmount> >::const_iterator it=addressIndex.begin(); it!=addressIndex.end(); it++) {
balance += it->second;
}
UniValue result(UniValue::VOBJ);
result.push_back(Pair("balance", balance));
return result;
}
UniValue getaddresstxids(const UniValue& params, bool fHelp)
{
if (fHelp || params.size() != 1)
throw runtime_error(
"getaddresstxids\n"
"\nReturns the txids for an address (requires addressindex to be enabled).\n"
"\nResult\n"
"[\n"
" \"transactionid\" (string) The transaction id\n"
" ,...\n"
"]\n"
);
std::vector<std::pair<uint160, int> > addresses;
if (!getAddressesFromParams(params, addresses)) {
throw JSONRPCError(RPC_INVALID_ADDRESS_OR_KEY, "Invalid address");
}
std::vector<std::pair<CAddressIndexKey, CAmount> > addressIndex;
for (std::vector<std::pair<uint160, int> >::iterator it = addresses.begin(); it != addresses.end(); it++) {
if (!GetAddressIndex((*it).first, (*it).second, addressIndex)) { if (!GetAddressIndex((*it).first, (*it).second, addressIndex)) {
throw JSONRPCError(RPC_INVALID_ADDRESS_OR_KEY, "No information available for address"); throw JSONRPCError(RPC_INVALID_ADDRESS_OR_KEY, "No information available for address");
} }

View File

@ -315,6 +315,7 @@ static const CRPCCommand vRPCCommands[] =
/* Address index */ /* Address index */
{ "addressindex", "getaddresstxids", &getaddresstxids, false }, { "addressindex", "getaddresstxids", &getaddresstxids, false },
{ "addressindex", "getaddressbalance", &getaddressbalance, false },
/* Utility functions */ /* Utility functions */
{ "util", "createmultisig", &createmultisig, true }, { "util", "createmultisig", &createmultisig, true },

View File

@ -167,6 +167,7 @@ extern void EnsureWalletIsUnlocked();
extern UniValue getconnectioncount(const UniValue& params, bool fHelp); // in rpcnet.cpp extern UniValue getconnectioncount(const UniValue& params, bool fHelp); // in rpcnet.cpp
extern UniValue getaddresstxids(const UniValue& params, bool fHelp); extern UniValue getaddresstxids(const UniValue& params, bool fHelp);
extern UniValue getaddressbalance(const UniValue& params, bool fHelp);
extern UniValue getpeerinfo(const UniValue& params, bool fHelp); extern UniValue getpeerinfo(const UniValue& params, bool fHelp);
extern UniValue ping(const UniValue& params, bool fHelp); extern UniValue ping(const UniValue& params, bool fHelp);