m.Handle("/", alwaysError(errors.New("not Found")))
m.Handle("/error", jsonHandler(a.walletError))
- m.Handle("/net-info", jsonHandler(a.getNetInfo))
-
m.Handle("/create-access-token", jsonHandler(a.createAccessToken))
m.Handle("/list-access-tokens", jsonHandler(a.listAccessTokens))
m.Handle("/delete-access-token", jsonHandler(a.deleteAccessToken))
m.Handle("/get-block-header", jsonHandler(a.getBlockHeader))
m.Handle("/get-block", jsonHandler(a.getBlock))
m.Handle("/get-block-count", jsonHandler(a.getBlockCount))
+ m.Handle("/get-difficulty", jsonHandler(a.getDifficulty))
+ m.Handle("/get-hash-rate", jsonHandler(a.getHashRate))
m.Handle("/is-mining", jsonHandler(a.isMining))
- m.Handle("/gas-rate", jsonHandler(a.gasRate))
+ m.Handle("/set-mining", jsonHandler(a.setMining))
+
m.Handle("/get-work", jsonHandler(a.getWork))
m.Handle("/submit-work", jsonHandler(a.submitWork))
- m.Handle("/set-mining", jsonHandler(a.setMining))
+
+ m.Handle("/gas-rate", jsonHandler(a.gasRate))
+ m.Handle("/net-info", jsonHandler(a.getNetInfo))
handler := latencyHandler(m, walletEnable)
handler = maxBytesHandler(handler) // TODO(tessr): consider moving this to non-core specific mux
package api
import (
+ "math/big"
+
"github.com/bytom/blockchain/query"
"github.com/bytom/consensus/difficulty"
chainjson "github.com/bytom/encoding/json"
}
return NewSuccessResponse(resp)
}
+
+// GetDifficultyResp is resp struct for getDifficulty API
+type GetDifficultyResp struct {
+ BlockHash *bc.Hash `json:"hash"`
+ BlockHeight uint64 `json:"height"`
+ Bits uint64 `json:"bits"`
+ Difficulty string `json:"difficulty"`
+}
+
+func (a *API) getDifficulty(ins *BlockReq) Response {
+ var err error
+ block := &types.Block{}
+
+ if len(ins.BlockHash) == 32 && ins.BlockHash != nil {
+ b32 := [32]byte{}
+ copy(b32[:], ins.BlockHash)
+ hash := bc.NewHash(b32)
+ block, err = a.chain.GetBlockByHash(&hash)
+ } else if ins.BlockHeight > 0 {
+ block, err = a.chain.GetBlockByHeight(ins.BlockHeight)
+ } else {
+ hash := a.chain.BestBlockHash()
+ block, err = a.chain.GetBlockByHash(hash)
+ }
+
+ if err != nil {
+ return NewErrorResponse(err)
+ }
+
+ blockHash := block.Hash()
+ resp := &GetDifficultyResp{
+ BlockHash: &blockHash,
+ BlockHeight: block.Height,
+ Bits: block.Bits,
+ Difficulty: difficulty.CalcWork(block.Bits).String(),
+ }
+ return NewSuccessResponse(resp)
+}
+
+// getHashRateResp is resp struct for getHashRate API
+type getHashRateResp struct {
+ BlockHash *bc.Hash `json:"hash"`
+ BlockHeight uint64 `json:"height"`
+ HashRate uint64 `json:"hash_rate"`
+}
+
+func (a *API) getHashRate(ins BlockReq) Response {
+ var err error
+ block := &types.Block{}
+
+ if len(ins.BlockHash) == 32 && ins.BlockHash != nil {
+ b32 := [32]byte{}
+ copy(b32[:], ins.BlockHash)
+ hash := bc.NewHash(b32)
+ block, err = a.chain.GetBlockByHash(&hash)
+ } else if ins.BlockHeight > 0 {
+ block, err = a.chain.GetBlockByHeight(ins.BlockHeight)
+ } else {
+ hash := a.chain.BestBlockHash()
+ block, err = a.chain.GetBlockByHash(hash)
+ }
+
+ if err != nil {
+ return NewErrorResponse(err)
+ }
+
+ preBlock, err := a.chain.GetBlockByHash(&block.PreviousBlockHash)
+ if err != nil {
+ return NewErrorResponse(err)
+ }
+
+ diffTime := block.Timestamp - preBlock.Timestamp
+ hashCount := difficulty.CalcWork(block.Bits)
+ hashRate := new(big.Int).Div(hashCount, big.NewInt(int64(diffTime)))
+
+ blockHash := block.Hash()
+ resp := &getHashRateResp{
+ BlockHash: &blockHash,
+ BlockHeight: block.Height,
+ HashRate: hashRate.Uint64(),
+ }
+ return NewSuccessResponse(resp)
+}
"github.com/bytom/util"
)
+func init() {
+ getDifficultyCmd.PersistentFlags().StringVar(&blockHash, "hash", "", "hash of block")
+ getDifficultyCmd.PersistentFlags().IntVar(&blockHeight, "height", 0, "height of block")
+
+ getHashRateCmd.PersistentFlags().StringVar(&blockHash, "hash", "", "hash of block")
+ getHashRateCmd.PersistentFlags().IntVar(&blockHeight, "height", 0, "height of block")
+}
+
+var (
+ blockHash = ""
+ blockHeight = 0
+)
+
var getBlockHashCmd = &cobra.Command{
Use: "get-block-hash",
Short: "Get the hash of most recent block",
BlockHash chainjson.HexBytes `json:"block_hash"`
}{BlockHeight: height, BlockHash: hash}
- data, exitCode := util.ClientCall("/get-block-header", &req)
+ data, exitCode := util.ClientCall("/get-block-header", req)
+ if exitCode != util.Success {
+ os.Exit(exitCode)
+ }
+ printJSON(data)
+ },
+}
+
+var getDifficultyCmd = &cobra.Command{
+ Use: "get-difficulty",
+ Short: "Get the difficulty of most recent block",
+ Args: cobra.NoArgs,
+ Run: func(cmd *cobra.Command, args []string) {
+ var hash chainjson.HexBytes
+ var err error
+
+ if blockHash != "" {
+ hash, err = hex.DecodeString(blockHash)
+ if err != nil {
+ jww.ERROR.Println(err)
+ os.Exit(util.ErrLocalExe)
+ }
+ }
+
+ req := &struct {
+ BlockHeight uint64 `json:"block_height"`
+ BlockHash chainjson.HexBytes `json:"block_hash"`
+ }{BlockHeight: uint64(blockHeight), BlockHash: hash}
+
+ data, exitCode := util.ClientCall("/get-difficulty", req)
+ if exitCode != util.Success {
+ os.Exit(exitCode)
+ }
+ printJSON(data)
+ },
+}
+
+var getHashRateCmd = &cobra.Command{
+ Use: "get-hash-rate",
+ Short: "Get the nonce of most recent block",
+ Args: cobra.NoArgs,
+ Run: func(cmd *cobra.Command, args []string) {
+ var hash chainjson.HexBytes
+ var err error
+
+ if blockHash != "" {
+ hash, err = hex.DecodeString(blockHash)
+ if err != nil {
+ jww.ERROR.Println(err)
+ os.Exit(util.ErrLocalExe)
+ }
+ }
+
+ req := &struct {
+ BlockHeight uint64 `json:"block_height"`
+ BlockHash chainjson.HexBytes `json:"block_hash"`
+ }{BlockHeight: uint64(blockHeight), BlockHash: hash}
+
+ data, exitCode := util.ClientCall("/get-hash-rate", req)
if exitCode != util.Success {
os.Exit(exitCode)
}
BytomcliCmd.AddCommand(getBlockHashCmd)
BytomcliCmd.AddCommand(getBlockCmd)
BytomcliCmd.AddCommand(getBlockHeaderCmd)
+ BytomcliCmd.AddCommand(getDifficultyCmd)
+ BytomcliCmd.AddCommand(getHashRateCmd)
BytomcliCmd.AddCommand(createKeyCmd)
BytomcliCmd.AddCommand(deleteKeyCmd)