157 const std::string::size_type
pos_format{param.rfind(
'.')};
210 std::vector<std::string> path = SplitString(param,
'/');
214 if (path.size() == 2) {
218 }
else if (path.size() == 1) {
223 }
catch (
const std::runtime_error&
e) {
227 return RESTERR(req,
HTTP_BAD_REQUEST,
"Invalid URI format. Expected /rest/headers/<hash>.<ext>?count=<count>");
241 std::vector<const CBlockIndex*>
headers;
251 while (pindex !=
nullptr &&
active_chain.Contains(*pindex)) {
264 ssHeader << pindex->GetBlockHeader();
269 req->
WriteHeader(
"Content-Type",
"application/octet-stream");
277 ssHeader << pindex->GetBlockHeader();
293 req->
WriteHeader(
"Content-Type",
"application/json");
313 coin.out.Serialize(
stream);
328 prevout.
pushKV(
"generated", coin.IsCoinBase());
329 prevout.
pushKV(
"height", coin.nHeight);
349 std::vector<std::string> path = SplitString(param,
'/');
352 if (path.size() == 1) {
388 req->
WriteHeader(
"Content-Type",
"application/octet-stream");
408 req->
WriteHeader(
"Content-Type",
"application/json");
429 std::optional<std::pair<size_t, size_t>>
block_part = std::nullopt)
477 req->
WriteHeader(
"Content-Type",
"application/octet-stream");
497 req->
WriteHeader(
"Content-Type",
"application/json");
534 }
catch (
const std::runtime_error&
e) {
546 std::vector<std::string>
uri_parts = SplitString(param,
'/');
558 }
catch (
const std::runtime_error&
e) {
562 return RESTERR(req,
HTTP_BAD_REQUEST,
"Invalid URI format. Expected /rest/blockfilterheaders/<filtertype>/<blockhash>.<ext>?count=<count>");
585 std::vector<const CBlockIndex*>
headers;
594 while (pindex !=
nullptr &&
active_chain.Contains(*pindex)) {
602 bool index_ready = index->BlockUntilSyncedToCurrentChain();
609 std::string
errmsg =
"Filter not found.";
612 errmsg +=
" Block filters are still in the process of being indexed.";
614 errmsg +=
" This error is unexpected and indicates index corruption.";
631 req->
WriteHeader(
"Content-Type",
"application/octet-stream");
655 req->
WriteHeader(
"Content-Type",
"application/json");
673 std::vector<std::string>
uri_parts = SplitString(param,
'/');
675 return RESTERR(req,
HTTP_BAD_REQUEST,
"Invalid URI format. Expected /rest/blockfilter/<filtertype>/<blockhash>");
707 bool index_ready = index->BlockUntilSyncedToCurrentChain();
711 std::string
errmsg =
"Filter not found.";
714 errmsg +=
" Block was not connected to active chain.";
716 errmsg +=
" Block filters are still in the process of being indexed.";
718 errmsg +=
" This error is unexpected and indicates index corruption.";
730 req->
WriteHeader(
"Content-Type",
"application/octet-stream");
749 req->
WriteHeader(
"Content-Type",
"application/json");
777 req->
WriteHeader(
"Content-Type",
"application/json");
811 if (!chainman)
return false;
820 req->
WriteHeader(
"Content-Type",
"application/json");
838 if (param !=
"contents" && param !=
"info") {
843 if (!mempool)
return false;
848 if (param ==
"contents") {
852 }
catch (
const std::runtime_error&
e) {
856 return RESTERR(req,
HTTP_BAD_REQUEST,
"The \"verbose\" query parameter must be either \"true\" or \"false\".");
861 }
catch (
const std::runtime_error&
e) {
865 return RESTERR(req,
HTTP_BAD_REQUEST,
"The \"mempool_sequence\" query parameter must be either \"true\" or \"false\".");
870 return RESTERR(req,
HTTP_BAD_REQUEST,
"Verbose results cannot contain mempool sequence values. (hint: set \"verbose=false\")");
878 req->
WriteHeader(
"Content-Type",
"application/json");
901 g_txindex->BlockUntilSyncedToCurrentChain();
905 if (!
node)
return false;
907 const CTransactionRef tx{GetTransaction(
nullptr,
node->mempool.get(), *hash,
node->chainman->m_blockman, hashBlock)};
917 req->
WriteHeader(
"Content-Type",
"application/octet-stream");
938 req->
WriteHeader(
"Content-Type",
"application/json");
957 if (param.length() > 1)
989 if (!txid || !output) {
1023 }
catch (
const std::ios_base::failure&) {
1045 std::vector<unsigned char>
bitmap;
1046 std::vector<CCoin>
outs;
1048 std::vector<bool>
hits;
1059 hits.push_back(coin.has_value());
1060 if (coin)
outs.emplace_back(std::move(*coin));
1068 if (!mempool)
return false;
1079 for (
size_t i = 0; i <
hits.size(); ++i) {
1094 req->
WriteHeader(
"Content-Type",
"application/octet-stream");
1122 utxo.pushKV(
"height", coin.nHeight);
1128 utxo.pushKV(
"scriptPubKey", std::move(
o));
1136 req->
WriteHeader(
"Content-Type",
"application/json");
1176 req->
WriteHeader(
"Content-Type",
"application/octet-stream");
1188 req->
WriteHeader(
"Content-Type",
"application/json");
1200static const struct {
UniValue blockToJSON(BlockManager &blockman, const CBlock &block, const CBlockIndex &tip, const CBlockIndex &blockindex, TxVerbosity verbosity, const uint256 pow_limit)
Block description to JSON.
UniValue blockheaderToJSON(const CBlockIndex &tip, const CBlockIndex &blockindex, const uint256 pow_limit)
Block header to JSON.
bool BlockFilterTypeByName(std::string_view name, BlockFilterType &filter_type)
Find a filter type by its human-readable name.
BlockFilterIndex * GetBlockFilterIndex(BlockFilterType filter_type)
Get a block filter index by type.
@ BLOCK_VALID_SCRIPTS
Scripts & signatures ok.
@ BLOCK_HAVE_UNDO
undo data available in rev*.dat
@ BLOCK_HAVE_DATA
full block available in blk*.dat
#define STR_INTERNAL_BUG(msg)
Complete block filter struct as defined in BIP 157.
const std::vector< unsigned char > & GetEncodedFilter() const LIFETIMEBOUND
BlockFilterIndex is used to store and retrieve block filters, hashes, and headers for a range of bloc...
bool LookupFilter(const CBlockIndex *block_index, BlockFilter &filter_out) const
Get a single filter by block.
bool LookupFilterHeader(const CBlockIndex *block_index, uint256 &header_out) EXCLUSIVE_LOCKS_REQUIRED(!m_cs_headers_cache)
Get a single filter header by block.
The block chain is a tree shaped structure starting with the genesis block at the root,...
uint256 GetBlockHash() const
Undo information for a CBlock.
An in-memory indexed chain of blocks.
CBlockIndex * Tip() const
Returns the index entry for the tip of this chain, or nullptr if none.
CCoinsView that adds a memory cache for transactions to another CCoinsView.
Pure abstract view on the open txout dataset.
CCoinsView that brings transactions from a mempool into view.
An outpoint - a combination of a transaction hash and an index n into its vout.
CTxMemPool stores valid-according-to-the-current-best-chain transactions that may be included in the ...
An output of a transaction.
Undo information for a CTransaction.
CCoinsViewCache & CoinsTip() EXCLUSIVE_LOCKS_REQUIRED(
Interface for managing multiple Chainstate objects, where each chainstate is associated with chainsta...
RecursiveMutex & GetMutex() const LOCK_RETURNED(
Alias for cs_main.
CBlockIndex * ActiveTip() const EXCLUSIVE_LOCKS_REQUIRED(GetMutex())
Chainstate & ActiveChainstate() const
Alternatives to CurrentChainstate() used by older code to query latest chainstate information without...
int ActiveHeight() const EXCLUSIVE_LOCKS_REQUIRED(GetMutex())
const Consensus::Params & GetConsensus() const
CChain & ActiveChain() const EXCLUSIVE_LOCKS_REQUIRED(GetMutex())
node::BlockManager m_blockman
A single BlockManager instance is shared across each constructed chainstate to avoid duplicating bloc...
Double ended buffer combining vector and stream-like interfaces.
void WriteHeader(std::string &&hdr, std::string &&value)
std::optional< std::string > GetQueryParameter(std::string_view key) const
std::string ReadBody() const
void WriteReply(HTTPStatusCode status, std::span< const std::byte > reply_body={})
UniValue HandleRequest(const JSONRPCRequest &request) const
Minimal stream for reading from an existing byte array by std::span.
void push_back(UniValue val)
std::string write(unsigned int prettyIndent=0, unsigned int indentLevel=0) const
void pushKV(std::string key, UniValue val)
CBlockIndex * LookupBlockIndex(const uint256 &hash) EXCLUSIVE_LOCKS_REQUIRED(cs_main)
bool ReadBlockUndo(CBlockUndo &blockundo, const CBlockIndex &index) const
ReadRawBlockResult ReadRawBlock(const FlatFilePos &pos, std::optional< std::pair< size_t, size_t > > block_part=std::nullopt) const
static std::optional< transaction_identifier > FromHex(std::string_view hex)
static std::optional< uint256 > FromHex(std::string_view str)
void ScriptToUniv(const CScript &script, UniValue &out, bool include_hex, bool include_address, const SigningProvider *provider)
void TxToUniv(const CTransaction &tx, const uint256 &block_hash, UniValue &entry, bool include_hex, const CTxUndo *txundo, TxVerbosity verbosity, std::function< bool(const CTxOut &)> is_change_func)
UniValue ValueFromAmount(const CAmount amount)
@ SHOW_DETAILS_AND_PREVOUT
The same as previous option with information about prevouts if available.
@ SHOW_TXID
Only TXID for each block's transaction.
RecursiveMutex cs_main
Mutex to guard access to validation specific variables, such as reading or changing the chainstate.
std::string HexStr(const std::span< const uint8_t > s)
Convert a span of bytes to a lower-case hexadecimal string.
void UnregisterHTTPHandler(const std::string &prefix, bool exactMatch)
Unregister handler for prefix.
void RegisterHTTPHandler(const std::string &prefix, bool exactMatch, const HTTPRequestHandler &handler)
Register handler for prefix.
CTransactionRef GetTransaction(const CBlockIndex *const block_index, const CTxMemPool *const mempool, const Txid &hash, const BlockManager &blockman, uint256 &hashBlock)
Return transaction with a given hash.
std::vector< std::string > SplitString(std::string_view str, char sep)
constexpr auto CeilDiv(const Dividend dividend, const Divisor divisor)
Integer ceiling division (for unsigned values).
constexpr TransactionSerParams TX_WITH_WITNESS
std::shared_ptr< const CTransaction > CTransactionRef
static constexpr unsigned int MAX_REST_HEADERS_RESULTS
static bool rest_headers(const std::any &context, HTTPRequest *req, const std::string &uri_part)
static void SerializeBlockUndo(DataStream &stream, const CBlockUndo &block_undo)
Serialize spent outputs as a list of per-transaction CTxOut lists using binary format.
static bool rest_block_extended(const std::any &context, HTTPRequest *req, const std::string &uri_part)
static bool rest_blockhash_by_height(const std::any &context, HTTPRequest *req, const std::string &str_uri_part)
static bool rest_block_part(const std::any &context, HTTPRequest *req, const std::string &uri_part)
static constexpr const char * REST_CACHE_IMMUTABLE
Response bytes never change.
static bool rest_block_filter(const std::any &context, HTTPRequest *req, const std::string &uri_part)
static bool rest_block_notxdetails(const std::any &context, HTTPRequest *req, const std::string &uri_part)
void StartREST(const std::any &context)
Start HTTP REST subsystem.
static bool rest_filter_header(const std::any &context, HTTPRequest *req, const std::string &uri_part)
bool(* handler)(const std::any &context, HTTPRequest *req, const std::string &strReq)
static bool rest_getutxos(const std::any &context, HTTPRequest *req, const std::string &uri_part)
static bool rest_tx(const std::any &context, HTTPRequest *req, const std::string &uri_part)
static bool rest_block(const std::any &context, HTTPRequest *req, const std::string &uri_part, std::optional< TxVerbosity > tx_verbosity, std::optional< std::pair< size_t, size_t > > block_part=std::nullopt)
This handler is used by multiple HTTP endpoints:
static const struct @10 uri_prefixes[]
void StopREST()
Stop HTTP REST subsystem.
void InterruptREST()
Interrupt RPC REST subsystem.
static bool rest_deploymentinfo(const std::any &context, HTTPRequest *req, const std::string &str_uri_part)
static bool RESTERR(HTTPRequest *req, enum HTTPStatusCode status, std::string message)
static bool rest_mempool(const std::any &context, HTTPRequest *req, const std::string &str_uri_part)
static const struct @9 rf_names[]
static constexpr const char * REST_CACHE_NO_STORE
Mutable, node-local, or error response; must not be cached.
static bool CheckWarmup(HTTPRequest *req)
static ChainstateManager * GetChainman(const std::any &context, HTTPRequest *req)
Get the node context chainstatemanager.
RPCMethod getblockchaininfo()
static void BlockUndoToJSON(const CBlockUndo &block_undo, UniValue &result)
Serialize spent outputs as a list of per-transaction CTxOut lists using JSON format.
static bool rest_chaininfo(const std::any &context, HTTPRequest *req, const std::string &uri_part)
RPCMethod getdeploymentinfo()
static bool rest_spent_txouts(const std::any &context, HTTPRequest *req, const std::string &uri_part)
RESTResponseFormat ParseDataFormat(std::string ¶m, const std::string &strReq)
Parse a URI to get the data format and URI without data format and query string.
static CTxMemPool * GetMemPool(const std::any &context, HTTPRequest *req)
Get the node context mempool.
static const size_t MAX_GETUTXOS_OUTPOINTS
static std::string AvailableDataFormatsString()
static NodeContext * GetNodeContext(const std::any &context, HTTPRequest *req)
Get the node context.
UniValue MempoolInfoToJSON(const CTxMemPool &pool)
Mempool information to JSON.
UniValue MempoolToJSON(const CTxMemPool &pool, bool verbose, bool include_mempool_sequence)
Mempool to JSON.
HTTPStatusCode
HTTP status codes.
@ HTTP_SERVICE_UNAVAILABLE
@ HTTP_INTERNAL_SERVER_ERROR
void WriteCompactSize(SizeComputer &os, uint64_t nSize)
bool RPCIsInWarmup(std::string *outStatus)
std::vector< Byte > ParseHex(std::string_view hex_str)
Like TryParseHex, but returns an empty vector on invalid input.
@ SAFE_CHARS_URI
Chars allowed in URIs (RFC 3986)
SERIALIZE_METHODS(CCoin, obj)
uint256 powLimit
Proof of work parameters.
NodeContext struct containing references to chain state and connection state.
#define WITH_LOCK(cs, code)
Run code while locking a mutex.
#define EXCLUSIVE_LOCKS_REQUIRED(...)
std::unique_ptr< TxIndex > g_txindex
The global transaction index, used in GetTransaction. May be null.
std::string SanitizeString(std::string_view str, int rule)
Remove unsafe chars.
constexpr auto Ticks(Dur2 d)
Helper to count the seconds of a duration/time_point.