Implement Bitcore socket.io method estimateSmartFee
parent
8c9dfc3ef4
commit
bcc8de4763
|
@ -132,6 +132,24 @@ type resGetRawTransactionVerbose struct {
|
|||
Result Tx `json:"result"`
|
||||
}
|
||||
|
||||
// estimatesmartfee
|
||||
|
||||
type cmdEstimateSmartFee struct {
|
||||
Method string `json:"method"`
|
||||
Params struct {
|
||||
ConfTarget int `json:"conf_target"`
|
||||
EstimateMode string `json:"estimate_mode"`
|
||||
} `json:"params"`
|
||||
}
|
||||
|
||||
type resEstimateSmartFee struct {
|
||||
Error *RPCError `json:"error"`
|
||||
Result struct {
|
||||
Feerate float64 `json:"feerate"`
|
||||
Blocks int `json:"blocks"`
|
||||
} `json:"result"`
|
||||
}
|
||||
|
||||
type BlockParser interface {
|
||||
ParseBlock(b []byte) (*Block, error)
|
||||
}
|
||||
|
@ -355,6 +373,29 @@ func (b *BitcoinRPC) GetTransaction(txid string) (*Tx, error) {
|
|||
return &res.Result, nil
|
||||
}
|
||||
|
||||
// EstimateSmartFee returns fee estimation.
|
||||
func (b *BitcoinRPC) EstimateSmartFee(blocks int, conservative bool) (float64, error) {
|
||||
glog.V(1).Info("rpc: estimatesmartfee ", blocks)
|
||||
|
||||
res := resEstimateSmartFee{}
|
||||
req := cmdEstimateSmartFee{Method: "estimatesmartfee"}
|
||||
req.Params.ConfTarget = blocks
|
||||
if conservative {
|
||||
req.Params.EstimateMode = "CONSERVATIVE"
|
||||
} else {
|
||||
req.Params.EstimateMode = "ECONOMICAL"
|
||||
}
|
||||
err := b.call(&req, &res)
|
||||
|
||||
if err != nil {
|
||||
return 0, err
|
||||
}
|
||||
if res.Error != nil {
|
||||
return 0, res.Error
|
||||
}
|
||||
return res.Result.Feerate, nil
|
||||
}
|
||||
|
||||
func (b *BitcoinRPC) call(req interface{}, res interface{}) error {
|
||||
httpData, err := json.Marshal(req)
|
||||
if err != nil {
|
||||
|
|
|
@ -103,21 +103,38 @@ type reqRange struct {
|
|||
To int `json:"to"`
|
||||
}
|
||||
|
||||
var onMessageHandlers = map[string]func(*SocketIoServer, json.RawMessage) (interface{}, error){
|
||||
"\"getAddressTxids\"": func(s *SocketIoServer, params json.RawMessage) (rv interface{}, err error) {
|
||||
addr, rr, err := unmarshalGetAddressTxids(params)
|
||||
if err == nil {
|
||||
rv, err = s.getAddressTxids(addr, &rr)
|
||||
}
|
||||
return
|
||||
},
|
||||
"\"getBlockHeader\"": func(s *SocketIoServer, params json.RawMessage) (rv interface{}, err error) {
|
||||
height, hash, err := unmarshalGetBlockHeader(params)
|
||||
if err == nil {
|
||||
rv, err = s.getBlockHeader(height, hash)
|
||||
}
|
||||
return
|
||||
},
|
||||
"\"estimateSmartFee\"": func(s *SocketIoServer, params json.RawMessage) (rv interface{}, err error) {
|
||||
blocks, conservative, err := unmarshalEstimateSmartFee(params)
|
||||
if err == nil {
|
||||
rv, err = s.estimateSmartFee(blocks, conservative)
|
||||
}
|
||||
return
|
||||
},
|
||||
}
|
||||
|
||||
func (s *SocketIoServer) onMessage(c *gosocketio.Channel, req map[string]json.RawMessage) interface{} {
|
||||
var err error
|
||||
var rv interface{}
|
||||
method := string(req["method"])
|
||||
params := req["params"]
|
||||
if method == "\"getAddressTxids\"" {
|
||||
addr, rr, err := unmarshalGetAddressTxids(params)
|
||||
if err == nil {
|
||||
rv, err = s.getAddressTxids(addr, &rr)
|
||||
}
|
||||
} else if method == "\"getBlockHeader\"" {
|
||||
height, hash, err := unmarshalGetBlockHeader(params)
|
||||
if err == nil {
|
||||
rv, err = s.getBlockHeader(height, hash)
|
||||
}
|
||||
f, ok := onMessageHandlers[method]
|
||||
if ok {
|
||||
rv, err = f(s, params)
|
||||
} else {
|
||||
err = errors.New("unknown method")
|
||||
}
|
||||
|
@ -184,16 +201,23 @@ func (s *SocketIoServer) getAddressTxids(addr []string, rr *reqRange) ([]string,
|
|||
return txids, nil
|
||||
}
|
||||
|
||||
func unmarshalGetBlockHeader(params []byte) (height uint32, hash string, err error) {
|
||||
var p []interface{}
|
||||
func unmarshalArray(params []byte, np int) (p []interface{}, err error) {
|
||||
err = json.Unmarshal(params, &p)
|
||||
if err != nil {
|
||||
return
|
||||
}
|
||||
if len(p) != 1 {
|
||||
if len(p) != np {
|
||||
err = errors.New("incorrect number of parameters")
|
||||
return
|
||||
}
|
||||
return
|
||||
}
|
||||
|
||||
func unmarshalGetBlockHeader(params []byte) (height uint32, hash string, err error) {
|
||||
p, err := unmarshalArray(params, 1)
|
||||
if err != nil {
|
||||
return
|
||||
}
|
||||
fheight, ok := p[0].(float64)
|
||||
if ok {
|
||||
return uint32(fheight), "", nil
|
||||
|
@ -248,6 +272,38 @@ func (s *SocketIoServer) getBlockHeader(height uint32, hash string) (res resultG
|
|||
return
|
||||
}
|
||||
|
||||
func unmarshalEstimateSmartFee(params []byte) (blocks int, conservative bool, err error) {
|
||||
p, err := unmarshalArray(params, 2)
|
||||
if err != nil {
|
||||
return
|
||||
}
|
||||
fblocks, ok := p[0].(float64)
|
||||
if !ok {
|
||||
err = errors.New("Invalid parameter blocks")
|
||||
return
|
||||
}
|
||||
blocks = int(fblocks)
|
||||
conservative, ok = p[1].(bool)
|
||||
if !ok {
|
||||
err = errors.New("Invalid parameter conservative")
|
||||
return
|
||||
}
|
||||
return
|
||||
}
|
||||
|
||||
type resultEstimateSmartFee struct {
|
||||
Result float64 `json:"result"`
|
||||
}
|
||||
|
||||
func (s *SocketIoServer) estimateSmartFee(blocks int, conservative bool) (res resultEstimateSmartFee, err error) {
|
||||
fee, err := s.chain.EstimateSmartFee(blocks, conservative)
|
||||
if err != nil {
|
||||
return
|
||||
}
|
||||
res.Result = fee
|
||||
return
|
||||
}
|
||||
|
||||
func (s *SocketIoServer) onSubscribe(c *gosocketio.Channel, req map[string]json.RawMessage) interface{} {
|
||||
glog.Info(c.Id(), " onSubscribe ", req)
|
||||
return nil
|
||||
|
|
|
@ -66,6 +66,21 @@
|
|||
return socket.send({ method, params }, f);
|
||||
}
|
||||
|
||||
function estimateSmartFee() {
|
||||
var blocks = document.getElementById('estimateSmartFeeBlocks').value;
|
||||
var conservative = document.getElementById("estimateSmartFeeConservative").checked;
|
||||
estimateSmartTxFee(parseInt(blocks), conservative, function (result) {
|
||||
console.log('estimateSmartFee sent successfully');
|
||||
console.log(result);
|
||||
document.getElementById('estimateSmartFeeResult').innerText = JSON.stringify(result).replace(/,/g, ", ");
|
||||
});
|
||||
}
|
||||
|
||||
function estimateSmartTxFee(blocks, conservative, f) {
|
||||
const method = 'estimateSmartFee';
|
||||
const params = [blocks, conservative];
|
||||
return socket.send({ method, params }, f);
|
||||
}
|
||||
</script>
|
||||
</head>
|
||||
|
||||
|
@ -115,6 +130,22 @@
|
|||
<div class="col" id="getBlockHeaderResult">
|
||||
</div>
|
||||
</div>
|
||||
<div class="row">
|
||||
<div class="col">
|
||||
<input class="btn btn-secondary" type="button" value="estimateSmartFee" onclick="estimateSmartFee()">
|
||||
</div>
|
||||
<div class="col-8">
|
||||
<input type="text" class="form-control" id="estimateSmartFeeBlocks" value="20">
|
||||
</div>
|
||||
<div class="col form-inline">
|
||||
<input type="checkbox" id="estimateSmartFeeConservative" checked>
|
||||
<label>conservative</label>
|
||||
</div>
|
||||
</div>
|
||||
<div class="row">
|
||||
<div class="col" id="estimateSmartFeeResult">
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</body>
|
||||
|
|
Loading…
Reference in New Issue