Bitcoin Core  0.19.99
P2P Digital Currency
util.h
Go to the documentation of this file.
1 // Copyright (c) 2017-2019 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 <node/transaction.h>
9 #include <outputtype.h>
10 #include <protocol.h>
11 #include <pubkey.h>
12 #include <rpc/protocol.h>
13 #include <rpc/request.h>
14 #include <script/script.h>
15 #include <script/sign.h>
16 #include <script/standard.h>
17 #include <univalue.h>
18 #include <util/check.h>
19 
20 #include <string>
21 #include <vector>
22 
23 #include <boost/variant.hpp>
24 
29 extern const std::string UNIX_EPOCH_TIME;
30 
35 extern const std::string EXAMPLE_ADDRESS[2];
36 
38 class CPubKey;
39 class CScript;
40 struct Sections;
41 
44 struct UniValueType {
45  UniValueType(UniValue::VType _type) : typeAny(false), type(_type) {}
46  UniValueType() : typeAny(true) {}
47  bool typeAny;
49 };
50 
55 void RPCTypeCheck(const UniValue& params,
56  const std::list<UniValueType>& typesExpected, bool fAllowNull=false);
57 
61 void RPCTypeCheckArgument(const UniValue& value, const UniValueType& typeExpected);
62 
63 /*
64  Check for expected keys/value types in an Object.
65 */
66 void RPCTypeCheckObj(const UniValue& o,
67  const std::map<std::string, UniValueType>& typesExpected,
68  bool fAllowNull = false,
69  bool fStrict = false);
70 
75 extern uint256 ParseHashV(const UniValue& v, std::string strName);
76 extern uint256 ParseHashO(const UniValue& o, std::string strKey);
77 extern std::vector<unsigned char> ParseHexV(const UniValue& v, std::string strName);
78 extern std::vector<unsigned char> ParseHexO(const UniValue& o, std::string strKey);
79 
80 extern CAmount AmountFromValue(const UniValue& value);
81 extern std::string HelpExampleCli(const std::string& methodname, const std::string& args);
82 extern std::string HelpExampleRpc(const std::string& methodname, const std::string& args);
83 
84 CPubKey HexToPubKey(const std::string& hex_in);
85 CPubKey AddrToPubKey(const FillableSigningProvider& keystore, const std::string& addr_in);
86 CTxDestination AddAndGetMultisigDestination(const int required, const std::vector<CPubKey>& pubkeys, OutputType type, FillableSigningProvider& keystore, CScript& script_out);
87 
89 
91 unsigned int ParseConfirmTarget(const UniValue& value, unsigned int max_target);
92 
94 UniValue JSONRPCTransactionError(TransactionError terr, const std::string& err_string = "");
95 
97 std::pair<int64_t, int64_t> ParseDescriptorRange(const UniValue& value);
98 
100 std::vector<CScript> EvalDescriptorStringOrObject(const UniValue& scanobject, FlatSigningProvider& provider);
101 
104 
109 enum class OuterType {
110  ARR,
111  OBJ,
112  NONE, // Only set on first recursion
113 };
114 
115 struct RPCArg {
116  enum class Type {
117  OBJ,
118  ARR,
119  STR,
120  NUM,
121  BOOL,
122  OBJ_USER_KEYS,
123  AMOUNT,
124  STR_HEX,
125  RANGE,
126  };
127 
128  enum class Optional {
130  NO,
135  OMITTED_NAMED_ARG,
142  OMITTED,
143  };
144  using Fallback = boost::variant<Optional, /* default value for optional args */ std::string>;
145  const std::string m_name;
146  const Type m_type;
147  const std::vector<RPCArg> m_inner;
149  const std::string m_description;
150  const std::string m_oneline_description;
151  const std::vector<std::string> m_type_str;
152 
154  const std::string name,
155  const Type type,
156  const Fallback fallback,
157  const std::string description,
158  const std::string oneline_description = "",
159  const std::vector<std::string> type_str = {})
160  : m_name{std::move(name)},
161  m_type{std::move(type)},
162  m_fallback{std::move(fallback)},
163  m_description{std::move(description)},
164  m_oneline_description{std::move(oneline_description)},
165  m_type_str{std::move(type_str)}
166  {
167  CHECK_NONFATAL(type != Type::ARR && type != Type::OBJ);
168  }
169 
171  const std::string name,
172  const Type type,
173  const Fallback fallback,
174  const std::string description,
175  const std::vector<RPCArg> inner,
176  const std::string oneline_description = "",
177  const std::vector<std::string> type_str = {})
178  : m_name{std::move(name)},
179  m_type{std::move(type)},
180  m_inner{std::move(inner)},
181  m_fallback{std::move(fallback)},
182  m_description{std::move(description)},
183  m_oneline_description{std::move(oneline_description)},
184  m_type_str{std::move(type_str)}
185  {
186  CHECK_NONFATAL(type == Type::ARR || type == Type::OBJ);
187  }
188 
189  bool IsOptional() const;
190 
195  std::string ToString(bool oneline) const;
200  std::string ToStringObj(bool oneline) const;
205  std::string ToDescriptionString() const;
206 };
207 
208 struct RPCResult {
209  enum class Type {
210  OBJ,
211  ARR,
212  STR,
213  NUM,
214  BOOL,
215  NONE,
216  STR_AMOUNT,
217  STR_HEX,
218  OBJ_DYN,
219  ARR_FIXED,
220  NUM_TIME,
221  ELISION,
222  };
223 
224  const Type m_type;
225  const std::string m_key_name;
226  const std::vector<RPCResult> m_inner;
227  const bool m_optional;
228  const std::string m_description;
229  const std::string m_cond;
230 
232  const std::string cond,
233  const Type type,
234  const std::string m_key_name,
235  const bool optional,
236  const std::string description,
237  const std::vector<RPCResult> inner = {})
238  : m_type{std::move(type)},
239  m_key_name{std::move(m_key_name)},
240  m_inner{std::move(inner)},
241  m_optional{optional},
242  m_description{std::move(description)},
243  m_cond{std::move(cond)}
244  {
245  CHECK_NONFATAL(!m_cond.empty());
246  const bool inner_needed{type == Type::ARR || type == Type::ARR_FIXED || type == Type::OBJ || type == Type::OBJ_DYN};
247  CHECK_NONFATAL(inner_needed != inner.empty());
248  }
249 
251  const std::string cond,
252  const Type type,
253  const std::string m_key_name,
254  const std::string description,
255  const std::vector<RPCResult> inner = {})
256  : RPCResult{cond, type, m_key_name, false, description, inner} {}
257 
259  const Type type,
260  const std::string m_key_name,
261  const bool optional,
262  const std::string description,
263  const std::vector<RPCResult> inner = {})
264  : m_type{std::move(type)},
265  m_key_name{std::move(m_key_name)},
266  m_inner{std::move(inner)},
267  m_optional{optional},
268  m_description{std::move(description)},
269  m_cond{}
270  {
271  const bool inner_needed{type == Type::ARR || type == Type::ARR_FIXED || type == Type::OBJ || type == Type::OBJ_DYN};
272  CHECK_NONFATAL(inner_needed != inner.empty());
273  }
274 
276  const Type type,
277  const std::string m_key_name,
278  const std::string description,
279  const std::vector<RPCResult> inner = {})
280  : RPCResult{type, m_key_name, false, description, inner} {}
281 
283  void ToSections(Sections& sections, OuterType outer_type = OuterType::NONE, const int current_indent = 0) const;
285  std::string ToStringObj() const;
287  std::string ToDescriptionString() const;
288 };
289 
290 struct RPCResults {
291  const std::vector<RPCResult> m_results;
292 
294  : m_results{{result}}
295  {
296  }
297 
298  RPCResults(std::initializer_list<RPCResult> results)
299  : m_results{results}
300  {
301  }
302 
306  std::string ToDescriptionString() const;
307 };
308 
309 struct RPCExamples {
310  const std::string m_examples;
311  explicit RPCExamples(
312  std::string examples)
313  : m_examples(std::move(examples))
314  {
315  }
316  std::string ToDescriptionString() const;
317 };
318 
320 {
321 public:
322  RPCHelpMan(std::string name, std::string description, std::vector<RPCArg> args, RPCResults results, RPCExamples examples);
323 
324  std::string ToString() const;
326  bool IsValidNumArgs(size_t num_args) const;
331  inline void Check(const JSONRPCRequest& request) const {
332  if (request.fHelp || !IsValidNumArgs(request.params.size())) {
333  throw std::runtime_error(ToString());
334  }
335  }
336 
337 private:
338  const std::string m_name;
339  const std::string m_description;
340  const std::vector<RPCArg> m_args;
343 };
344 
345 #endif // BITCOIN_RPC_UTIL_H
UniValue DescribeAddress(const CTxDestination &dest)
Definition: util.cpp:247
std::string HelpExampleCli(const std::string &methodname, const std::string &args)
Definition: util.cpp:112
UniValueType(UniValue::VType _type)
Definition: util.h:45
void RPCTypeCheck(const UniValue &params, const std::list< UniValueType > &typesExpected, bool fAllowNull=false)
Type-check arguments; throws JSONRPCError if wrong type given.
Definition: util.cpp:19
uint256 ParseHashV(const UniValue &v, std::string strName)
Utilities: convert hex-encoded Values (throws error if not hex).
Definition: util.cpp:85
std::vector< unsigned char > ParseHexV(const UniValue &v, std::string strName)
Definition: util.cpp:98
const std::vector< RPCResult > m_inner
Only used for arrays or dicts.
Definition: util.h:226
Type
Definition: util.h:116
std::vector< CScript > EvalDescriptorStringOrObject(const UniValue &scanobject, FlatSigningProvider &provider)
Evaluate a descriptor given as a string, or as a {"desc":...,"range":...} object, with default range ...
Definition: util.cpp:786
const Fallback m_fallback
Definition: util.h:148
ServiceFlags
nServices flags
Definition: protocol.h:243
uint256 ParseHashO(const UniValue &o, std::string strKey)
Definition: util.cpp:94
RPCResult(const Type type, const std::string m_key_name, const bool optional, const std::string description, const std::vector< RPCResult > inner={})
Definition: util.h:258
Keeps track of RPCArgs by transforming them into sections for the purpose of serializing everything t...
Definition: util.cpp:304
const std::string m_oneline_description
Should be empty unless it is supposed to override the auto-generated summary line.
Definition: util.h:150
const std::string m_name
The name of the arg (can be empty for inner args)
Definition: util.h:145
const std::string UNIX_EPOCH_TIME
String used to describe UNIX epoch time in documentation, factored out to a constant for consistency...
Definition: util.cpp:16
bool typeAny
Definition: util.h:47
CPubKey AddrToPubKey(const FillableSigningProvider &keystore, const std::string &addr_in)
Definition: util.cpp:137
CPubKey HexToPubKey(const std::string &hex_in)
Definition: util.cpp:124
const std::string EXAMPLE_ADDRESS[2]
Example bech32 addresses for the RPCExamples help documentation.
Definition: util.cpp:17
#define CHECK_NONFATAL(condition)
Throw a NonFatalCheckError when the condition evaluates to false.
Definition: check.h:28
CAmount AmountFromValue(const UniValue &value)
Definition: util.cpp:73
const std::string m_key_name
Only used for dicts.
Definition: util.h:225
RPCResult(const Type type, const std::string m_key_name, const std::string description, const std::vector< RPCResult > inner={})
Definition: util.h:275
const RPCExamples m_examples
Definition: util.h:342
boost::variant< Optional, std::string > Fallback
Definition: util.h:144
RPCResult(const std::string cond, const Type type, const std::string m_key_name, const bool optional, const std::string description, const std::vector< RPCResult > inner={})
Definition: util.h:231
void Check(const JSONRPCRequest &request) const
Check if the given request is valid according to this command or if the user is asking for help infor...
Definition: util.h:331
const std::vector< RPCArg > m_inner
Only used for arrays or dicts.
Definition: util.h:147
OutputType
Definition: outputtype.h:17
const std::string m_cond
Definition: util.h:229
void RPCTypeCheckArgument(const UniValue &value, const UniValueType &typeExpected)
Type-check one argument; throws JSONRPCError if wrong type given.
Definition: util.cpp:36
RPCErrorCode RPCErrorFromTransactionError(TransactionError terr)
Definition: util.cpp:261
const Type m_type
Definition: util.h:224
UniValue::VType type
Definition: util.h:48
const std::string m_description
Definition: util.h:339
int64_t CAmount
Amount in satoshis (Can be negative)
Definition: amount.h:12
void RPCTypeCheckObj(const UniValue &o, const std::map< std::string, UniValueType > &typesExpected, bool fAllowNull=false, bool fStrict=false)
Definition: util.cpp:43
std::string ToString(const T &t)
Locale-independent version of std::to_string.
Definition: string.h:61
Definition: util.h:115
CTxDestination AddAndGetMultisigDestination(const int required, const std::vector< CPubKey > &pubkeys, OutputType type, FillableSigningProvider &keystore, CScript &script_out)
Definition: util.cpp:158
UniValue params
Definition: request.h:32
const char * name
Definition: rest.cpp:40
RPCArg(const std::string name, const Type type, const Fallback fallback, const std::string description, const std::string oneline_description="", const std::vector< std::string > type_str={})
Definition: util.h:153
RPCResults(std::initializer_list< RPCResult > results)
Definition: util.h:298
An encapsulated public key.
Definition: pubkey.h:30
Fillable signing provider that keeps keys in an address->secret map.
UniValue GetServicesNames(ServiceFlags services)
Returns, given services flags, a list of humanly readable (known) network services.
Definition: util.cpp:824
unsigned int ParseConfirmTarget(const UniValue &value, unsigned int max_target)
Parse a confirm target option and raise an RPC error if it is invalid.
Definition: util.cpp:252
const std::vector< RPCResult > m_results
Definition: util.h:291
std::string HelpExampleRpc(const std::string &methodname, const std::string &args)
Definition: util.cpp:117
const std::vector< RPCArg > m_args
Definition: util.h:340
const std::string m_description
Definition: util.h:149
UniValue JSONRPCTransactionError(TransactionError terr, const std::string &err_string="")
Definition: util.cpp:280
const std::string m_examples
Definition: util.h:310
const std::vector< std::string > m_type_str
Should be empty unless it is supposed to override the auto-generated type strings. Vector length is either 0 or 2, m_type_str.at(0) will override the type of the value in a key-value pair, m_type_str.at(1) will override the type in the argument description.
Definition: util.h:151
const RPCResults m_results
Definition: util.h:341
bool fHelp
Definition: request.h:33
OuterType
Serializing JSON objects depends on the outer type.
Definition: util.h:109
256-bit opaque blob.
Definition: uint256.h:120
UniValueType()
Definition: util.h:46
Serialized script, used inside transaction inputs and outputs.
Definition: script.h:390
Optional
Definition: util.h:128
const std::string m_description
Definition: util.h:228
TransactionError
Definition: error.h:22
RPCResults(RPCResult result)
Definition: util.h:293
RPCResult(const std::string cond, const Type type, const std::string m_key_name, const std::string description, const std::vector< RPCResult > inner={})
Definition: util.h:250
const Type m_type
Definition: util.h:146
RPCArg(const std::string name, const Type type, const Fallback fallback, const std::string description, const std::vector< RPCArg > inner, const std::string oneline_description="", const std::vector< std::string > type_str={})
Definition: util.h:170
RPCExamples(std::string examples)
Definition: util.h:311
const bool m_optional
Definition: util.h:227
size_t size() const
Definition: univalue.h:68
boost::optional< T > Optional
Substitute for C++17 std::optional.
Definition: optional.h:14
const std::string m_name
Definition: util.h:338
RPCErrorCode
Bitcoin RPC error codes.
Definition: protocol.h:23
boost::variant< CNoDestination, PKHash, ScriptHash, WitnessV0ScriptHash, WitnessV0KeyHash, WitnessUnknown > CTxDestination
A txout script template with a specific destination.
Definition: standard.h:143
std::pair< int64_t, int64_t > ParseDescriptorRange(const UniValue &value)
Parse a JSON range specified as int64, or [int64, int64].
Definition: util.cpp:770
Wrapper for UniValue::VType, which includes typeAny: Used to denote don&#39;t care type.
Definition: util.h:44
std::vector< unsigned char > ParseHexO(const UniValue &o, std::string strKey)
Definition: util.cpp:107