Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat: PRT - Near shard spec verification #1783

Merged
merged 12 commits into from
Nov 25, 2024
10 changes: 9 additions & 1 deletion .golangci.yml
Original file line number Diff line number Diff line change
Expand Up @@ -41,6 +41,14 @@ linters:
- whitespace

issues:
exclude-files:
- "protocol/chainlib/chainproxy/rpcInterfaceMessages/grpcMessage.go"
- "protocol/chainlib/grpc.go"
- "protocol/chainlib/grpcproxy/dyncodec/remote_grpc_reflection.go"
- "protocol/chainlib/grpcproxy/dyncodec/remote_relayer.go"
- "protocol/chainlib/grpcproxy/dyncodec/remotes_test.go"
- "ecosystem/lavajs/*"
- "ecosystem/lava-sdk/*"
exclude-rules:
- text: "singleCaseSwitch"
linters:
Expand All @@ -56,7 +64,7 @@ issues:
- text: "ST1016:"
linters:
- stylecheck
- text: "SA1019:.*\"github.com/golang/protobuf/proto\" is deprecated.*" # proto is deprecated, but some places couldn't be removed
- text: 'SA1019:.*"github.com/golang/protobuf/proto" is deprecated.*' # proto is deprecated, but some places couldn't be removed
linters:
- staticcheck
- path: "migrations"
Expand Down
26 changes: 26 additions & 0 deletions cookbook/specs/near.json
Original file line number Diff line number Diff line change
Expand Up @@ -430,6 +430,32 @@
}
],
"verifications": [
{
"name": "tracking-shards",
"parse_directive": {
"function_template": "{\"jsonrpc\":\"2.0\",\"id\":\"dontcare\",\"method\":\"query\",\"params\":{\"request_type\":\"view_account\",\"finality\":\"final\",\"account_id\":\"floor.is.lava\"}}",
"function_tag": "VERIFICATION",
"parsers": [
{
"parse_path": ".error.cause.name",
"value": "UNKNOWN_ACCOUNT",
"parse_type": "RESULT"
},
{
"parse_path": ".result.amount",
"value": "*",
"parse_type": "RESULT"
}
],
"api_name": "query"
},
"values": [
{
"expected_value": "*",
"severity": "Warning"
}
]
},
{
"name": "chain-id",
"parse_directive": {
Expand Down
16 changes: 8 additions & 8 deletions proto/lavanet/lava/spec/api_collection.proto
Original file line number Diff line number Diff line change
Expand Up @@ -119,14 +119,14 @@ enum FUNCTION_TAG {
}

enum PARSER_TYPE {
NO_PARSER = 0;
BLOCK_LATEST = 1;
BLOCK_EARLIEST = 2;
RESULT = 3;
EXTENSION_ARG = 4;
IDENTIFIER = 5;
DEFAULT_VALUE = 6;
BLOCK_HASH = 7;
NO_PARSER = 0; // parsing is disabled
BLOCK_LATEST = 1; // parse the latest block
BLOCK_EARLIEST = 2; // parse the earliest block
RESULT = 3; // parse the result of the rpc call
EXTENSION_ARG = 4; // parse the extension argument (e.g. should we turn on an extension or not, based on the parsed value)
IDENTIFIER = 5; // parse the id of the rpc message
DEFAULT_VALUE = 6; // set the default value for the parsed result (currently used for block, after all other generic parsers failed)
BLOCK_HASH = 7; // parse the block hash
}

enum PARSER_FUNC{
Expand Down
22 changes: 17 additions & 5 deletions protocol/chainlib/chain_fetcher.go
Original file line number Diff line number Diff line change
Expand Up @@ -191,7 +191,18 @@ func (cf *ChainFetcher) Verify(ctx context.Context, verification VerificationCon

parsedInput := parser.ParseBlockFromReply(parserInput, parsing.ResultParsing, parsing.Parsers)
if parsedInput.GetRawParsedData() == "" {
return utils.LavaFormatWarning("[-] verify failed to parse result", err,
return utils.LavaFormatWarning("[-] verify failed to parse result", nil,
utils.LogAttr("chainId", chainId),
utils.LogAttr("nodeUrl", proxyUrl.Url),
utils.LogAttr("Method", parsing.GetApiName()),
utils.LogAttr("Response", string(reply.RelayReply.Data)),
)
}

parserError := parsedInput.GetParserError()
if parserError != "" {
return utils.LavaFormatWarning("[-] parser returned an error", nil,
utils.LogAttr("error", parserError),
utils.LogAttr("chainId", chainId),
utils.LogAttr("nodeUrl", proxyUrl.Url),
utils.LogAttr("Method", parsing.GetApiName()),
Expand All @@ -201,7 +212,7 @@ func (cf *ChainFetcher) Verify(ctx context.Context, verification VerificationCon
if verification.LatestDistance != 0 && latestBlock != 0 && verification.ParseDirective.FunctionTag != spectypes.FUNCTION_TAG_GET_BLOCK_BY_NUM {
parsedResultAsNumber := parsedInput.GetBlock()
if parsedResultAsNumber == spectypes.NOT_APPLICABLE {
return utils.LavaFormatWarning("[-] verify failed to parse result as number", err,
return utils.LavaFormatWarning("[-] verify failed to parse result as number", nil,
utils.LogAttr("chainId", chainId),
utils.LogAttr("nodeUrl", proxyUrl.Url),
utils.LogAttr("Method", parsing.GetApiName()),
Expand All @@ -211,7 +222,7 @@ func (cf *ChainFetcher) Verify(ctx context.Context, verification VerificationCon
}
uint64ParsedResultAsNumber := uint64(parsedResultAsNumber)
if uint64ParsedResultAsNumber > latestBlock {
return utils.LavaFormatWarning("[-] verify failed parsed result is greater than latestBlock", err,
return utils.LavaFormatWarning("[-] verify failed parsed result is greater than latestBlock", nil,
utils.LogAttr("chainId", chainId),
utils.LogAttr("nodeUrl", proxyUrl.Url),
utils.LogAttr("Method", parsing.GetApiName()),
Expand All @@ -220,7 +231,7 @@ func (cf *ChainFetcher) Verify(ctx context.Context, verification VerificationCon
)
}
if latestBlock-uint64ParsedResultAsNumber < verification.LatestDistance {
return utils.LavaFormatWarning("[-] verify failed expected block distance is not sufficient", err,
return utils.LavaFormatWarning("[-] verify failed expected block distance is not sufficient", nil,
utils.LogAttr("chainId", chainId),
utils.LogAttr("nodeUrl", proxyUrl.Url),
utils.LogAttr("Method", parsing.GetApiName()),
Expand All @@ -234,7 +245,7 @@ func (cf *ChainFetcher) Verify(ctx context.Context, verification VerificationCon
if verification.Value != "*" && verification.Value != "" && verification.ParseDirective.FunctionTag != spectypes.FUNCTION_TAG_GET_BLOCK_BY_NUM {
rawData := parsedInput.GetRawParsedData()
if rawData != verification.Value {
return utils.LavaFormatWarning("[-] verify failed expected and received are different", err,
return utils.LavaFormatWarning("[-] verify failed expected and received are different", nil,
utils.LogAttr("chainId", chainId),
utils.LogAttr("nodeUrl", proxyUrl.Url),
utils.LogAttr("rawParsedBlock", rawData),
Expand All @@ -246,6 +257,7 @@ func (cf *ChainFetcher) Verify(ctx context.Context, verification VerificationCon
)
}
}

utils.LavaFormatInfo("[+] verified successfully",
utils.LogAttr("chainId", chainId),
utils.LogAttr("nodeUrl", proxyUrl.Url),
Expand Down
5 changes: 5 additions & 0 deletions protocol/chainlib/chainproxy/common.go
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@ import (

"github.com/goccy/go-json"

"github.com/lavanet/lava/v4/protocol/chainlib/chainproxy/rpcclient"
"github.com/lavanet/lava/v4/protocol/parser"
pairingtypes "github.com/lavanet/lava/v4/x/pairing/types"
spectypes "github.com/lavanet/lava/v4/x/spec/types"
Expand Down Expand Up @@ -93,6 +94,10 @@ func (dri DefaultRPCInput) GetID() json.RawMessage {
return nil
}

func (dri DefaultRPCInput) GetError() *rpcclient.JsonError {
return nil
}

func (dri DefaultRPCInput) ParseBlock(inp string) (int64, error) {
return parser.ParseDefaultBlockParameter(inp)
}
Expand Down
6 changes: 6 additions & 0 deletions protocol/chainlib/chainproxy/rpcInterfaceMessages/common.go
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@ import (
"github.com/goccy/go-json"

"github.com/lavanet/lava/v4/protocol/chainlib/chainproxy"
"github.com/lavanet/lava/v4/protocol/chainlib/chainproxy/rpcclient"
"github.com/lavanet/lava/v4/protocol/parser"
pairingtypes "github.com/lavanet/lava/v4/x/pairing/types"
)
Expand All @@ -13,6 +14,7 @@ var WontCalculateBatchHash = sdkerrors.New("Wont calculate batch hash", 892, "wo

type ParsableRPCInput struct {
Result json.RawMessage
Error *rpcclient.JsonError
chainproxy.BaseMessage
}

Expand All @@ -36,6 +38,10 @@ func (pri ParsableRPCInput) GetID() json.RawMessage {
return nil
}

func (pri ParsableRPCInput) GetError() *rpcclient.JsonError {
return pri.Error
}

type GenericMessage interface {
GetHeaders() []pairingtypes.Metadata
DisableErrorHandling()
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -126,6 +126,10 @@ func (gm GrpcMessage) GetID() json.RawMessage {
return nil
}

func (gm GrpcMessage) GetError() *rpcclient.JsonError {
return nil
}

func (gm GrpcMessage) NewParsableRPCInput(input json.RawMessage) (parser.RPCInput, error) {
msgFactory := dynamic.NewMessageFactoryWithDefaults()
if gm.methodDesc == nil {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -121,11 +121,7 @@ func (jm JsonrpcMessage) NewParsableRPCInput(input json.RawMessage) (parser.RPCI
return nil, utils.LavaFormatError("failed unmarshaling JsonrpcMessage", err, utils.Attribute{Key: "input", Value: input})
}

// Make sure the response does not have an error
if msg.Error != nil && msg.Result == nil {
return nil, utils.LavaFormatError("response is an error message", msg.Error)
}
return ParsableRPCInput{Result: msg.Result}, nil
return ParsableRPCInput{Result: msg.Result, Error: msg.Error}, nil
}

func (jm JsonrpcMessage) GetParams() interface{} {
Expand All @@ -147,6 +143,10 @@ func (jm JsonrpcMessage) GetID() json.RawMessage {
return jm.ID
}

func (jm JsonrpcMessage) GetError() *rpcclient.JsonError {
return jm.Error
}

func (jm JsonrpcMessage) ParseBlock(inp string) (int64, error) {
return parser.ParseDefaultBlockParameter(inp)
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -105,6 +105,10 @@ func (rm RestMessage) GetID() json.RawMessage {
return nil
}

func (rm RestMessage) GetError() *rpcclient.JsonError {
return nil
}

// ParseBlock parses default block number from string to int
func (rm RestMessage) ParseBlock(inp string) (int64, error) {
return parser.ParseDefaultBlockParameter(inp)
Expand Down
14 changes: 14 additions & 0 deletions protocol/chainlib/chainproxy/rpcclient/json.go
Original file line number Diff line number Diff line change
Expand Up @@ -174,6 +174,20 @@ func (err *JsonError) ErrorData() interface{} {
return err.Data
}

func (err *JsonError) ToMap() map[string]interface{} {
if err == nil {
return nil
}

return map[string]interface{}{
"code": err.Code,
"message": err.Message,
"data": err.Data,
"name": err.Name,
"cause": err.Cause,
}
}

// Conn is a subset of the methods of net.Conn which are sufficient for ServerCodec.
type Conn interface {
io.ReadWriteCloser
Expand Down
Loading
Loading