-
Notifications
You must be signed in to change notification settings - Fork 2.4k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
rpcclient: Add getblockfilter JSON-RPC client command #1579
Conversation
// NewGetBlockFilterCmd returns a new instance which can be used to issue a | ||
// getblockfilter JSON-RPC command. |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
We generally add the following comment whenever there are optional arguments.
// NewGetBlockFilterCmd returns a new instance which can be used to issue a | |
// getblockfilter JSON-RPC command. | |
// NewGetBlockFilterCmd returns a new instance which can be used to issue a | |
// getblockfilter JSON-RPC command. | |
// | |
// The parameters which are pointers indicate they are optional. Passing nil | |
// for optional parameters will use the default value. |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Right on. Added these.
btcjson/chainsvrresults.go
Outdated
Filter string `json:"filter"` | ||
Header string `json:"header"` |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Nit: Whenever possible, adding extra comments always helps, since it shows up beautifully on pkg.go.dev.
Filter string `json:"filter"` | |
Header string `json:"header"` | |
Filter string `json:"filter"` // the hex-encoded filter data | |
Header string `json:"header"` // the hex-encoded filter header |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Good shout makes the result easier to consume. Didn't consider pkg.go.dev
Also added comments to GetBlockFilterCmd
fields though they're not as visible through rpcclient
.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Looks good. 👍 Just added some minor remarks about comments.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I appended the changes to the original commit. Now I realised perhaps it would be easier for reviewers if I would have introduced fixes in a new commit and in the end you'd squash merge.
btcjson/chainsvrcmds.go
Outdated
@@ -163,6 +163,24 @@ func NewGetBlockCountCmd() *GetBlockCountCmd { | |||
return &GetBlockCountCmd{} | |||
} | |||
|
|||
// GetBlockFilterCmd defines the getblockfilter JSON-RPC command. | |||
type GetBlockFilterCmd struct { | |||
BlockHash string // The hash of the block |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I'd suggest using the chainhash.Hash
type here.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
These btcjson.*Cmd
structs are generally using basic types assigned through NewCmd constructors. btcjson.assignField
function makes a conversion from command-line input to the basic type that NewCmd takes.
While it's possible to implement JSON Unmarshaler to use a more specific type as you suggest I think the idea is to keep these types as stupid as possible.
In the JSON-RPC request the type will be string that the server has to unmarshal. Just taking the string from command-line and converting it to a JSON-RPC request without any semantic validation offloads the validation to server. Doing validation client-side would result in double validation which would be more fragile and more complex to consume.
As I see it GetBlockFilterCmd
defines the JSON-RPC command which shouldn't be aware of non-JSON types.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
rpcclient.GetBlockFilter
now takes chainhash.Hash
. rpcclient
is where to take the Golang call and transform it to JSON.
btcjson/chainsvrcmds.go
Outdated
// GetBlockFilterCmd defines the getblockfilter JSON-RPC command. | ||
type GetBlockFilterCmd struct { | ||
BlockHash string // The hash of the block | ||
FilterType *string // The type name of the filter, default=basic |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Looking at the Bitcoin Core codebase, "basic" is the only known filter type there. Are there any other known types out in the wild? Might make sense to create a custom type for this instead of passing in a string.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Haven't seen others than types basic
. Not sure how standard the filter names are but first see
my previous response about doing validation only server-side.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I can see that for instance in btcjson.AddNodeCmd
there is a custom type AddNodeSubCmd
being used but in that case the options are in the spec.
In case of getblockfilter the spec only mentions basic
which is the default anyway.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
BIP 157 describes that initial filter types are defined in BIP 158 which defines only the Basic
filter.
Bitcoin Core CLI seems to allow describing any getblockfilter
in a CLI command and will send the request server which will reject any unknown filter type name. I'd have the similar behavior in btcctl
and just handle this as a string.
In rpcclient
the second parameter of rpcclient.GetBlockFilter
could have a more specific type, for instance we can call it FilterTypeName
. For the server-side implementation of getblockfilter
to resolve the filter for the name we can map the basic FilterTypeName
to wire.GCSFilterRegular
.
I'll look at how to best implement FilterTypeName
. It seems a good idea for rpcclient
.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Good points about validation, as well as that in this specific scenario it might not be possible to construct a good type.
Just so you understand my reasoning: custom types are (at least for me) very beneficial when coding with btcd
packages as a library, because they limit the scope of possibilities and place you on a narrower path of "valid actions". Does this make sense?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Agreed definitely should have types for the rpcclient
API. Sorry about the fuss - with the way you suggested the CLI mechanism works just as well when defining FilterTypeName
as a type of string (facepalm)
Please see the new commit 9d7bd87
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
LGTM 🥇
func NewFilterTypeName(v FilterTypeName) *FilterTypeName { | ||
p := new(FilterTypeName) | ||
*p = v | ||
return p | ||
} |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Was about to comment that it might make sense to make the const FilterTypeBasic
a var
so it would be possible to do &FilterTypeBasic
, but seems like you already anticipated this and added a nice solution:-)
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Wasn't super happy about adding helper for this but it allows using const
instead of var
and is pretty consistent with how rpcclient
API is used
Add type for second getblockfilter param
@onyb @torkelrogstad Squashed ready to merge |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
The rpcclient implementation looks good, but since our existing getcfilter
does the exact same thing, I think we can just alias getblockfilter
to the existing code for GetCFilterCmd, and skip rewriting filter types.
@Rjected |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
@lindlof sorry for the late response. Yeah I get what you're saying now, unless we want to deviate from core we need these new types. If we ever decide to support this on the server side, we could potentially reuse implementation but yeah I don't see how the client implementation could really benefit from the type reuse.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
OK
Adds
getblockfilter
call to JSON-RPC client.