rpc: Add getnodeaddresses JSON-RPC support
Add NodeAddresses function to rpcserverConnManager interface for fetching known node addresses.
This commit is contained in:
parent
9ef973c282
commit
fff96610aa
7 changed files with 150 additions and 0 deletions
|
@ -557,6 +557,22 @@ func NewGetNetworkHashPSCmd(numBlocks, height *int) *GetNetworkHashPSCmd {
|
|||
}
|
||||
}
|
||||
|
||||
// GetNodeAddressesCmd defines the getnodeaddresses JSON-RPC command.
|
||||
type GetNodeAddressesCmd struct {
|
||||
Count *int32 `jsonrpcdefault:"1"`
|
||||
}
|
||||
|
||||
// NewGetNodeAddressesCmd returns a new instance which can be used to issue a
|
||||
// getnodeaddresses JSON-RPC command.
|
||||
//
|
||||
// The parameters which are pointers indicate they are optional. Passing nil
|
||||
// for optional parameters will use the default value.
|
||||
func NewGetNodeAddressesCmd(count *int32) *GetNodeAddressesCmd {
|
||||
return &GetNodeAddressesCmd{
|
||||
Count: count,
|
||||
}
|
||||
}
|
||||
|
||||
// GetPeerInfoCmd defines the getpeerinfo JSON-RPC command.
|
||||
type GetPeerInfoCmd struct{}
|
||||
|
||||
|
@ -974,6 +990,7 @@ func init() {
|
|||
MustRegisterCmd("getnetworkinfo", (*GetNetworkInfoCmd)(nil), flags)
|
||||
MustRegisterCmd("getnettotals", (*GetNetTotalsCmd)(nil), flags)
|
||||
MustRegisterCmd("getnetworkhashps", (*GetNetworkHashPSCmd)(nil), flags)
|
||||
MustRegisterCmd("getnodeaddresses", (*GetNodeAddressesCmd)(nil), flags)
|
||||
MustRegisterCmd("getpeerinfo", (*GetPeerInfoCmd)(nil), flags)
|
||||
MustRegisterCmd("getrawmempool", (*GetRawMempoolCmd)(nil), flags)
|
||||
MustRegisterCmd("getrawtransaction", (*GetRawTransactionCmd)(nil), flags)
|
||||
|
|
|
@ -753,6 +753,32 @@ func TestChainSvrCmds(t *testing.T) {
|
|||
Height: btcjson.Int(123),
|
||||
},
|
||||
},
|
||||
{
|
||||
name: "getnodeaddresses",
|
||||
newCmd: func() (interface{}, error) {
|
||||
return btcjson.NewCmd("getnodeaddresses")
|
||||
},
|
||||
staticCmd: func() interface{} {
|
||||
return btcjson.NewGetNodeAddressesCmd(nil)
|
||||
},
|
||||
marshalled: `{"jsonrpc":"1.0","method":"getnodeaddresses","params":[],"id":1}`,
|
||||
unmarshalled: &btcjson.GetNodeAddressesCmd{
|
||||
Count: btcjson.Int32(1),
|
||||
},
|
||||
},
|
||||
{
|
||||
name: "getnodeaddresses optional",
|
||||
newCmd: func() (interface{}, error) {
|
||||
return btcjson.NewCmd("getnodeaddresses", 10)
|
||||
},
|
||||
staticCmd: func() interface{} {
|
||||
return btcjson.NewGetNodeAddressesCmd(btcjson.Int32(10))
|
||||
},
|
||||
marshalled: `{"jsonrpc":"1.0","method":"getnodeaddresses","params":[10],"id":1}`,
|
||||
unmarshalled: &btcjson.GetNodeAddressesCmd{
|
||||
Count: btcjson.Int32(10),
|
||||
},
|
||||
},
|
||||
{
|
||||
name: "getpeerinfo",
|
||||
newCmd: func() (interface{}, error) {
|
||||
|
|
|
@ -365,6 +365,16 @@ type GetNetworkInfoResult struct {
|
|||
Warnings string `json:"warnings"`
|
||||
}
|
||||
|
||||
// GetNodeAddressesResult models the data returned from the getnodeaddresses
|
||||
// command.
|
||||
type GetNodeAddressesResult struct {
|
||||
// Timestamp in seconds since epoch (Jan 1 1970 GMT) keeping track of when the node was last seen
|
||||
Time int64 `json:"time"`
|
||||
Services uint64 `json:"services"` // The services offered
|
||||
Address string `json:"address"` // The address of the node
|
||||
Port uint16 `json:"port"` // The port of the node
|
||||
}
|
||||
|
||||
// GetPeerInfoResult models the data returned from the getpeerinfo command.
|
||||
type GetPeerInfoResult struct {
|
||||
ID int32 `json:"id"`
|
||||
|
|
|
@ -223,6 +223,15 @@ func (cm *rpcConnManager) RelayTransactions(txns []*mempool.TxDesc) {
|
|||
cm.server.relayTransactions(txns)
|
||||
}
|
||||
|
||||
// NodeAddresses returns an array consisting node addresses which can
|
||||
// potentially be used to find new nodes in the network.
|
||||
//
|
||||
// This function is safe for concurrent access and is part of the
|
||||
// rpcserverConnManager interface implementation.
|
||||
func (cm *rpcConnManager) NodeAddresses() []*wire.NetAddress {
|
||||
return cm.server.addrManager.AddressCache()
|
||||
}
|
||||
|
||||
// rpcSyncMgr provides a block manager for use with the RPC server and
|
||||
// implements the rpcserverSyncManager interface.
|
||||
type rpcSyncMgr struct {
|
||||
|
|
|
@ -281,6 +281,43 @@ func (c *Client) GetNetworkInfo() (*btcjson.GetNetworkInfoResult, error) {
|
|||
return c.GetNetworkInfoAsync().Receive()
|
||||
}
|
||||
|
||||
// FutureGetNodeAddressesResult is a future promise to deliver the result of a
|
||||
// GetNodeAddressesAsync RPC invocation (or an applicable error).
|
||||
type FutureGetNodeAddressesResult chan *response
|
||||
|
||||
// Receive waits for the response promised by the future and returns data about
|
||||
// known node addresses.
|
||||
func (r FutureGetNodeAddressesResult) Receive() ([]btcjson.GetNodeAddressesResult, error) {
|
||||
res, err := receiveFuture(r)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
// Unmarshal result as an array of getnodeaddresses result objects.
|
||||
var nodeAddresses []btcjson.GetNodeAddressesResult
|
||||
err = json.Unmarshal(res, &nodeAddresses)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
return nodeAddresses, nil
|
||||
}
|
||||
|
||||
// GetNodeAddressesAsync returns an instance of a type that can be used to get the
|
||||
// result of the RPC at some future time by invoking the Receive function on the
|
||||
// returned instance.
|
||||
//
|
||||
// See GetNodeAddresses for the blocking version and more details.
|
||||
func (c *Client) GetNodeAddressesAsync(count *int32) FutureGetNodeAddressesResult {
|
||||
cmd := btcjson.NewGetNodeAddressesCmd(count)
|
||||
return c.sendCmd(cmd)
|
||||
}
|
||||
|
||||
// GetNodeAddresses returns data about known node addresses.
|
||||
func (c *Client) GetNodeAddresses(count *int32) ([]btcjson.GetNodeAddressesResult, error) {
|
||||
return c.GetNodeAddressesAsync(count).Receive()
|
||||
}
|
||||
|
||||
// FutureGetPeerInfoResult is a future promise to deliver the result of a
|
||||
// GetPeerInfoAsync RPC invocation (or an applicable error).
|
||||
type FutureGetPeerInfoResult chan *response
|
||||
|
|
39
rpcserver.go
39
rpcserver.go
|
@ -156,6 +156,7 @@ var rpcHandlersBeforeInit = map[string]commandHandler{
|
|||
"getmininginfo": handleGetMiningInfo,
|
||||
"getnettotals": handleGetNetTotals,
|
||||
"getnetworkhashps": handleGetNetworkHashPS,
|
||||
"getnodeaddresses": handleGetNodeAddresses,
|
||||
"getpeerinfo": handleGetPeerInfo,
|
||||
"getrawmempool": handleGetRawMempool,
|
||||
"getrawtransaction": handleGetRawTransaction,
|
||||
|
@ -2477,6 +2478,40 @@ func handleGetNetworkHashPS(s *rpcServer, cmd interface{}, closeChan <-chan stru
|
|||
return hashesPerSec.Int64(), nil
|
||||
}
|
||||
|
||||
// handleGetNodeAddresses implements the getnodeaddresses command.
|
||||
func handleGetNodeAddresses(s *rpcServer, cmd interface{}, closeChan <-chan struct{}) (interface{}, error) {
|
||||
c := cmd.(*btcjson.GetNodeAddressesCmd)
|
||||
|
||||
count := int32(1)
|
||||
if c.Count != nil {
|
||||
count = *c.Count
|
||||
if count <= 0 {
|
||||
return nil, &btcjson.RPCError{
|
||||
Code: btcjson.ErrRPCInvalidParameter,
|
||||
Message: "Address count out of range",
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
nodes := s.cfg.ConnMgr.NodeAddresses()
|
||||
if n := int32(len(nodes)); n < count {
|
||||
count = n
|
||||
}
|
||||
|
||||
addresses := make([]*btcjson.GetNodeAddressesResult, 0, count)
|
||||
for _, node := range nodes[:count] {
|
||||
address := &btcjson.GetNodeAddressesResult{
|
||||
Time: node.Timestamp.Unix(),
|
||||
Services: uint64(node.Services),
|
||||
Address: node.IP.String(),
|
||||
Port: node.Port,
|
||||
}
|
||||
addresses = append(addresses, address)
|
||||
}
|
||||
|
||||
return addresses, nil
|
||||
}
|
||||
|
||||
// handleGetPeerInfo implements the getpeerinfo command.
|
||||
func handleGetPeerInfo(s *rpcServer, cmd interface{}, closeChan <-chan struct{}) (interface{}, error) {
|
||||
peers := s.cfg.ConnMgr.ConnectedPeers()
|
||||
|
@ -4298,6 +4333,10 @@ type rpcserverConnManager interface {
|
|||
// RelayTransactions generates and relays inventory vectors for all of
|
||||
// the passed transactions to all connected peers.
|
||||
RelayTransactions(txns []*mempool.TxDesc)
|
||||
|
||||
// NodeAddresses returns an array consisting node addresses which can
|
||||
// potentially be used to find new nodes in the network.
|
||||
NodeAddresses() []*wire.NetAddress
|
||||
}
|
||||
|
||||
// rpcserverSyncManager represents a sync manager for use with the RPC server.
|
||||
|
|
|
@ -452,6 +452,17 @@ var helpDescsEnUS = map[string]string{
|
|||
"getnettotalsresult-totalbytessent": "Total bytes sent",
|
||||
"getnettotalsresult-timemillis": "Number of milliseconds since 1 Jan 1970 GMT",
|
||||
|
||||
// GetNodeAddressesResult help.
|
||||
"getnodeaddressesresult-time": "Timestamp in seconds since epoch (Jan 1 1970 GMT) keeping track of when the node was last seen",
|
||||
"getnodeaddressesresult-services": "The services offered",
|
||||
"getnodeaddressesresult-address": "The address of the node",
|
||||
"getnodeaddressesresult-port": "The port of the node",
|
||||
|
||||
// GetNodeAddressesCmd help.
|
||||
"getnodeaddresses--synopsis": "Return known addresses which can potentially be used to find new nodes in the network",
|
||||
"getnodeaddresses-count": "How many addresses to return. Limited to the smaller of 2500 or 23% of all known addresses",
|
||||
"getnodeaddresses--result0": "List of node addresses",
|
||||
|
||||
// GetPeerInfoResult help.
|
||||
"getpeerinforesult-id": "A unique node ID",
|
||||
"getpeerinforesult-addr": "The ip address and port of the peer",
|
||||
|
@ -726,6 +737,7 @@ var rpcResultTypes = map[string][]interface{}{
|
|||
"getmininginfo": {(*btcjson.GetMiningInfoResult)(nil)},
|
||||
"getnettotals": {(*btcjson.GetNetTotalsResult)(nil)},
|
||||
"getnetworkhashps": {(*int64)(nil)},
|
||||
"getnodeaddresses": {(*[]btcjson.GetNodeAddressesResult)(nil)},
|
||||
"getpeerinfo": {(*[]btcjson.GetPeerInfoResult)(nil)},
|
||||
"getrawmempool": {(*[]string)(nil), (*btcjson.GetRawMempoolVerboseResult)(nil)},
|
||||
"getrawtransaction": {(*string)(nil), (*btcjson.TxRawResult)(nil)},
|
||||
|
|
Loading…
Reference in a new issue