diff --git a/src/node/coinstats.h b/src/node/coinstats.h --- a/src/node/coinstats.h +++ b/src/node/coinstats.h @@ -39,7 +39,10 @@ //! The number of coins contained. uint64_t coins_count{0}; - bool from_index{false}; + //! Signals if the coinstatsindex should be used (when available). + bool index_requested{true}; + //! Signals if the coinstatsindex was used to retrieve the statistics. + bool index_used{false}; // Following values are only available from coinstats index Amount total_subsidy{Amount::zero()}; diff --git a/src/node/coinstats.cpp b/src/node/coinstats.cpp --- a/src/node/coinstats.cpp +++ b/src/node/coinstats.cpp @@ -103,12 +103,12 @@ stats.nHeight = Assert(pindex)->nHeight; stats.hashBlock = pindex->GetBlockHash(); - // Use CoinStatsIndex if it is available and a hash_type of Muhash or None - // was requested + // Use CoinStatsIndex if it is requested and available and a hash_type of + // Muhash or None was requested if ((stats.m_hash_type == CoinStatsHashType::MUHASH || stats.m_hash_type == CoinStatsHashType::NONE) && - g_coin_stats_index) { - stats.from_index = true; + g_coin_stats_index && stats.index_requested) { + stats.index_used = true; return g_coin_stats_index->LookUpStats(pindex, stats); } diff --git a/src/rpc/blockchain.cpp b/src/rpc/blockchain.cpp --- a/src/rpc/blockchain.cpp +++ b/src/rpc/blockchain.cpp @@ -1297,6 +1297,8 @@ "with coinstatsindex).", "", {"", "string or numeric"}}, + {"use_index", RPCArg::Type::BOOL, /* default */ "true", + "Use coinstatsindex, if available."}, }, RPCResult{ RPCResult::Type::OBJ, @@ -1377,6 +1379,8 @@ ? CoinStatsHashType::HASH_SERIALIZED : ParseHashType(request.params[0].get_str())}; CCoinsStats stats{hash_type}; + stats.index_requested = + request.params[2].isNull() || request.params[2].get_bool(); NodeContext &node = EnsureAnyNodeContext(request.context); ChainstateManager &chainman = EnsureChainman(node); @@ -1416,7 +1420,7 @@ ret.pushKV("muhash", stats.hashSerialized.GetHex()); } ret.pushKV("total_amount", stats.nTotalAmount); - if (!stats.from_index) { + if (!stats.index_used) { ret.pushKV("transactions", static_cast(stats.nTransactions)); ret.pushKV("disk_size", stats.nDiskSize); diff --git a/src/rpc/client.cpp b/src/rpc/client.cpp --- a/src/rpc/client.cpp +++ b/src/rpc/client.cpp @@ -112,6 +112,7 @@ {"gettxout", 2, "include_mempool"}, {"gettxoutproof", 0, "txids"}, {"gettxoutsetinfo", 1, "hash_or_height"}, + {"gettxoutsetinfo", 2, "use_index"}, {"lockunspent", 0, "unlock"}, {"lockunspent", 1, "transactions"}, {"send", 0, "outputs"}, diff --git a/test/functional/feature_coinstatsindex.py b/test/functional/feature_coinstatsindex.py --- a/test/functional/feature_coinstatsindex.py +++ b/test/functional/feature_coinstatsindex.py @@ -40,6 +40,7 @@ def run_test(self): self._test_coin_stats_index() + self._test_use_index_option() def block_sanity_check(self, block_info): block_subsidy = 50_000_000 @@ -254,6 +255,17 @@ res10 = index_node.gettxoutsetinfo('muhash') assert(res8['txouts'] < res10['txouts']) + def _test_use_index_option(self): + self.log.info("Test use_index option for nodes running the index") + + self.connect_nodes(0, 1) + self.nodes[0].waitforblockheight(110) + res = self.nodes[0].gettxoutsetinfo('muhash') + option_res = self.nodes[1].gettxoutsetinfo( + hash_type='muhash', hash_or_height=None, use_index=False) + del res['disk_size'], option_res['disk_size'] + assert_equal(res, option_res) + if __name__ == '__main__': CoinStatsIndexTest().main()