diff --git a/http/base/actor/net_server.go b/http/base/actor/net_server.go index 7715030d51..00c9a1dce0 100644 --- a/http/base/actor/net_server.go +++ b/http/base/actor/net_server.go @@ -61,6 +61,24 @@ func GetConnectionCnt() (uint32, error) { return r.Cnt, nil } +//GetMaxPeerBlockHeight from netSever actor +func GetMaxPeerBlockHeight() (uint64, error) { + if netServerPid == nil { + return 1, nil + } + future := netServerPid.RequestFuture(&ac.GetMaxPeerBlockHeightReq{}, REQ_TIMEOUT*time.Second) + result, err := future.Result() + if err != nil { + log.Errorf(ERR_ACTOR_COMM, err) + return 0, err + } + r, ok := result.(*ac.GetMaxPeerBlockHeightRsp) + if !ok { + return 0, errors.New("fail") + } + return r.MaxPeerBlockHeight, nil +} + //GetNeighborAddrs from netSever actor func GetNeighborAddrs() []common.PeerAddr { if netServerPid == nil { diff --git a/http/base/common/common.go b/http/base/common/common.go index fe801be7f5..21bfe244ba 100644 --- a/http/base/common/common.go +++ b/http/base/common/common.go @@ -499,3 +499,28 @@ func GetAddress(str string) (common.Address, error) { } return address, err } + +type SyncStatus struct { + CurrentBlockHeight uint32 + ConnectCount uint32 + MaxPeerBlockHeight uint64 +} + +func GetSyncStatus() (SyncStatus, error) { + var status SyncStatus + height, err := bactor.GetMaxPeerBlockHeight() + if err != nil { + return status, err + } + cnt, err := bactor.GetConnectionCnt() + if err != nil { + return status, err + } + curBlockHeight := bactor.GetCurrentBlockHeight() + + return SyncStatus{ + CurrentBlockHeight: curBlockHeight, + ConnectCount: cnt, + MaxPeerBlockHeight: height, + }, nil +} diff --git a/http/base/rest/interfaces.go b/http/base/rest/interfaces.go index fa13157c9e..221ef87376 100644 --- a/http/base/rest/interfaces.go +++ b/http/base/rest/interfaces.go @@ -64,6 +64,16 @@ func GetConnectionCount(cmd map[string]interface{}) map[string]interface{} { return resp } +func GetNodeSyncStatus(cmd map[string]interface{}) map[string]interface{} { + resp := ResponsePack(berr.SUCCESS) + status, err := bcomn.GetSyncStatus() + if err != nil { + return ResponsePack(berr.INTERNAL_ERROR) + } + resp["Result"] = status + return resp +} + //get block height func GetBlockHeight(cmd map[string]interface{}) map[string]interface{} { resp := ResponsePack(berr.SUCCESS) diff --git a/http/base/rpc/interfaces.go b/http/base/rpc/interfaces.go index 28337994ad..3852e1a77c 100644 --- a/http/base/rpc/interfaces.go +++ b/http/base/rpc/interfaces.go @@ -121,6 +121,17 @@ func GetConnectionCount(params []interface{}) map[string]interface{} { return responseSuccess(count) } +//get node connection most height +func GetSyncStatus(params []interface{}) map[string]interface{} { + status, err := bcomn.GetSyncStatus() + if err != nil { + log.Errorf("GetSyncStatus error:%s", err) + return responsePack(berr.INTERNAL_ERROR, false) + } + + return responseSuccess(status) +} + func GetRawMemPool(params []interface{}) map[string]interface{} { txs := []*bcomn.Transactions{} txpool := bactor.GetTxsFromPool(false) diff --git a/http/jsonrpc/rpc_server.go b/http/jsonrpc/rpc_server.go index e00f9f0149..60b5cd0041 100644 --- a/http/jsonrpc/rpc_server.go +++ b/http/jsonrpc/rpc_server.go @@ -38,6 +38,7 @@ func StartRPCServer() error { rpc.HandleFunc("getblockcount", rpc.GetBlockCount) rpc.HandleFunc("getblockhash", rpc.GetBlockHash) rpc.HandleFunc("getconnectioncount", rpc.GetConnectionCount) + rpc.HandleFunc("getsyncstatus", rpc.GetSyncStatus) //HandleFunc("getrawmempool", GetRawMemPool) rpc.HandleFunc("getrawtransaction", rpc.GetRawTransaction) diff --git a/http/restful/restful/server.go b/http/restful/restful/server.go index 52240e1d4b..a67ac24a07 100644 --- a/http/restful/restful/server.go +++ b/http/restful/restful/server.go @@ -54,6 +54,7 @@ type restServer struct { const ( GET_CONN_COUNT = "/api/v1/node/connectioncount" + GET_SYNC_STATUS = "/api/v1/node/syncstatus" GET_BLK_TXS_BY_HEIGHT = "/api/v1/block/transactions/height/:height" GET_BLK_BY_HEIGHT = "/api/v1/block/details/height/:height" GET_BLK_BY_HASH = "/api/v1/block/details/hash/:hash" @@ -134,6 +135,7 @@ func (this *restServer) registryMethod() { getMethodMap := map[string]Action{ GET_CONN_COUNT: {name: "getconnectioncount", handler: rest.GetConnectionCount}, + GET_SYNC_STATUS: {name: "getsyncstatus", handler: rest.GetNodeSyncStatus}, GET_BLK_TXS_BY_HEIGHT: {name: "getblocktxsbyheight", handler: rest.GetBlockTxsByHeight}, GET_BLK_BY_HEIGHT: {name: "getblockbyheight", handler: rest.GetBlockByHeight}, GET_BLK_BY_HASH: {name: "getblockbyhash", handler: rest.GetBlockByHash}, diff --git a/p2pserver/actor/server/actor.go b/p2pserver/actor/server/actor.go index 2de0169a56..be0965fe97 100644 --- a/p2pserver/actor/server/actor.go +++ b/p2pserver/actor/server/actor.go @@ -68,6 +68,8 @@ func (this *P2PActor) Receive(ctx actor.Context) { this.handleGetVersionReq(ctx, msg) case *GetConnectionCntReq: this.handleGetConnectionCntReq(ctx, msg) + case *GetMaxPeerBlockHeightReq: + this.handleGetMaxPeerBlockHeightReq(ctx, msg) case *GetIdReq: this.handleGetIDReq(ctx, msg) case *GetConnectionStateReq: @@ -140,6 +142,17 @@ func (this *P2PActor) handleGetConnectionCntReq(ctx actor.Context, req *GetConne } } +//max peer blockheight handler +func (this *P2PActor) handleGetMaxPeerBlockHeightReq(ctx actor.Context, req *GetMaxPeerBlockHeightReq) { + height := this.server.GetMaxPeerBlockHeight() + if ctx.Sender() != nil { + resp := &GetMaxPeerBlockHeightRsp{ + MaxPeerBlockHeight: height, + } + ctx.Sender().Request(resp, ctx.Self()) + } +} + //get id handler func (this *P2PActor) handleGetIDReq(ctx actor.Context, req *GetIdReq) { id := this.server.GetID() diff --git a/p2pserver/actor/server/common.go b/p2pserver/actor/server/common.go index a02eebcd5e..1b50419345 100644 --- a/p2pserver/actor/server/common.go +++ b/p2pserver/actor/server/common.go @@ -40,15 +40,24 @@ type GetVersionRsp struct { Version uint32 } -//connection count requet +//connection count request type GetConnectionCntReq struct { } -//response of connection count requet +//response of connection count request type GetConnectionCntRsp struct { Cnt uint32 } +//request of max peer block height +type GetMaxPeerBlockHeightReq struct { +} + +//response of max peer block height +type GetMaxPeerBlockHeightRsp struct { + MaxPeerBlockHeight uint64 +} + //get net module id type GetIdReq struct { } diff --git a/p2pserver/net/netserver/netserver.go b/p2pserver/net/netserver/netserver.go index 19aa1ffdb9..83e866398b 100644 --- a/p2pserver/net/netserver/netserver.go +++ b/p2pserver/net/netserver/netserver.go @@ -193,6 +193,11 @@ func (this *NetServer) GetConnectionCnt() uint32 { return this.Np.GetNbrNodeCnt() } +//GetMaxPeerBlockHeight return the most height of valid connections +func (this *NetServer) GetMaxPeerBlockHeight() uint64 { + return this.Np.GetNeighborMostHeight() +} + //AddNbrNode add peer to nbr peer list func (this *NetServer) AddNbrNode(remotePeer *peer.Peer) { this.Np.AddNbrNode(remotePeer) diff --git a/p2pserver/net/protocol/server.go b/p2pserver/net/protocol/server.go index 30d0107aef..615d0b04f1 100644 --- a/p2pserver/net/protocol/server.go +++ b/p2pserver/net/protocol/server.go @@ -41,6 +41,7 @@ type P2P interface { GetNeighbors() []*peer.Peer GetNeighborAddrs() []common.PeerAddr GetConnectionCnt() uint32 + GetMaxPeerBlockHeight() uint64 GetNp() *peer.NbrPeers GetPeer(uint64) *peer.Peer SetHeight(uint64) diff --git a/p2pserver/p2pserver.go b/p2pserver/p2pserver.go index e258b4da2c..333e477553 100644 --- a/p2pserver/p2pserver.go +++ b/p2pserver/p2pserver.go @@ -89,6 +89,11 @@ func (this *P2PServer) GetConnectionCnt() uint32 { return this.network.GetConnectionCnt() } +//GetMaxPeerBlockHeight return the established connect count +func (this *P2PServer) GetMaxPeerBlockHeight() uint64 { + return this.network.GetMaxPeerBlockHeight() +} + //Start create all services func (this *P2PServer) Start() error { if this.network != nil { diff --git a/p2pserver/peer/nbr_peers.go b/p2pserver/peer/nbr_peers.go index b884a5a91a..ec3fe77812 100644 --- a/p2pserver/peer/nbr_peers.go +++ b/p2pserver/peer/nbr_peers.go @@ -143,6 +143,22 @@ func (this *NbrPeers) GetNeighborHeights() map[uint64]uint64 { return hm } +//GetNeighborMostHeight return the most height of nbr peers +func (this *NbrPeers) GetNeighborMostHeight() uint64 { + this.RLock() + defer this.RUnlock() + mostHeight := uint64(0) + for _, n := range this.List { + if n.GetState() == common.ESTABLISH { + height := n.GetHeight() + if mostHeight < height { + mostHeight = height + } + } + } + return mostHeight +} + //GetNeighbors return all establish peers in nbr list func (this *NbrPeers) GetNeighbors() []*Peer { this.RLock()