/Users/eugenesiegel/btc/bitcoin/src/rpc/util.h
Line | Count | Source (jump to first uncovered line) |
1 | | // Copyright (c) 2017-present The Bitcoin Core developers |
2 | | // Distributed under the MIT software license, see the accompanying |
3 | | // file COPYING or http://www.opensource.org/licenses/mit-license.php. |
4 | | |
5 | | #ifndef BITCOIN_RPC_UTIL_H |
6 | | #define BITCOIN_RPC_UTIL_H |
7 | | |
8 | | #include <addresstype.h> |
9 | | #include <consensus/amount.h> |
10 | | #include <node/transaction.h> |
11 | | #include <outputtype.h> |
12 | | #include <pubkey.h> |
13 | | #include <rpc/protocol.h> |
14 | | #include <rpc/request.h> |
15 | | #include <script/script.h> |
16 | | #include <script/sign.h> |
17 | | #include <uint256.h> |
18 | | #include <univalue.h> |
19 | | #include <util/check.h> |
20 | | |
21 | | #include <cstddef> |
22 | | #include <cstdint> |
23 | | #include <functional> |
24 | | #include <initializer_list> |
25 | | #include <map> |
26 | | #include <optional> |
27 | | #include <string> |
28 | | #include <string_view> |
29 | | #include <type_traits> |
30 | | #include <utility> |
31 | | #include <variant> |
32 | | #include <vector> |
33 | | |
34 | | class JSONRPCRequest; |
35 | | enum ServiceFlags : uint64_t; |
36 | | enum class OutputType; |
37 | | struct FlatSigningProvider; |
38 | | struct bilingual_str; |
39 | | namespace common { |
40 | | enum class PSBTError; |
41 | | } // namespace common |
42 | | namespace node { |
43 | | enum class TransactionError; |
44 | | } // namespace node |
45 | | |
46 | | static constexpr bool DEFAULT_RPC_DOC_CHECK{ |
47 | | #ifdef RPC_DOC_CHECK |
48 | | true |
49 | | #else |
50 | | false |
51 | | #endif |
52 | | }; |
53 | | |
54 | | /** |
55 | | * String used to describe UNIX epoch time in documentation, factored out to a |
56 | | * constant for consistency. |
57 | | */ |
58 | | extern const std::string UNIX_EPOCH_TIME; |
59 | | |
60 | | /** |
61 | | * Example bech32 addresses for the RPCExamples help documentation. They are intentionally |
62 | | * invalid to prevent accidental transactions by users. |
63 | | */ |
64 | | extern const std::string EXAMPLE_ADDRESS[2]; |
65 | | |
66 | | class FillableSigningProvider; |
67 | | class CScript; |
68 | | struct Sections; |
69 | | |
70 | | struct HelpResult : std::runtime_error { |
71 | 0 | explicit HelpResult(const std::string& msg) : std::runtime_error{msg} {} |
72 | | }; |
73 | | |
74 | | /** |
75 | | * Gets all existing output types formatted for RPC help sections. |
76 | | * |
77 | | * @return Comma separated string representing output type names. |
78 | | */ |
79 | | std::string GetAllOutputTypes(); |
80 | | |
81 | | /** Wrapper for UniValue::VType, which includes typeAny: |
82 | | * Used to denote don't care type. */ |
83 | | struct UniValueType { |
84 | 0 | UniValueType(UniValue::VType _type) : typeAny(false), type(_type) {} |
85 | 0 | UniValueType() : typeAny(true) {} |
86 | | bool typeAny; |
87 | | UniValue::VType type; |
88 | | }; |
89 | | |
90 | | /* |
91 | | Check for expected keys/value types in an Object. |
92 | | */ |
93 | | void RPCTypeCheckObj(const UniValue& o, |
94 | | const std::map<std::string, UniValueType>& typesExpected, |
95 | | bool fAllowNull = false, |
96 | | bool fStrict = false); |
97 | | |
98 | | /** |
99 | | * Utilities: convert hex-encoded Values |
100 | | * (throws error if not hex). |
101 | | */ |
102 | | uint256 ParseHashV(const UniValue& v, std::string_view name); |
103 | | uint256 ParseHashO(const UniValue& o, std::string_view strKey); |
104 | | std::vector<unsigned char> ParseHexV(const UniValue& v, std::string_view name); |
105 | | std::vector<unsigned char> ParseHexO(const UniValue& o, std::string_view strKey); |
106 | | |
107 | | /** |
108 | | * Parses verbosity from provided UniValue. |
109 | | * |
110 | | * @param[in] arg The verbosity argument as an int (0, 1, 2,...) or bool if allow_bool is set to true |
111 | | * @param[in] default_verbosity The value to return if verbosity argument is null |
112 | | * @param[in] allow_bool If true, allows arg to be a bool and parses it |
113 | | * @returns An integer describing the verbosity level (e.g. 0, 1, 2, etc.) |
114 | | * @throws JSONRPCError if allow_bool is false but arg provided is boolean |
115 | | */ |
116 | | int ParseVerbosity(const UniValue& arg, int default_verbosity, bool allow_bool); |
117 | | |
118 | | /** |
119 | | * Validate and return a CAmount from a UniValue number or string. |
120 | | * |
121 | | * @param[in] value UniValue number or string to parse. |
122 | | * @param[in] decimals Number of significant digits (default: 8). |
123 | | * @returns a CAmount if the various checks pass. |
124 | | */ |
125 | | CAmount AmountFromValue(const UniValue& value, int decimals = 8); |
126 | | /** |
127 | | * Parse a json number or string, denoting BTC/kvB, into a CFeeRate (sat/kvB). |
128 | | * Reject negative values or rates larger than 1BTC/kvB. |
129 | | */ |
130 | | CFeeRate ParseFeeRate(const UniValue& json); |
131 | | |
132 | | using RPCArgList = std::vector<std::pair<std::string, UniValue>>; |
133 | | std::string HelpExampleCli(const std::string& methodname, const std::string& args); |
134 | | std::string HelpExampleCliNamed(const std::string& methodname, const RPCArgList& args); |
135 | | std::string HelpExampleRpc(const std::string& methodname, const std::string& args); |
136 | | std::string HelpExampleRpcNamed(const std::string& methodname, const RPCArgList& args); |
137 | | |
138 | | CPubKey HexToPubKey(const std::string& hex_in); |
139 | | CTxDestination AddAndGetMultisigDestination(const int required, const std::vector<CPubKey>& pubkeys, OutputType type, FlatSigningProvider& keystore, CScript& script_out); |
140 | | |
141 | | UniValue DescribeAddress(const CTxDestination& dest); |
142 | | |
143 | | /** Parse a sighash string representation and raise an RPC error if it is invalid. */ |
144 | | std::optional<int> ParseSighashString(const UniValue& sighash); |
145 | | |
146 | | //! Parse a confirm target option and raise an RPC error if it is invalid. |
147 | | unsigned int ParseConfirmTarget(const UniValue& value, unsigned int max_target); |
148 | | |
149 | | RPCErrorCode RPCErrorFromTransactionError(node::TransactionError terr); |
150 | | UniValue JSONRPCPSBTError(common::PSBTError err); |
151 | | UniValue JSONRPCTransactionError(node::TransactionError terr, const std::string& err_string = ""); |
152 | | |
153 | | //! Parse a JSON range specified as int64, or [int64, int64] |
154 | | std::pair<int64_t, int64_t> ParseDescriptorRange(const UniValue& value); |
155 | | |
156 | | /** Evaluate a descriptor given as a string, or as a {"desc":...,"range":...} object, with default range of 1000. */ |
157 | | std::vector<CScript> EvalDescriptorStringOrObject(const UniValue& scanobject, FlatSigningProvider& provider, const bool expand_priv = false); |
158 | | |
159 | | /** |
160 | | * Serializing JSON objects depends on the outer type. Only arrays and |
161 | | * dictionaries can be nested in json. The top-level outer type is "NONE". |
162 | | */ |
163 | | enum class OuterType { |
164 | | ARR, |
165 | | OBJ, |
166 | | NONE, // Only set on first recursion |
167 | | }; |
168 | | |
169 | | struct RPCArgOptions { |
170 | | bool skip_type_check{false}; |
171 | | std::string oneline_description{}; //!< Should be empty unless it is supposed to override the auto-generated summary line |
172 | | std::vector<std::string> type_str{}; //!< Should be empty unless it is supposed to override the auto-generated type strings. Vector length is either 0 or 2, m_opts.type_str.at(0) will override the type of the value in a key-value pair, m_opts.type_str.at(1) will override the type in the argument description. |
173 | | bool hidden{false}; //!< For testing only |
174 | | bool also_positional{false}; //!< If set allows a named-parameter field in an OBJ_NAMED_PARAM options object |
175 | | //!< to have the same name as a top-level parameter. By default the RPC |
176 | | //!< framework disallows this, because if an RPC request passes the value by |
177 | | //!< name, it is assigned to top-level parameter position, not to the options |
178 | | //!< position, defeating the purpose of using OBJ_NAMED_PARAMS instead OBJ for |
179 | | //!< that option. But sometimes it makes sense to allow less-commonly used |
180 | | //!< options to be passed by name only, and more commonly used options to be |
181 | | //!< passed by name or position, so the RPC framework allows this as long as |
182 | | //!< methods set the also_positional flag and read values from both positions. |
183 | | }; |
184 | | |
185 | | // NOLINTNEXTLINE(misc-no-recursion) |
186 | | struct RPCArg { |
187 | | enum class Type { |
188 | | OBJ, |
189 | | ARR, |
190 | | STR, |
191 | | NUM, |
192 | | BOOL, |
193 | | OBJ_NAMED_PARAMS, //!< Special type that behaves almost exactly like |
194 | | //!< OBJ, defining an options object with a list of |
195 | | //!< pre-defined keys. The only difference between OBJ |
196 | | //!< and OBJ_NAMED_PARAMS is that OBJ_NAMED_PARMS |
197 | | //!< also allows the keys to be passed as top-level |
198 | | //!< named parameters, as a more convenient way to pass |
199 | | //!< options to the RPC method without nesting them. |
200 | | OBJ_USER_KEYS, //!< Special type where the user must set the keys e.g. to define multiple addresses; as opposed to e.g. an options object where the keys are predefined |
201 | | AMOUNT, //!< Special type representing a floating point amount (can be either NUM or STR) |
202 | | STR_HEX, //!< Special type that is a STR with only hex chars |
203 | | RANGE, //!< Special type that is a NUM or [NUM,NUM] |
204 | | }; |
205 | | |
206 | | enum class Optional { |
207 | | /** Required arg */ |
208 | | NO, |
209 | | /** |
210 | | * Optional argument for which the default value is omitted from |
211 | | * help text for one of two reasons: |
212 | | * - It's a named argument and has a default value of `null`. |
213 | | * - Its default value is implicitly clear. That is, elements in an |
214 | | * array may not exist by default. |
215 | | * When possible, the default value should be specified. |
216 | | */ |
217 | | OMITTED, |
218 | | }; |
219 | | /** Hint for default value */ |
220 | | using DefaultHint = std::string; |
221 | | /** Default constant value */ |
222 | | using Default = UniValue; |
223 | | using Fallback = std::variant<Optional, DefaultHint, Default>; |
224 | | |
225 | | const std::string m_names; //!< The name of the arg (can be empty for inner args, can contain multiple aliases separated by | for named request arguments) |
226 | | const Type m_type; |
227 | | const std::vector<RPCArg> m_inner; //!< Only used for arrays or dicts |
228 | | const Fallback m_fallback; |
229 | | const std::string m_description; |
230 | | const RPCArgOptions m_opts; |
231 | | |
232 | | RPCArg( |
233 | | std::string name, |
234 | | Type type, |
235 | | Fallback fallback, |
236 | | std::string description, |
237 | | RPCArgOptions opts = {}) |
238 | 0 | : m_names{std::move(name)}, |
239 | 0 | m_type{std::move(type)}, |
240 | 0 | m_fallback{std::move(fallback)}, |
241 | 0 | m_description{std::move(description)}, |
242 | 0 | m_opts{std::move(opts)} |
243 | 0 | { |
244 | 0 | CHECK_NONFATAL(type != Type::ARR && type != Type::OBJ && type != Type::OBJ_NAMED_PARAMS && type != Type::OBJ_USER_KEYS); Line | Count | Source | 103 | 0 | inline_check_non_fatal(condition, __FILE__, __LINE__, __func__, #condition) |
|
245 | 0 | } |
246 | | |
247 | | RPCArg( |
248 | | std::string name, |
249 | | Type type, |
250 | | Fallback fallback, |
251 | | std::string description, |
252 | | std::vector<RPCArg> inner, |
253 | | RPCArgOptions opts = {}) |
254 | 0 | : m_names{std::move(name)}, |
255 | 0 | m_type{std::move(type)}, |
256 | 0 | m_inner{std::move(inner)}, |
257 | 0 | m_fallback{std::move(fallback)}, |
258 | 0 | m_description{std::move(description)}, |
259 | 0 | m_opts{std::move(opts)} |
260 | 0 | { |
261 | 0 | CHECK_NONFATAL(type == Type::ARR || type == Type::OBJ || type == Type::OBJ_NAMED_PARAMS || type == Type::OBJ_USER_KEYS); Line | Count | Source | 103 | 0 | inline_check_non_fatal(condition, __FILE__, __LINE__, __func__, #condition) |
|
262 | 0 | } |
263 | | |
264 | | bool IsOptional() const; |
265 | | |
266 | | /** |
267 | | * Check whether the request JSON type matches. |
268 | | * Returns true if type matches, or object describing error(s) if not. |
269 | | */ |
270 | | UniValue MatchesType(const UniValue& request) const; |
271 | | |
272 | | /** Return the first of all aliases */ |
273 | | std::string GetFirstName() const; |
274 | | |
275 | | /** Return the name, throws when there are aliases */ |
276 | | std::string GetName() const; |
277 | | |
278 | | /** |
279 | | * Return the type string of the argument. |
280 | | * Set oneline to allow it to be overridden by a custom oneline type string (m_opts.oneline_description). |
281 | | */ |
282 | | std::string ToString(bool oneline) const; |
283 | | /** |
284 | | * Return the type string of the argument when it is in an object (dict). |
285 | | * Set oneline to get the oneline representation (less whitespace) |
286 | | */ |
287 | | std::string ToStringObj(bool oneline) const; |
288 | | /** |
289 | | * Return the description string, including the argument type and whether |
290 | | * the argument is required. |
291 | | */ |
292 | | std::string ToDescriptionString(bool is_named_arg) const; |
293 | | }; |
294 | | |
295 | | // NOLINTNEXTLINE(misc-no-recursion) |
296 | | struct RPCResult { |
297 | | enum class Type { |
298 | | OBJ, |
299 | | ARR, |
300 | | STR, |
301 | | NUM, |
302 | | BOOL, |
303 | | NONE, |
304 | | ANY, //!< Special type to disable type checks (for testing only) |
305 | | STR_AMOUNT, //!< Special string to represent a floating point amount |
306 | | STR_HEX, //!< Special string with only hex chars |
307 | | OBJ_DYN, //!< Special dictionary with keys that are not literals |
308 | | ARR_FIXED, //!< Special array that has a fixed number of entries |
309 | | NUM_TIME, //!< Special numeric to denote unix epoch time |
310 | | ELISION, //!< Special type to denote elision (...) |
311 | | }; |
312 | | |
313 | | const Type m_type; |
314 | | const std::string m_key_name; //!< Only used for dicts |
315 | | const std::vector<RPCResult> m_inner; //!< Only used for arrays or dicts |
316 | | const bool m_optional; |
317 | | const bool m_skip_type_check; |
318 | | const std::string m_description; |
319 | | const std::string m_cond; |
320 | | |
321 | | RPCResult( |
322 | | std::string cond, |
323 | | Type type, |
324 | | std::string m_key_name, |
325 | | bool optional, |
326 | | std::string description, |
327 | | std::vector<RPCResult> inner = {}) |
328 | 0 | : m_type{std::move(type)}, |
329 | 0 | m_key_name{std::move(m_key_name)}, |
330 | 0 | m_inner{std::move(inner)}, |
331 | 0 | m_optional{optional}, |
332 | 0 | m_skip_type_check{false}, |
333 | 0 | m_description{std::move(description)}, |
334 | 0 | m_cond{std::move(cond)} |
335 | 0 | { |
336 | 0 | CHECK_NONFATAL(!m_cond.empty()); Line | Count | Source | 103 | 0 | inline_check_non_fatal(condition, __FILE__, __LINE__, __func__, #condition) |
|
337 | 0 | CheckInnerDoc(); |
338 | 0 | } |
339 | | |
340 | | RPCResult( |
341 | | std::string cond, |
342 | | Type type, |
343 | | std::string m_key_name, |
344 | | std::string description, |
345 | | std::vector<RPCResult> inner = {}) |
346 | 0 | : RPCResult{std::move(cond), type, std::move(m_key_name), /*optional=*/false, std::move(description), std::move(inner)} {} |
347 | | |
348 | | RPCResult( |
349 | | Type type, |
350 | | std::string m_key_name, |
351 | | bool optional, |
352 | | std::string description, |
353 | | std::vector<RPCResult> inner = {}, |
354 | | bool skip_type_check = false) |
355 | 0 | : m_type{std::move(type)}, |
356 | 0 | m_key_name{std::move(m_key_name)}, |
357 | 0 | m_inner{std::move(inner)}, |
358 | 0 | m_optional{optional}, |
359 | 0 | m_skip_type_check{skip_type_check}, |
360 | 0 | m_description{std::move(description)}, |
361 | 0 | m_cond{} |
362 | 0 | { |
363 | 0 | CheckInnerDoc(); |
364 | 0 | } |
365 | | |
366 | | RPCResult( |
367 | | Type type, |
368 | | std::string m_key_name, |
369 | | std::string description, |
370 | | std::vector<RPCResult> inner = {}, |
371 | | bool skip_type_check = false) |
372 | 0 | : RPCResult{type, std::move(m_key_name), /*optional=*/false, std::move(description), std::move(inner), skip_type_check} {} |
373 | | |
374 | | /** Append the sections of the result. */ |
375 | | void ToSections(Sections& sections, OuterType outer_type = OuterType::NONE, const int current_indent = 0) const; |
376 | | /** Return the type string of the result when it is in an object (dict). */ |
377 | | std::string ToStringObj() const; |
378 | | /** Return the description string, including the result type. */ |
379 | | std::string ToDescriptionString() const; |
380 | | /** Check whether the result JSON type matches. |
381 | | * Returns true if type matches, or object describing error(s) if not. |
382 | | */ |
383 | | UniValue MatchesType(const UniValue& result) const; |
384 | | |
385 | | private: |
386 | | void CheckInnerDoc() const; |
387 | | }; |
388 | | |
389 | | struct RPCResults { |
390 | | const std::vector<RPCResult> m_results; |
391 | | |
392 | | RPCResults(RPCResult result) |
393 | 0 | : m_results{{result}} |
394 | 0 | { |
395 | 0 | } |
396 | | |
397 | | RPCResults(std::initializer_list<RPCResult> results) |
398 | 0 | : m_results{results} |
399 | 0 | { |
400 | 0 | } |
401 | | |
402 | | /** |
403 | | * Return the description string. |
404 | | */ |
405 | | std::string ToDescriptionString() const; |
406 | | }; |
407 | | |
408 | | struct RPCExamples { |
409 | | const std::string m_examples; |
410 | | explicit RPCExamples( |
411 | | std::string examples) |
412 | 0 | : m_examples(std::move(examples)) |
413 | 0 | { |
414 | 0 | } |
415 | | std::string ToDescriptionString() const; |
416 | | }; |
417 | | |
418 | | class RPCHelpMan |
419 | | { |
420 | | public: |
421 | | RPCHelpMan(std::string name, std::string description, std::vector<RPCArg> args, RPCResults results, RPCExamples examples); |
422 | | using RPCMethodImpl = std::function<UniValue(const RPCHelpMan&, const JSONRPCRequest&)>; |
423 | | RPCHelpMan(std::string name, std::string description, std::vector<RPCArg> args, RPCResults results, RPCExamples examples, RPCMethodImpl fun); |
424 | | |
425 | | UniValue HandleRequest(const JSONRPCRequest& request) const; |
426 | | /** |
427 | | * @brief Helper to get a required or default-valued request argument. |
428 | | * |
429 | | * Use this function when the argument is required or when it has a default value. If the |
430 | | * argument is optional and may not be provided, use MaybeArg instead. |
431 | | * |
432 | | * This function only works during m_fun(), i.e., it should only be used in |
433 | | * RPC method implementations. It internally checks whether the user-passed |
434 | | * argument isNull() and parses (from JSON) and returns the user-passed argument, |
435 | | * or the default value derived from the RPCArg documentation. |
436 | | * |
437 | | * The instantiation of this helper for type R must match the corresponding RPCArg::Type. |
438 | | * |
439 | | * @return The value of the RPC argument (or the default value) cast to type R. |
440 | | * |
441 | | * @see MaybeArg for handling optional arguments without default values. |
442 | | */ |
443 | | template <typename R> |
444 | | auto Arg(std::string_view key) const |
445 | 0 | { |
446 | 0 | auto i{GetParamIndex(key)}; |
447 | | // Return argument (required or with default value). |
448 | 0 | if constexpr (std::is_integral_v<R> || std::is_floating_point_v<R>) { |
449 | | // Return numbers by value. |
450 | 0 | return ArgValue<R>(i); |
451 | 0 | } else { |
452 | | // Return everything else by reference. |
453 | 0 | return ArgValue<const R&>(i); |
454 | 0 | } |
455 | 0 | } Unexecuted instantiation: _ZNK10RPCHelpMan3ArgIiEEDaNSt3__117basic_string_viewIcNS1_11char_traitsIcEEEE Unexecuted instantiation: _ZNK10RPCHelpMan3ArgIjEEDaNSt3__117basic_string_viewIcNS1_11char_traitsIcEEEE Unexecuted instantiation: _ZNK10RPCHelpMan3ArgIbEEDaNSt3__117basic_string_viewIcNS1_11char_traitsIcEEEE Unexecuted instantiation: _ZNK10RPCHelpMan3ArgINSt3__112basic_stringIcNS1_11char_traitsIcEENS1_9allocatorIcEEEEEEDaNS1_17basic_string_viewIcS4_EE Unexecuted instantiation: _ZNK10RPCHelpMan3ArgI8UniValueEEDaNSt3__117basic_string_viewIcNS2_11char_traitsIcEEEE Unexecuted instantiation: _ZNK10RPCHelpMan3ArgIyEEDaNSt3__117basic_string_viewIcNS1_11char_traitsIcEEEE |
456 | | /** |
457 | | * @brief Helper to get an optional request argument. |
458 | | * |
459 | | * Use this function when the argument is optional and does not have a default value. If the |
460 | | * argument is required or has a default value, use Arg instead. |
461 | | * |
462 | | * This function only works during m_fun(), i.e., it should only be used in |
463 | | * RPC method implementations. It internally checks whether the user-passed |
464 | | * argument isNull() and parses (from JSON) and returns the user-passed argument, |
465 | | * or a falsy value if no argument was passed. |
466 | | * |
467 | | * The instantiation of this helper for type R must match the corresponding RPCArg::Type. |
468 | | * |
469 | | * @return For integral and floating-point types, a std::optional<R> is returned. |
470 | | * For other types, a R* pointer to the argument is returned. If the |
471 | | * argument is not provided, std::nullopt or a null pointer is returned. |
472 | | * |
473 | | * @see Arg for handling arguments that are required or have a default value. |
474 | | */ |
475 | | template <typename R> |
476 | | auto MaybeArg(std::string_view key) const |
477 | 0 | { |
478 | 0 | auto i{GetParamIndex(key)}; |
479 | | // Return optional argument (without default). |
480 | 0 | if constexpr (std::is_integral_v<R> || std::is_floating_point_v<R>) { |
481 | | // Return numbers by value, wrapped in optional. |
482 | 0 | return ArgValue<std::optional<R>>(i); |
483 | 0 | } else { |
484 | | // Return other types by pointer. |
485 | 0 | return ArgValue<const R*>(i); |
486 | 0 | } |
487 | 0 | } Unexecuted instantiation: _ZNK10RPCHelpMan8MaybeArgINSt3__112basic_stringIcNS1_11char_traitsIcEENS1_9allocatorIcEEEEEEDaNS1_17basic_string_viewIcS4_EE Unexecuted instantiation: _ZNK10RPCHelpMan8MaybeArgIbEEDaNSt3__117basic_string_viewIcNS1_11char_traitsIcEEEE Unexecuted instantiation: _ZNK10RPCHelpMan8MaybeArgIdEEDaNSt3__117basic_string_viewIcNS1_11char_traitsIcEEEE |
488 | | std::string ToString() const; |
489 | | /** Return the named args that need to be converted from string to another JSON type */ |
490 | | UniValue GetArgMap() const; |
491 | | /** If the supplied number of args is neither too small nor too high */ |
492 | | bool IsValidNumArgs(size_t num_args) const; |
493 | | //! Return list of arguments and whether they are named-only. |
494 | | std::vector<std::pair<std::string, bool>> GetArgNames() const; |
495 | | |
496 | | const std::string m_name; |
497 | | |
498 | | private: |
499 | | const RPCMethodImpl m_fun; |
500 | | const std::string m_description; |
501 | | const std::vector<RPCArg> m_args; |
502 | | const RPCResults m_results; |
503 | | const RPCExamples m_examples; |
504 | | mutable const JSONRPCRequest* m_req{nullptr}; // A pointer to the request for the duration of m_fun() |
505 | | template <typename R> |
506 | | R ArgValue(size_t i) const; |
507 | | //! Return positional index of a parameter using its name as key. |
508 | | size_t GetParamIndex(std::string_view key) const; |
509 | | }; |
510 | | |
511 | | /** |
512 | | * Push warning messages to an RPC "warnings" field as a JSON array of strings. |
513 | | * |
514 | | * @param[in] warnings Warning messages to push. |
515 | | * @param[out] obj UniValue object to push the warnings array object to. |
516 | | */ |
517 | | void PushWarnings(const UniValue& warnings, UniValue& obj); |
518 | | void PushWarnings(const std::vector<bilingual_str>& warnings, UniValue& obj); |
519 | | |
520 | | std::vector<RPCResult> ScriptPubKeyDoc(); |
521 | | |
522 | | /*** |
523 | | * Get the target for a given block index. |
524 | | * |
525 | | * @param[in] blockindex the block |
526 | | * @param[in] pow_limit PoW limit (consensus parameter) |
527 | | * |
528 | | * @return the target |
529 | | */ |
530 | | uint256 GetTarget(const CBlockIndex& blockindex, const uint256 pow_limit); |
531 | | |
532 | | #endif // BITCOIN_RPC_UTIL_H |