aboutsummaryrefslogtreecommitdiff
path: root/src/rest.cpp
diff options
context:
space:
mode:
authorMarcoFalke <falke.marco@gmail.com>2020-05-21 06:53:30 -0400
committerMarcoFalke <falke.marco@gmail.com>2020-05-21 06:53:39 -0400
commit25ad2c623af30056ffb36dcd203a52edda2b170f (patch)
tree94fabc7fa4df3d58fb1f2f1fc204ffc8db93bd0e /src/rest.cpp
parent97b21b302a117dc8ef8334a5f3c94f6a6b9eeff0 (diff)
parentb3f7f375efb9a9ca9a7a4f2caf41fe3df2262520 (diff)
downloadbitcoin-25ad2c623af30056ffb36dcd203a52edda2b170f.tar.xz
Merge #18740: Remove g_rpc_node global
b3f7f375efb9a9ca9a7a4f2caf41fe3df2262520 refactor: Remove g_rpc_node global (Russell Yanofsky) ccb5059ee89f6e8dc31ba5b82830b384890bb65e scripted-diff: Remove g_rpc_node references (Russell Yanofsky) 6fca33b2edc09ed62dab2323c780b31585de1750 refactor: Pass NodeContext to RPC and REST methods through util::Ref (Russell Yanofsky) 691c817b340d10e806dc3b1834d2a8fcc5e681fd Add util::Ref class as temporary alternative for c++17 std::any (Russell Yanofsky) Pull request description: This PR removes the `g_rpc_node` global, to get same benefits we see removing other globals and make RPC code more testable, modular, and reusable. This uses a hybrid of the approaches suggested in #17548. Instead of using `std::any`, which isn't available in c++11, or `void*`, which isn't type safe, it uses a small new `util::Ref` helper class, which acts like a simplified `std::any` that only holds references, not values. Motivation for writing this was to provide an simpler alternative to #18647 by Harris Brakmić (brakmic) which avoids some shortcomings of that PR (https://github.com/bitcoin/bitcoin/pull/18647#issuecomment-617878826) ACKs for top commit: MarcoFalke: re-ACK b3f7f375ef, only change is adding back const and more tests 🚾 ajtowns: ACK b3f7f375efb9a9ca9a7a4f2caf41fe3df2262520 Tree-SHA512: 56292268a001bdbe34d641db1180c215351503966ff451e55cc96c9137f1d262225d7d7733de9c9da7ce7d7a4b34213a98c2476266b58c89dbbb0f3cb5aa5d70
Diffstat (limited to 'src/rest.cpp')
-rw-r--r--src/rest.cpp45
1 files changed, 25 insertions, 20 deletions
diff --git a/src/rest.cpp b/src/rest.cpp
index 1d381696d1..cde8b472d3 100644
--- a/src/rest.cpp
+++ b/src/rest.cpp
@@ -18,6 +18,7 @@
#include <sync.h>
#include <txmempool.h>
#include <util/check.h>
+#include <util/ref.h>
#include <util/strencodings.h>
#include <validation.h>
#include <version.h>
@@ -75,13 +76,14 @@ static bool RESTERR(HTTPRequest* req, enum HTTPStatusCode status, std::string me
* @param[in] req the HTTP request
* return pointer to the mempool or nullptr if no mempool found
*/
-static CTxMemPool* GetMemPool(HTTPRequest* req)
+static CTxMemPool* GetMemPool(const util::Ref& context, HTTPRequest* req)
{
- if (!g_rpc_node || !g_rpc_node->mempool) {
+ NodeContext* node = context.Has<NodeContext>() ? &context.Get<NodeContext>() : nullptr;
+ if (!node || !node->mempool) {
RESTERR(req, HTTP_NOT_FOUND, "Mempool disabled or instance not found");
return nullptr;
}
- return g_rpc_node->mempool;
+ return node->mempool;
}
static RetFormat ParseDataFormat(std::string& param, const std::string& strReq)
@@ -129,7 +131,8 @@ static bool CheckWarmup(HTTPRequest* req)
return true;
}
-static bool rest_headers(HTTPRequest* req,
+static bool rest_headers(const util::Ref& context,
+ HTTPRequest* req,
const std::string& strURIPart)
{
if (!CheckWarmup(req))
@@ -270,12 +273,12 @@ static bool rest_block(HTTPRequest* req,
}
}
-static bool rest_block_extended(HTTPRequest* req, const std::string& strURIPart)
+static bool rest_block_extended(const util::Ref& context, HTTPRequest* req, const std::string& strURIPart)
{
return rest_block(req, strURIPart, true);
}
-static bool rest_block_notxdetails(HTTPRequest* req, const std::string& strURIPart)
+static bool rest_block_notxdetails(const util::Ref& context, HTTPRequest* req, const std::string& strURIPart)
{
return rest_block(req, strURIPart, false);
}
@@ -283,7 +286,7 @@ static bool rest_block_notxdetails(HTTPRequest* req, const std::string& strURIPa
// A bit of a hack - dependency on a function defined in rpc/blockchain.cpp
UniValue getblockchaininfo(const JSONRPCRequest& request);
-static bool rest_chaininfo(HTTPRequest* req, const std::string& strURIPart)
+static bool rest_chaininfo(const util::Ref& context, HTTPRequest* req, const std::string& strURIPart)
{
if (!CheckWarmup(req))
return false;
@@ -292,7 +295,7 @@ static bool rest_chaininfo(HTTPRequest* req, const std::string& strURIPart)
switch (rf) {
case RetFormat::JSON: {
- JSONRPCRequest jsonRequest;
+ JSONRPCRequest jsonRequest(context);
jsonRequest.params = UniValue(UniValue::VARR);
UniValue chainInfoObject = getblockchaininfo(jsonRequest);
std::string strJSON = chainInfoObject.write() + "\n";
@@ -306,11 +309,11 @@ static bool rest_chaininfo(HTTPRequest* req, const std::string& strURIPart)
}
}
-static bool rest_mempool_info(HTTPRequest* req, const std::string& strURIPart)
+static bool rest_mempool_info(const util::Ref& context, HTTPRequest* req, const std::string& strURIPart)
{
if (!CheckWarmup(req))
return false;
- const CTxMemPool* mempool = GetMemPool(req);
+ const CTxMemPool* mempool = GetMemPool(context, req);
if (!mempool) return false;
std::string param;
const RetFormat rf = ParseDataFormat(param, strURIPart);
@@ -330,10 +333,10 @@ static bool rest_mempool_info(HTTPRequest* req, const std::string& strURIPart)
}
}
-static bool rest_mempool_contents(HTTPRequest* req, const std::string& strURIPart)
+static bool rest_mempool_contents(const util::Ref& context, HTTPRequest* req, const std::string& strURIPart)
{
if (!CheckWarmup(req)) return false;
- const CTxMemPool* mempool = GetMemPool(req);
+ const CTxMemPool* mempool = GetMemPool(context, req);
if (!mempool) return false;
std::string param;
const RetFormat rf = ParseDataFormat(param, strURIPart);
@@ -353,7 +356,7 @@ static bool rest_mempool_contents(HTTPRequest* req, const std::string& strURIPar
}
}
-static bool rest_tx(HTTPRequest* req, const std::string& strURIPart)
+static bool rest_tx(const util::Ref& context, HTTPRequest* req, const std::string& strURIPart)
{
if (!CheckWarmup(req))
return false;
@@ -409,7 +412,7 @@ static bool rest_tx(HTTPRequest* req, const std::string& strURIPart)
}
}
-static bool rest_getutxos(HTTPRequest* req, const std::string& strURIPart)
+static bool rest_getutxos(const util::Ref& context, HTTPRequest* req, const std::string& strURIPart)
{
if (!CheckWarmup(req))
return false;
@@ -518,7 +521,7 @@ static bool rest_getutxos(HTTPRequest* req, const std::string& strURIPart)
};
if (fCheckMemPool) {
- const CTxMemPool* mempool = GetMemPool(req);
+ const CTxMemPool* mempool = GetMemPool(context, req);
if (!mempool) return false;
// use db+mempool as cache backend in case user likes to query mempool
LOCK2(cs_main, mempool->cs);
@@ -595,7 +598,7 @@ static bool rest_getutxos(HTTPRequest* req, const std::string& strURIPart)
}
}
-static bool rest_blockhash_by_height(HTTPRequest* req,
+static bool rest_blockhash_by_height(const util::Ref& context, HTTPRequest* req,
const std::string& str_uri_part)
{
if (!CheckWarmup(req)) return false;
@@ -643,7 +646,7 @@ static bool rest_blockhash_by_height(HTTPRequest* req,
static const struct {
const char* prefix;
- bool (*handler)(HTTPRequest* req, const std::string& strReq);
+ bool (*handler)(const util::Ref& context, HTTPRequest* req, const std::string& strReq);
} uri_prefixes[] = {
{"/rest/tx/", rest_tx},
{"/rest/block/notxdetails/", rest_block_notxdetails},
@@ -656,10 +659,12 @@ static const struct {
{"/rest/blockhashbyheight/", rest_blockhash_by_height},
};
-void StartREST()
+void StartREST(const util::Ref& context)
{
- for (unsigned int i = 0; i < ARRAYLEN(uri_prefixes); i++)
- RegisterHTTPHandler(uri_prefixes[i].prefix, false, uri_prefixes[i].handler);
+ for (const auto& up : uri_prefixes) {
+ auto handler = [&context, up](HTTPRequest* req, const std::string& prefix) { return up.handler(context, req, prefix); };
+ RegisterHTTPHandler(up.prefix, false, handler);
+ }
}
void InterruptREST()