diff --git a/go.mod b/go.mod index 27500f3dc4..f2b7f0ca45 100644 --- a/go.mod +++ b/go.mod @@ -4,6 +4,8 @@ go 1.20 replace github.com/ipfs/go-verifcid => github.com/celestiaorg/go-verifcid v0.0.1-lazypatch +replace github.com/celestiaorg/go-header => github.com/derrandz/go-header v0.0.0-20230426152902-919e3a027ef0 + require ( cosmossdk.io/math v1.0.0-beta.3 github.com/BurntSushi/toml v1.2.1 diff --git a/go.sum b/go.sum index 5d7dcd43e0..740170bb82 100644 --- a/go.sum +++ b/go.sum @@ -350,8 +350,6 @@ github.com/celestiaorg/dagstore v0.0.0-20230413141458-735ab09a15d6 h1:/yCwMCoOPc github.com/celestiaorg/dagstore v0.0.0-20230413141458-735ab09a15d6/go.mod h1:ta/DlqIH10bvhwqJIw51Nq3QU4XVMp6pz3f0Deve9fM= github.com/celestiaorg/go-fraud v0.1.0 h1:v6mZvlmf2J5ELZfPnrtmmOvKbaYIUs/erDWPO8NbZyY= github.com/celestiaorg/go-fraud v0.1.0/go.mod h1:yoNM35cKMAkt5Mi/Qx3Wi9bnPilLi8n6RpHZVglTUDs= -github.com/celestiaorg/go-header v0.2.6 h1:f1Mlyu+EfDpkuzO3SWU5dow+ga2vLQ7hNuvsOe//z64= -github.com/celestiaorg/go-header v0.2.6/go.mod h1:i9OpY70+PJ1xPw1IgMfF0Pk6vBD6VWPmjY3bgubJBcU= github.com/celestiaorg/go-libp2p-messenger v0.2.0 h1:/0MuPDcFamQMbw9xTZ73yImqgTO3jHV7wKHvWD/Irao= github.com/celestiaorg/go-libp2p-messenger v0.2.0/go.mod h1:s9PIhMi7ApOauIsfBcQwbr7m+HBzmVfDIS+QLdgzDSo= github.com/celestiaorg/go-verifcid v0.0.1-lazypatch h1:9TSe3w1cmJmbWlweCwCTIZkan7jV8M+KwglXpdD+UG8= @@ -492,6 +490,8 @@ github.com/decred/dcrd/dcrec/secp256k1/v4 v4.1.0/go.mod h1:DZGJHZMqrU4JJqFAWUS2U github.com/decred/dcrd/lru v1.0.0/go.mod h1:mxKOwFd7lFjN2GZYsiz/ecgqR6kkYAl+0pz0tEMk218= github.com/deepmap/oapi-codegen v1.6.0/go.mod h1:ryDa9AgbELGeB+YEXE1dR53yAjHwFvE9iAUlWl9Al3M= github.com/deepmap/oapi-codegen v1.8.2/go.mod h1:YLgSKSDv/bZQB7N4ws6luhozi3cEdRktEqrX88CvjIw= +github.com/derrandz/go-header v0.0.0-20230426152902-919e3a027ef0 h1:X5ir2bPOUDRes1qGYcXb9RaxF6584NcZCjfA/VHYHvo= +github.com/derrandz/go-header v0.0.0-20230426152902-919e3a027ef0/go.mod h1:i9OpY70+PJ1xPw1IgMfF0Pk6vBD6VWPmjY3bgubJBcU= github.com/desertbit/timer v0.0.0-20180107155436-c41aec40b27f h1:U5y3Y5UE0w7amNe7Z5G/twsBW0KEalRQXZzf8ufSh9I= github.com/desertbit/timer v0.0.0-20180107155436-c41aec40b27f/go.mod h1:xH/i4TFMt8koVQZ6WFms69WAsDWr2XsYL3Hkl7jkoLE= github.com/dgraph-io/badger v1.5.5-0.20190226225317-8115aed38f8f/go.mod h1:VZxzAIRPHRVNRKRo6AXrX9BJegn6il06VMTZVJYCIjQ= diff --git a/nodebuilder/header/constructors.go b/nodebuilder/header/constructors.go index 7d70f0f5a8..c4dec7fc2c 100644 --- a/nodebuilder/header/constructors.go +++ b/nodebuilder/header/constructors.go @@ -5,13 +5,13 @@ import ( "github.com/libp2p/go-libp2p/core/host" "github.com/libp2p/go-libp2p/core/peer" - "github.com/libp2p/go-libp2p/core/peerstore" "github.com/libp2p/go-libp2p/p2p/net/conngater" "go.uber.org/fx" libfraud "github.com/celestiaorg/go-fraud" libhead "github.com/celestiaorg/go-header" "github.com/celestiaorg/go-header/p2p" + "github.com/celestiaorg/go-header/p2p/peerstore" "github.com/celestiaorg/go-header/store" "github.com/celestiaorg/go-header/sync" @@ -19,6 +19,8 @@ import ( modfraud "github.com/celestiaorg/celestia-node/nodebuilder/fraud" modp2p "github.com/celestiaorg/celestia-node/nodebuilder/p2p" "github.com/celestiaorg/celestia-node/share/eds/byzantine" + + p2p_peerstore "github.com/libp2p/go-libp2p/core/peerstore" ) // newP2PExchange constructs a new Exchange for headers. @@ -29,6 +31,7 @@ func newP2PExchange( host host.Host, conngater *conngater.BasicConnectionGater, cfg Config, + peerstore peerstore.Peerstore, ) (libhead.Exchange[*header.ExtendedHeader], error) { peers, err := cfg.trustedPeers(bpeers) if err != nil { @@ -37,12 +40,20 @@ func newP2PExchange( ids := make([]peer.ID, len(peers)) for index, peer := range peers { ids[index] = peer.ID - host.Peerstore().AddAddrs(peer.ID, peer.Addrs, peerstore.PermanentAddrTTL) + host.Peerstore().AddAddrs(peer.ID, peer.Addrs, p2p_peerstore.PermanentAddrTTL) + } + peerlist, err := peerstore.Load(context.Background()) + if err != nil { + log.Info("Error loading peerlist from disk", "err", err) + } else { + log.Info("Loaded peerlist from disk", peerlist) } + exchange, err := p2p.NewExchange[*header.ExtendedHeader](host, ids, conngater, p2p.WithParams(cfg.Client), p2p.WithNetworkID[p2p.ClientParameters](network.String()), p2p.WithChainID(network.String()), + p2p.WithPeerPersistence[p2p.ClientParameters](peerstore), ) if err != nil { return nil, err diff --git a/nodebuilder/header/module.go b/nodebuilder/header/module.go index 77e7c5eb99..454274f736 100644 --- a/nodebuilder/header/module.go +++ b/nodebuilder/header/module.go @@ -3,6 +3,7 @@ package header import ( "context" + "github.com/celestiaorg/go-header/p2p/peerstore" "github.com/ipfs/go-datastore" logging "github.com/ipfs/go-log/v2" pubsub "github.com/libp2p/go-libp2p-pubsub" @@ -16,6 +17,7 @@ import ( "github.com/celestiaorg/celestia-node/header" modfraud "github.com/celestiaorg/celestia-node/nodebuilder/fraud" + pstore "github.com/celestiaorg/celestia-node/nodebuilder/header/peerstore" "github.com/celestiaorg/celestia-node/nodebuilder/node" modp2p "github.com/celestiaorg/celestia-node/nodebuilder/p2p" ) @@ -89,6 +91,9 @@ func ConstructModule(tp node.Type, cfg *Config) fx.Option { return server.Stop(ctx) }), )), + fx.Provide(func(ds datastore.Batching) peerstore.Peerstore { + return pstore.NewPeerStore(ds) + }), ) switch tp { diff --git a/nodebuilder/header/peerstore/peerstore.go b/nodebuilder/header/peerstore/peerstore.go new file mode 100644 index 0000000000..b94b9a430e --- /dev/null +++ b/nodebuilder/header/peerstore/peerstore.go @@ -0,0 +1,64 @@ +package peerstore + +import ( + "context" + "encoding/json" + "fmt" + + "github.com/celestiaorg/go-header/p2p/peerstore" + "github.com/ipfs/go-datastore" + "github.com/ipfs/go-datastore/namespace" + "github.com/libp2p/go-libp2p/core/peer" + + logging "github.com/ipfs/go-log/v2" +) + +var ( + storePrefix = datastore.NewKey("p2p") + peersKey = datastore.NewKey("good_peers") + + log = logging.Logger("module/header/peerstore") +) + +var _ peerstore.Peerstore = (*peerStore)(nil) + +type peerStore struct { + ds datastore.Datastore +} + +// newPeerStore wraps the given datastore.Datastore with the `p2p` prefix. +func NewPeerStore(ds datastore.Datastore) peerstore.Peerstore { + return &peerStore{ds: namespace.Wrap(ds, storePrefix)} +} + +func (s *peerStore) Load(ctx context.Context) ([]peer.AddrInfo, error) { + log.Info("Loading peerlist") + bs, err := s.ds.Get(ctx, peersKey) + if err != nil { + return make([]peer.AddrInfo, 0), err + } + + peerlist := make([]peer.AddrInfo, 0) + err = json.Unmarshal(bs, &peerlist) + if err != nil { + return make([]peer.AddrInfo, 0), fmt.Errorf("error unmarshalling peerlist: %w", err) + } + + log.Info("Loaded peerlist", peerlist) + return peerlist, err +} + +func (s *peerStore) Put(ctx context.Context, peerlist []peer.AddrInfo) error { + log.Info("Storing peerlist", peerlist) + + bs, err := json.Marshal(peerlist) + if err != nil { + return fmt.Errorf("marshal checkpoint: %w", err) + } + + if err = s.ds.Put(ctx, peersKey, bs); err != nil { + return err + } + + return nil +}