Skip to content

Conversation

laanwj
Copy link
Member

@laanwj laanwj commented Sep 29, 2016

(follow-up to #8780)

There have been some requests for a client-side getinfo and this is my PoC of how to do it. The high-level idea is to have one command to gather and show various information and statistics about a bitcoind in one go.

This could be used as an opportunity to make getinfo better, it doesn't have to have exactly the same fields as the original RPC, e.g. a chain instead of testnet flag would make sense (but it is currently the same, according to this table: #8455 (comment)).

If this is considered a good idea some of the logic could be moved up to rpcclient.cpp and used in the GUI console as well.

Implementation

This adds the infrastructure BaseRequestHandler class that takes care of converting bitcoin-cli arguments into a JSON-RPC request object, and converting the reply into a JSON object that can be shown as result.

This is subsequently used to handle the -getinfo option, which sends a JSON-RPC batch request to the RPC server with ["getnetworkinfo", "getblockchaininfo", "getwalletinfo"], and after reply combines the result into what looks like a getinfo result.

@sipa
Copy link
Member

sipa commented Oct 4, 2016

Concept ACK. This allows us to maintain backward compatibility with "bitcoin-cli getinfo" without keeping it at the RPC level. Should "-getinfo" automatically trigger when the getinfo RPC is requested?

@laanwj
Copy link
Member Author

laanwj commented Oct 4, 2016

Should "-getinfo" automatically trigger when the getinfo RPC is requested?

Not sure about that. That's how I had it first but this would blur the line between what bitcoin-cli calls an RPC call and what is actually available on the API endpoint.

Maybe "bitcoin-cli getinfo" if it fails (with the code that the call is missing) could print an helpful message to use "-getinfo" instead.

@luke-jr
Copy link
Member

luke-jr commented Oct 4, 2016

Eh, IMO the only backward-compatibility need for getinfo is at the RPC level. RPC isn't really designed for end users, and in any case, end users can adapt to changes easier than legacy software making RPC calls.

I don't particularly care about whether -getinfo is added to bitcoin-cli, but it doesn't seem like a viable migration path or substitute for the getinfo RPC.

@laanwj
Copy link
Member Author

laanwj commented Oct 4, 2016

I don't particularly care about whether -getinfo is added to bitcoin-cli, but it doesn't seem like a viable migration path or substitute for the getinfo RPC.

You are right that RPC is not there for end users.
However, bitcoin-cli is there for end users, and many people use bitcoind+bitcoin-cli as a console wallet.

This is not just for backwards-compatibility. As I say in my OP

The high-level idea is to have one command to gather and show various information and statistics about a bitcoind in one go.

I'd be fine with completely different output here. However, the idea of having a single command that combines and prints various status information makes sense, IMO.

@laanwj
Copy link
Member Author

laanwj commented Oct 4, 2016

And yes, this could be an external Python script too. I don't really care. Although history has shown that those scripts hardly get maintained nor used, e.g. remember contrib/bitrpc? Thought so.

(so if that is a requirement I'm just going to keep it as a private script and not bother with this, this may be too much of an ego-PR anyway)

@laanwj laanwj closed this Oct 4, 2016
@laanwj
Copy link
Member Author

laanwj commented Jun 15, 2017

Reopening after IRC discussion.

@laanwj laanwj reopened this Jun 15, 2017
This adds the infrastructure `BaseRequestHandler` class that takes care
of converting bitcoin-cli arguments into a JSON-RPC request object, and
converting the reply into a JSON object that can be shown as result.

This is subsequently used to handle the `-getinfo` option, which sends
a JSON-RPC batch request to the RPC server with
`["getnetworkinfo", "getblockchaininfo", "getwalletinfo"]`,
and after reply combines the result into what looks like a `getinfo`
result.

There have been some requests for a client-side `getinfo` and this
is my PoC of how to do it. If this is considered a good idea
some of the logic could be moved up to rpcclient.cpp and
used in the GUI console as well.
@laanwj laanwj force-pushed the 2016_09_getinfo_clientside branch from 9552a3a to 157f0bf Compare June 15, 2017 20:28
@laanwj
Copy link
Member Author

laanwj commented Jun 15, 2017

rebased

Copy link
Contributor

@jnewbery jnewbery left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Looks good.

Should "-getinfo" automatically trigger when the getinfo RPC is requested?

That's how I had it first but this would blur the line between what bitcoin-cli calls an RPC call and what is actually available on the API endpoint.

I think bitcoin-cli getinfo should continue to work. I would also lean towards not using the bitcoin-cli -getinfo form. Yes, it's a bit magic, but it would mean maximum compatibility with any scripts, etc that are calling bitcoin-cli getinfo, and there'd be no excuse to not remove the actual RPC. If you're feeling really fastidious, you could add an extra "warnings" field to the returned object to say that getinfo isn't a real RPC. The returned object already has an "errors" field, so that wouldn't look too strange.

It's a shame that we don't have support in test/functional for bitcoin-cli tests. I don't think it's worth adding that just for this new function, but longer term we should aim to add tests.

Just one piece of functional feedback, and a couple of nits.

@@ -46,6 +46,7 @@ std::string HelpMessageCli()
strUsage += HelpMessageOpt("-rpcpassword=<pw>", _("Password for JSON-RPC connections"));
strUsage += HelpMessageOpt("-rpcclienttimeout=<n>", strprintf(_("Timeout in seconds during HTTP requests, or 0 for no timeout. (default: %d)"), DEFAULT_HTTP_CLIENT_TIMEOUT));
strUsage += HelpMessageOpt("-stdin", _("Read extra arguments from standard input, one per line until EOF/Ctrl-D (recommended for sensitive information such as passphrases)"));
strUsage += HelpMessageOpt("-getinfo", _("Get general information from the remote server"));
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

nit: please place alphabetically within help messages.

std::string strRequest = JSONRPCRequestObj(strMethod, params, 1).write() + "\n";
struct evbuffer* output_buffer = evhttp_request_get_output_buffer(req.get());
std::string strRequest = rh->PrepareRequest(strMethod, args).write() + "\n";
struct evbuffer * output_buffer = evhttp_request_get_output_buffer(req.get());
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

nit: why add a space here?

result.pushKV("testnet", UniValue(batch[ID_BLOCKCHAININFO]["result"]["chain"].get_str() == "test"));
if (!batch[ID_WALLETINFO].isNull()) {
result.pushKV("keypoololdest", batch[ID_WALLETINFO]["result"]["keypoololdest"]);
result.pushKV("keypoolsize", batch[ID_WALLETINFO]["result"]["keypoolsize"]);
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

slight incompatibility here since HD split. For HD split wallets, keypoolsize refers to the size of the external keypool, and there's a new field returned in getwalletinfo called keypoolsize_hd_internal, which refers to the size of the internal keypool. This implementation should return the sum of those two if keypoolsize_hd_internal exists.

Otherwise:

→ bitcoin-cli getinfo
{
  "version": 149900,
...
  "keypoolsize": 199,
...
}

→ bitcoin-cli -getinfo
{
  "version": 149900,
...
  "keypoolsize": 99,
...
}

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actually, I've got this backwards. getinfo should be updated to be consistent with getwalletinfo, not making -getinfo consistent with the incorrect getinfo.

I think that can be done as a separate commit in this PR. Let me know if you want me to make a branch with that commit.

@@ -124,3 +124,19 @@ void DeleteAuthCookie()
}
}

std::vector<UniValue> JSONRPCProcessBatchReply(const UniValue &in, size_t num)
{
if (!in.isArray())
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

nit: new code so should use braces for if blocks (sorry!)

@jnewbery
Copy link
Contributor

I'd love for this to make it in to v0.15.0, to ease the removal of getinfo in (hopefully) v0.15.1.

@fanquake fanquake added this to the 0.15.0 milestone Jul 16, 2017
@TheBlueMatt
Copy link
Contributor

I am concerned that this breaks the atomicity of the previously-atomic RPC getinfo, which may be very surprising for users. I'm not sure how much it matters if you get inconsistent data in results from bitcoin-cli, since most automated things will likely be using RPC directly, but I'm not convinced it is a great direction.

@promag
Copy link
Contributor

promag commented Jul 16, 2017

NACK. Keep it simple for cli. IMO this is a good example for what to not do in a cli and can lead to others do the same in their cli.. This doesn't break atomicity as there is no getinfo, at the very least that should be a concern in #8843. The ones requesting getinfo should either just make the calls or understand what they really need.

@jnewbery
Copy link
Contributor

I'm not convinced it is a great direction

this is a good example for what to not do in a cli and can lead to others do the same in their cli

Idealogical purity is fine in its place, but this is an isolated change to help those who are currently use getinfo from the command line. I don't think it sets a precedent for doing more hacks with the cli.

Perhaps don't document this? Or document it as a debug option? Would that be better?

To be clear: I'm not advocating strongly for this PR. If the consensus view is that this is not required to remove getinfo then I'm happy to go along with that. However, I'm certainly not concerned about it setting precedent and I don't think that a good reason to not merge this.

@TheBlueMatt
Copy link
Contributor

TheBlueMatt commented Jul 17, 2017 via email

@laanwj
Copy link
Member Author

laanwj commented Jul 17, 2017

Closing this, I don't feel like addressing the atomicity concern, it seems arbitrary, never came up before, and a way to call multiple RPC calls atomically is WAY out of scope for this. Not going to maintain this anymore.

@promag
Copy link
Contributor

promag commented Jul 17, 2017

but this is an isolated change to help those who are currently use getinfo from the command line

@jnewbery that's what deprecation is for.

Forcing the client to make separate calls clarifies that somewhat.

@TheBlueMatt I totally agree with you! Sorry if I wasn't clear.

@laanwj IMO best solution is to add support for http://www.jsonrpc.org/specification#batch, where the locks are held while handling the batch request.

@laanwj
Copy link
Member Author

laanwj commented Jul 17, 2017 via email

@laanwj
Copy link
Member Author

laanwj commented Jul 17, 2017 via email

@promag
Copy link
Contributor

promag commented Jul 17, 2017

I use a batch in the implementation of this!

@laanwj sorry I've overlook the code and did not realize there is already support for server side batch requests.

👍 for custom scripting.

jnewbery pushed a commit to jnewbery/bitcoin that referenced this pull request Aug 23, 2017
luke-jr pushed a commit to bitcoinknots/bitcoin that referenced this pull request Sep 2, 2017
laanwj added a commit that referenced this pull request Sep 28, 2017
…8843)

5e69a43 Add test for bitcoin-cli -getinfo (John Newbery)
3826253 rpc: Handle `getinfo` locally in bitcoin-cli w/ `-getinfo` (Wladimir J. van der Laan)

Pull request description:

  Since @laanwj doesn't want to maintain these changes anymore, I will.

  This PR is a revival of #8843. I have addressed @jnewbery's comments.

  Regarding atomicity, I don't think that is a concern here. This is explicitly a new API and those who use it will know that this is different and that it is not atomic.

Tree-SHA512: 9664ed13a5557bda8c43f34d6527669a641f260b7830e592409b28c845258fc7e0fdd85dd42bfa88c103fea3ecdfede5f81e3d91870e2accba81c6d6de6b21ff
PastaPastaPasta pushed a commit to PastaPastaPasta/dash that referenced this pull request Feb 13, 2020
…al of bitcoin#8843)

5e69a43 Add test for bitcoin-cli -getinfo (John Newbery)
3826253 rpc: Handle `getinfo` locally in bitcoin-cli w/ `-getinfo` (Wladimir J. van der Laan)

Pull request description:

  Since @laanwj doesn't want to maintain these changes anymore, I will.

  This PR is a revival of bitcoin#8843. I have addressed @jnewbery's comments.

  Regarding atomicity, I don't think that is a concern here. This is explicitly a new API and those who use it will know that this is different and that it is not atomic.

Tree-SHA512: 9664ed13a5557bda8c43f34d6527669a641f260b7830e592409b28c845258fc7e0fdd85dd42bfa88c103fea3ecdfede5f81e3d91870e2accba81c6d6de6b21ff
PastaPastaPasta pushed a commit to PastaPastaPasta/dash that referenced this pull request Feb 13, 2020
…al of bitcoin#8843)

5e69a43 Add test for bitcoin-cli -getinfo (John Newbery)
3826253 rpc: Handle `getinfo` locally in bitcoin-cli w/ `-getinfo` (Wladimir J. van der Laan)

Pull request description:

  Since @laanwj doesn't want to maintain these changes anymore, I will.

  This PR is a revival of bitcoin#8843. I have addressed @jnewbery's comments.

  Regarding atomicity, I don't think that is a concern here. This is explicitly a new API and those who use it will know that this is different and that it is not atomic.

Tree-SHA512: 9664ed13a5557bda8c43f34d6527669a641f260b7830e592409b28c845258fc7e0fdd85dd42bfa88c103fea3ecdfede5f81e3d91870e2accba81c6d6de6b21ff
PastaPastaPasta pushed a commit to PastaPastaPasta/dash that referenced this pull request Feb 29, 2020
…al of bitcoin#8843)

5e69a43 Add test for bitcoin-cli -getinfo (John Newbery)
3826253 rpc: Handle `getinfo` locally in bitcoin-cli w/ `-getinfo` (Wladimir J. van der Laan)

Pull request description:

  Since @laanwj doesn't want to maintain these changes anymore, I will.

  This PR is a revival of bitcoin#8843. I have addressed @jnewbery's comments.

  Regarding atomicity, I don't think that is a concern here. This is explicitly a new API and those who use it will know that this is different and that it is not atomic.

Tree-SHA512: 9664ed13a5557bda8c43f34d6527669a641f260b7830e592409b28c845258fc7e0fdd85dd42bfa88c103fea3ecdfede5f81e3d91870e2accba81c6d6de6b21ff
@bitcoin bitcoin locked as resolved and limited conversation to collaborators Sep 8, 2021
Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Projects
None yet
Development

Successfully merging this pull request may close these issues.

7 participants