Created
February 2, 2022 02:38
-
-
Save rauljordan/4b18de3ec74df6c25cdb1eefe1510b66 to your computer and use it in GitHub Desktop.
Prysm gRPC Indexed Attestation Parsing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
module github.com/rauljordan/attestation-parse | |
go 1.17 | |
require ( | |
github.com/golang/protobuf v1.5.2 | |
github.com/prysmaticlabs/prysm/v2 v2.0.1 | |
google.golang.org/grpc v1.37.0 | |
) | |
require ( | |
github.com/btcsuite/btcd v0.22.0-beta // indirect | |
github.com/cespare/xxhash v1.1.0 // indirect | |
github.com/cpuguy83/go-md2man/v2 v2.0.0-20190314233015-f79a8a8ca69d // indirect | |
github.com/dgraph-io/ristretto v0.0.4-0.20210318174700-74754f61e018 // indirect | |
github.com/dustin/go-humanize v1.0.0 // indirect | |
github.com/ethereum/go-ethereum v1.9.25 // indirect | |
github.com/ferranbt/fastssz v0.0.0-20210905181407-59cf6761a7d5 // indirect | |
github.com/golang/groupcache v0.0.0-20200121045136-8c9f03a8e57e // indirect | |
github.com/grpc-ecosystem/grpc-gateway/v2 v2.0.1 // indirect | |
github.com/herumi/bls-eth-go-binary v0.0.0-20210917013441-d37c07cfda4e // indirect | |
github.com/klauspost/cpuid/v2 v2.0.8 // indirect | |
github.com/konsorten/go-windows-terminal-sequences v1.0.3 // indirect | |
github.com/minio/sha256-simd v1.0.0 // indirect | |
github.com/mitchellh/mapstructure v1.4.1 // indirect | |
github.com/mohae/deepcopy v0.0.0-20170929034955-c48cc78d4826 // indirect | |
github.com/pkg/errors v0.9.1 // indirect | |
github.com/prysmaticlabs/eth2-types v0.0.0-20210303084904-c9735a06829d // indirect | |
github.com/prysmaticlabs/go-bitfield v0.0.0-20210809151128-385d8c5e3fb7 // indirect | |
github.com/russross/blackfriday/v2 v2.0.1 // indirect | |
github.com/shurcooL/sanitized_anchor_name v1.0.0 // indirect | |
github.com/sirupsen/logrus v1.6.0 // indirect | |
github.com/supranational/blst v0.3.5 // indirect | |
github.com/thomaso-mirodin/intmath v0.0.0-20160323211736-5dc6d854e46e // indirect | |
github.com/urfave/cli/v2 v2.3.0 // indirect | |
go.opencensus.io v0.23.0 // indirect | |
golang.org/x/crypto v0.0.0-20210711020723-a769d52b0f97 // indirect | |
golang.org/x/net v0.0.0-20210716203947-853a461950ff // indirect | |
golang.org/x/sys v0.0.0-20210630005230-0f9fa26af87c // indirect | |
golang.org/x/text v0.3.6 // indirect | |
google.golang.org/genproto v0.0.0-20210426193834-eac7f76ac494 // indirect | |
google.golang.org/protobuf v1.27.1 // indirect | |
gopkg.in/yaml.v2 v2.4.0 // indirect | |
) |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
package main | |
import ( | |
"context" | |
"fmt" | |
"sort" | |
"github.com/golang/protobuf/ptypes/empty" | |
ethpb "github.com/prysmaticlabs/prysm/v2/proto/prysm/v1alpha1" | |
"github.com/prysmaticlabs/prysm/v2/proto/prysm/v1alpha1/attestation" | |
"google.golang.org/grpc" | |
) | |
func main() { | |
client, err := grpc.Dial("localhost:4000", grpc.WithInsecure()) | |
if err != nil { | |
panic(err) | |
} | |
beaconClient := ethpb.NewBeaconChainClient(client) | |
ctx := context.Background() | |
head, err := beaconClient.GetChainHead(ctx, &empty.Empty{}) | |
if err != nil { | |
panic(err) | |
} | |
fmt.Printf("Head slot %d, epoch %d\n", head.HeadSlot, head.HeadEpoch) | |
fmt.Println("Fetching beacon committees (this can take a min)...") | |
committeesResp, err := beaconClient.ListBeaconCommittees(ctx, ðpb.ListCommitteesRequest{ | |
QueryFilter: ðpb.ListCommitteesRequest_Epoch{ | |
Epoch: head.HeadEpoch, | |
}, | |
}) | |
slots := make([]uint64, 0) | |
for k := range committeesResp.Committees { | |
slots = append(slots, k) | |
} | |
sort.SliceStable(slots, func(i, j int) bool { | |
return slots[i] < slots[j] | |
}) | |
fmt.Printf("Committee lowest slot %d and highest %d\n", slots[0], slots[len(slots)-1]) | |
fmt.Printf("Fetching beacon blocks for head epoch %d...\n", head.HeadEpoch) | |
blocksResp, err := beaconClient.ListBeaconBlocks(ctx, ðpb.ListBlocksRequest{ | |
QueryFilter: ðpb.ListBlocksRequest_Epoch{ | |
Epoch: head.HeadEpoch, | |
}, | |
}) | |
// TODO: Get the last few epochs worth of committees, as some attestations could be from committees in past epochs. | |
fmt.Printf("Found %d blocks in epoch %d\n", len(blocksResp.BlockContainers), head.HeadEpoch) | |
attestationsInEpoch := make([]*ethpb.Attestation, 0) | |
for _, blk := range blocksResp.BlockContainers { | |
cntr, ok := blk.Block.(*ethpb.BeaconBlockContainer_AltairBlock) | |
if !ok { | |
panic("not an altair block") | |
} | |
signedBlock := cntr.AltairBlock | |
block := signedBlock.Block | |
attestationsInEpoch = append(attestationsInEpoch, block.Body.Attestations...) | |
} | |
fmt.Printf("Found %d attestations in epoch %d\n", len(attestationsInEpoch), head.HeadEpoch) | |
indexedAttestations := make([]*ethpb.IndexedAttestation, len(attestationsInEpoch)) | |
for _, att := range attestationsInEpoch { | |
committeesForSlot, ok := committeesResp.Committees[uint64(att.Data.Slot)] | |
if !ok { | |
// We should get at least 2 epochs worth of committees so this should not happen. | |
continue | |
} | |
committeeForAttestation := committeesForSlot.Committees[att.Data.CommitteeIndex] | |
indexedAtt, err := attestation.ConvertToIndexed(ctx, att, committeeForAttestation.ValidatorIndices) | |
if err != nil { | |
panic(err) | |
} | |
indexedAttestations = append(indexedAttestations, indexedAtt) | |
} | |
fmt.Printf("Converted %d attestations to indexed form\n", len(indexedAttestations)) | |
_ = indexedAttestations // Do something with the validator indices within. | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment