Skip to content

Commit

Permalink
add support for node info persistence on file
Browse files Browse the repository at this point in the history
  • Loading branch information
alejoacosta74 committed Oct 25, 2023
1 parent 67a4770 commit 4e5ac3c
Show file tree
Hide file tree
Showing 4 changed files with 61 additions and 8 deletions.
3 changes: 2 additions & 1 deletion .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -5,4 +5,5 @@
# git config --global core.excludesfile ~/.gitignore_global

*.key
nodelogs
nodelogs
node.info
3 changes: 2 additions & 1 deletion p2p/node/api.go
Original file line number Diff line number Diff line change
Expand Up @@ -104,8 +104,9 @@ func (p *P2PNode) ListenForEvents() {
case evt := <-subAddrUpdated.Out():
if e, ok := evt.(event.EvtLocalAddressesUpdated); ok {
for _, addr := range e.Current {
fullAddr := fmt.Sprintf("%+v/p2p/%s", addr, p.ID().Pretty())
fullAddr := fmt.Sprintf("%+v/p2p/%s", addr.Address.String(), p.ID().Pretty())
log.Debugf("Advertised Address changed: %s", fullAddr)
saveNodeInfo("Advertised address: " + fullAddr)
}
}
case evt := <-subPeerConnected.Out():
Expand Down
38 changes: 38 additions & 0 deletions p2p/node/cid.go
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
package node

import (
"bufio"
"crypto/rand"
"os"

Expand All @@ -9,6 +10,11 @@ import (
"github.com/libp2p/go-libp2p/core/crypto"
)

const (
// file to store node's CID and listening address
nodeInfoFile = "node.info"
)

// Returns the private key stored in the file to be used to generate
// the node's identity (CID)
func getPrivKey(privKeyFile string) (crypto.PrivKey, error) {
Expand Down Expand Up @@ -52,3 +58,35 @@ func getPrivKey(privKeyFile string) (crypto.PrivKey, error) {
return privateKey, nil

}

// Utility function that synchronously writes the provided "info" string to the node.info file.
// If the file doesn't exist, it creates it. Otherwise, it appends the new "info" as a new line.
func saveNodeInfo(info string) {
go func() {
// Open file with O_APPEND flag to append data to the file or create the file if it doesn't exist.
f, err := os.OpenFile(nodeInfoFile, os.O_APPEND|os.O_CREATE|os.O_WRONLY, 0644)
if err != nil {
log.Errorf("error opening node info file: %s", err)
return
}
defer f.Close()

// Use bufio for efficient writing
writer := bufio.NewWriter(f)
defer writer.Flush()

// Append new line and write to file
writer.WriteString(info + "\n")
}()
}

// utility function used to delete any existing node info file
func deleteNodeInfoFile() error {
if _, err := os.Stat(nodeInfoFile); !os.IsNotExist(err) {
err := os.Remove(nodeInfoFile)
if err != nil {
return err
}
}
return nil
}
25 changes: 19 additions & 6 deletions p2p/node/node.go
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,6 @@ import (
routedhost "github.com/libp2p/go-libp2p/p2p/host/routed"

"github.com/libp2p/go-libp2p"
dht "github.com/libp2p/go-libp2p-kad-dht"
kadht "github.com/libp2p/go-libp2p-kad-dht"
"github.com/libp2p/go-libp2p/core/host"

Expand Down Expand Up @@ -51,12 +50,11 @@ func NewNode(ctx context.Context) (*P2PNode, error) {

// list of options to instantiate the libp2p node
nodeOptions := []libp2p.Option{}

// use a private key for persistent identity
nodeOptions = append(nodeOptions, libp2p.Identity(privateKey))

// pass the ip address and port to listen on
sourceMultiAddr, _ := multiaddr.NewMultiaddr(fmt.Sprintf("/ip4/%s/tcp/%s", ipAddr, port))
nodeOptions = append(nodeOptions, libp2p.ListenAddrs(sourceMultiAddr))

// check if there is a host IP we can use to replace Docker's internal IP
hostIP, err := readHostIPFromFile(hostIPFile)
if err != nil || hostIP == "" {
Expand Down Expand Up @@ -87,7 +85,7 @@ func NewNode(ctx context.Context) (*P2PNode, error) {
return nil, err
}

// wrap the node with the routed host
// wrap the node with the routed host to improve network performance
rnode := routedhost.Wrap(node, p2pNode.dht)
p2pNode.Host = rnode
log.Debugf("Routed node created")
Expand All @@ -101,11 +99,26 @@ func NewNode(ctx context.Context) (*P2PNode, error) {
return nil, err
}

err = deleteNodeInfoFile()
if err != nil {
log.Errorf("error deleting node info file: %s", err)
return nil, err
}

// log the p2p node's ID
log.Infof("node created: %s", p2pNode.ID().Pretty())
saveNodeInfo("Node ID: " + p2pNode.ID().Pretty())

// log the p2p node's listening addresses
for _, addr := range p2pNode.Addrs() {
log.Infof("listening on: %s", addr.String())
}

return p2pNode, nil
}

// Initializes the DHT for the libp2p node in server mode.
func (p *P2PNode) initializeDHT(opts ...dht.Option) error {
func (p *P2PNode) initializeDHT(opts ...kadht.Option) error {
serverModeOpt := kadht.Mode(kadht.ModeServer)
opts = append(opts, serverModeOpt)
p.dht = &discovery.KadDHT{}
Expand Down

0 comments on commit 4e5ac3c

Please sign in to comment.