-
Notifications
You must be signed in to change notification settings - Fork 1.7k
/
replay_controller.go
93 lines (79 loc) · 2.33 KB
/
replay_controller.go
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
package web
import (
"net/http"
"strconv"
"github.com/gin-gonic/gin"
"github.com/pkg/errors"
"github.com/smartcontractkit/chainlink/v2/core/services/chainlink"
"github.com/smartcontractkit/chainlink/v2/core/utils"
)
type ReplayController struct {
App chainlink.Application
}
// ReplayFromBlock causes the node to process blocks again from the given block number
// Example:
//
// "<application>/v2/replay_from_block/:number"
func (bdc *ReplayController) ReplayFromBlock(c *gin.Context) {
if c.Param("number") == "" {
jsonAPIError(c, http.StatusUnprocessableEntity, errors.New("missing 'number' parameter"))
return
}
// check if "force" query string parameter provided
var force bool
var err error
if fb := c.Query("force"); fb != "" {
force, err = strconv.ParseBool(fb)
if err != nil {
jsonAPIError(c, http.StatusUnprocessableEntity, errors.Wrap(err, "boolean value required for 'force' query string param"))
return
}
}
blockNumber, err := strconv.ParseInt(c.Param("number"), 10, 0)
if err != nil {
jsonAPIError(c, http.StatusUnprocessableEntity, err)
return
}
if blockNumber < 0 {
jsonAPIError(c, http.StatusUnprocessableEntity, errors.Errorf("block number cannot be negative: %v", blockNumber))
return
}
chain, err := getChain(bdc.App.GetChains().EVM, c.Query("evmChainID"))
switch err {
case ErrInvalidChainID, ErrMultipleChains, ErrMissingChainID:
jsonAPIError(c, http.StatusUnprocessableEntity, err)
return
case nil:
break
default:
jsonAPIError(c, http.StatusInternalServerError, err)
return
}
chainID := chain.ID()
if err := bdc.App.ReplayFromBlock(chainID, uint64(blockNumber), force); err != nil {
jsonAPIError(c, http.StatusInternalServerError, err)
return
}
response := ReplayResponse{
Message: "Replay started",
EVMChainID: utils.NewBig(chainID),
}
jsonAPIResponse(c, &response, "response")
}
type ReplayResponse struct {
Message string `json:"message"`
EVMChainID *utils.Big `json:"evmChainID"`
}
// GetID returns the jsonapi ID.
func (s ReplayResponse) GetID() string {
return "replayID"
}
// GetName returns the collection name for jsonapi.
func (ReplayResponse) GetName() string {
return "replay"
}
// SetID is used to conform to the UnmarshallIdentifier interface for
// deserializing from jsonapi documents.
func (*ReplayResponse) SetID(string) error {
return nil
}