Commit 5f573335 authored by Matthew Slipper's avatar Matthew Slipper Committed by GitHub

Merge pull request #1894 from mslipper/bugfix/eng-1768-string-ids

go/proxyd: Allow string RPC IDs
parents d667bbb8 7b7ffd2e
---
'@eth-optimism/proxyd': minor
---
Allows string RPC ids on proxyd
......@@ -25,11 +25,6 @@ const (
)
var (
ErrInvalidRequest = &RPCErr{
Code: -32601,
Message: "invalid request",
HTTPErrorCode: 400,
}
ErrParseErr = &RPCErr{
Code: -32700,
Message: "parse error",
......@@ -67,6 +62,14 @@ var (
}
)
func ErrInvalidRequest(msg string) *RPCErr {
return &RPCErr{
Code: -32601,
Message: msg,
HTTPErrorCode: 400,
}
}
type Backend struct {
Name string
rpcURL string
......@@ -498,7 +501,7 @@ func (w *WSProxier) clientPump(ctx context.Context, errC chan error) {
// just handle them here.
req, err := w.prepareClientMsg(msg)
if err != nil {
var id *int
var id json.RawMessage
method := MethodUnknown
if req != nil {
id = req.ID
......@@ -555,7 +558,7 @@ func (w *WSProxier) backendPump(ctx context.Context, errC chan error) {
res, err := w.parseBackendMsg(msg)
if err != nil {
var id *int
var id json.RawMessage
if res != nil {
id = res.ID
}
......
......@@ -4,20 +4,21 @@ import (
"encoding/json"
"io"
"io/ioutil"
"strings"
)
type RPCReq struct {
JSONRPC string `json:"jsonrpc"`
Method string `json:"method"`
Params json.RawMessage `json:"params"`
ID *int `json:"id"`
ID json.RawMessage `json:"id"`
}
type RPCRes struct {
JSONRPC string `json:"jsonrpc"`
Result interface{} `json:"result,omitempty"`
Error *RPCErr `json:"error,omitempty"`
ID *int `json:"id"`
JSONRPC string `json:"jsonrpc"`
Result interface{} `json:"result,omitempty"`
Error *RPCErr `json:"error,omitempty"`
ID json.RawMessage `json:"id"`
}
func (r *RPCRes) IsError() bool {
......@@ -34,6 +35,17 @@ func (r *RPCErr) Error() string {
return r.Message
}
func IsValidID(id json.RawMessage) bool {
// handle the case where the ID is a string
if strings.HasPrefix(string(id), "\"") && strings.HasSuffix(string(id), "\"") {
return len(id) > 2
}
// technically allows a boolean/null ID, but so does Geth
// https://github.com/ethereum/go-ethereum/blob/master/rpc/json.go#L72
return len(id) > 0 && id[0] != '{' && id[0] != '['
}
func ParseRPCReq(r io.Reader) (*RPCReq, error) {
body, err := ioutil.ReadAll(r)
if err != nil {
......@@ -46,11 +58,15 @@ func ParseRPCReq(r io.Reader) (*RPCReq, error) {
}
if req.JSONRPC != JSONRPCVersion {
return nil, ErrInvalidRequest
return nil, ErrInvalidRequest("invalid JSON-RPC version")
}
if req.Method == "" {
return nil, ErrInvalidRequest
return nil, ErrInvalidRequest("no method specified")
}
if !IsValidID(req.ID) {
return nil, ErrInvalidRequest("invalid ID")
}
return req, nil
......@@ -70,7 +86,7 @@ func ParseRPCRes(r io.Reader) (*RPCRes, error) {
return res, nil
}
func NewRPCErrorRes(id *int, err error) *RPCRes {
func NewRPCErrorRes(id json.RawMessage, err error) *RPCRes {
var rpcErr *RPCErr
if rr, ok := err.(*RPCErr); ok {
rpcErr = rr
......
......@@ -232,7 +232,7 @@ func (s *Server) populateContext(w http.ResponseWriter, r *http.Request) context
)
}
func writeRPCError(w http.ResponseWriter, id *int, err error) {
func writeRPCError(w http.ResponseWriter, id json.RawMessage, err error) {
var res *RPCRes
if r, ok := err.(*RPCErr); ok {
res = NewRPCErrorRes(id, r)
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment