Skip to content

Rename beacon to boostrapper, define bootstrappers in JSON file for cross-language compatiblity #1439

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

Merged
merged 35 commits into from
May 30, 2023
Merged
Show file tree
Hide file tree
Changes from 27 commits
Commits
Show all changes
35 commits
Select commit Hold shift + click to select a range
e77d476
genesis: add "getBeacons" to wrap getNodeIDs/IPs
gyuho Apr 27, 2023
671370d
add beacons.json with full compatibility checks
gyuho Apr 27, 2023
4ca21a7
rename beacons to bootstrappers
gyuho Apr 27, 2023
db00eca
use "SampleBootstrappers"
gyuho Apr 27, 2023
afa65c8
use "embed" to load bootstrapper.json file
gyuho Apr 27, 2023
ce679ca
use IPDesc
gyuho Apr 27, 2023
f86d352
ips: add unit test for IPDesc
gyuho Apr 27, 2023
b3bd5b4
use IPDesc/NodeID
gyuho Apr 27, 2023
d20c3ac
bootstrapper: fix static analysis
gyuho Apr 27, 2023
ba89041
skip empty IP/ID for bootstrap
gyuho Apr 27, 2023
6659f38
Merge branch 'dev' into cleanup-beacons
gyuho Apr 27, 2023
d38f33a
genesis: use network name as a key to bootstrappers.json
gyuho Apr 27, 2023
bd17aaf
fix config
gyuho Apr 28, 2023
770ec1c
fix config
gyuho Apr 28, 2023
9caf16a
config: fix static analysis warn
gyuho Apr 28, 2023
fcef58e
Update genesis/bootstrappers.go
gyuho Apr 30, 2023
6dfc25e
Merge branch 'dev' into cleanup-beacons
gyuho May 1, 2023
3d0d936
Merge branch 'dev' into cleanup-beacons
gyuho May 1, 2023
9425eb1
genesis: add a simple unit test for SampleBootstrappers
gyuho May 1, 2023
1b4809a
genesis: simplify with math.Min
gyuho May 1, 2023
0749f29
node, config: add "--bootstrappers" flag
gyuho May 1, 2023
4d9f66c
Merge branch 'dev' into cleanup-beacons
gyuho May 4, 2023
911dea6
Merge branch 'dev' into cleanup-beacons
gyuho May 30, 2023
fc499b9
Update config/config.go
gyuho May 30, 2023
d115c33
Update config/flags.go
gyuho May 30, 2023
ef42f4a
Update config/flags.go
gyuho May 30, 2023
2bb8be2
Update config/config.go
gyuho May 30, 2023
e52a4d7
Update config/config.go
gyuho May 30, 2023
b16d85f
config: gofmt
gyuho May 30, 2023
da33ca3
config: remove --bootstrappers flag
gyuho May 30, 2023
bf5eeac
simplify bootstrap parsing
StephenButtolph May 30, 2023
256fd3a
fix error message
StephenButtolph May 30, 2023
8001e89
nits
StephenButtolph May 30, 2023
e4f5868
Fix nit + improve tests
StephenButtolph May 30, 2023
ce36ed0
Merge branch 'dev' into cleanup-beacons
StephenButtolph May 30, 2023
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
70 changes: 44 additions & 26 deletions config/config.go
Original file line number Diff line number Diff line change
Expand Up @@ -62,8 +62,11 @@ const (

var (
// Deprecated key --> deprecation message (i.e. which key replaces it)
// TODO: deprecate "BootstrapIDsKey" and "BootstrapIPsKey"
deprecatedKeys = map[string]string{
NetworkCompressionEnabledKey: fmt.Sprintf("use --%s instead", NetworkCompressionTypeKey),
BootstrapIDsKey: fmt.Sprintf("use --%s instead", BootstrappersKey),
BootstrapIPsKey: fmt.Sprintf("use --%s instead", BootstrappersKey),
GenesisConfigFileKey: fmt.Sprintf("use --%s instead", GenesisFileKey),
GenesisConfigContentKey: fmt.Sprintf("use --%s instead", GenesisFileContentKey),
InboundConnUpgradeThrottlerCooldownKey: fmt.Sprintf("use --%s instead", NetworkInboundConnUpgradeThrottlerCooldownKey),
Expand Down Expand Up @@ -532,6 +535,12 @@ func getBootstrapConfig(v *viper.Viper, networkID uint32) (node.BootstrapConfig,
BootstrapAncestorsMaxContainersReceived: int(v.GetUint(BootstrapAncestorsMaxContainersReceivedKey)),
}

if v.IsSet(BootstrappersKey) {
s := v.GetString(BootstrappersKey)
return config, json.Unmarshal([]byte(s), &config.Bootstrappers)
}

// "--bootstrappers" is not set, so fallback to old flags
ipsSet := v.IsSet(BootstrapIPsKey)
idsSet := v.IsSet(BootstrapIDsKey)
if ipsSet && !idsSet {
Expand All @@ -541,39 +550,48 @@ func getBootstrapConfig(v *viper.Viper, networkID uint32) (node.BootstrapConfig,
return node.BootstrapConfig{}, fmt.Errorf("set %q but didn't set %q", BootstrapIDsKey, BootstrapIPsKey)
}

bootstrapIPs, bootstrapIDs := genesis.SampleBeacons(networkID, 5)
bootstrappers := genesis.SampleBootstrappers(networkID, 5)
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This code is really pretty jank and confusing. Should we replace config.BootstrapIPs and config.BootstrapIDs with config.Bootstrapers?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

+1000, I think combining them into a single flag value of JSON format is much simpler.

if ipsSet {
bootstrapIPs = strings.Split(v.GetString(BootstrapIPsKey), ",")
}
for _, ip := range bootstrapIPs {
if ip == "" {
continue
}
addr, err := ips.ToIPPort(ip)
if err != nil {
return node.BootstrapConfig{}, fmt.Errorf("couldn't parse bootstrap ip %s: %w", ip, err)
bootstrapIPs := strings.Split(v.GetString(BootstrapIPsKey), ",")

bootstrappers = make([]genesis.Bootstrapper, 0, len(bootstrapIPs))
for _, bootstrapIP := range bootstrapIPs {
ip := strings.TrimSpace(bootstrapIP)
if ip == "" {
continue
}

addr, err := ips.ToIPPort(ip)
if err != nil {
return node.BootstrapConfig{}, fmt.Errorf("couldn't parse bootstrap ip %s: %w", ip, err)
}
bootstrappers = append(bootstrappers, genesis.Bootstrapper{ID: ids.EmptyNodeID, IP: ips.IPDesc(addr)})
}
config.BootstrapIPs = append(config.BootstrapIPs, addr)
}
config.Bootstrappers = bootstrappers

if idsSet {
bootstrapIDs = strings.Split(v.GetString(BootstrapIDsKey), ",")
}
for _, id := range bootstrapIDs {
if id == "" {
continue
}
nodeID, err := ids.NodeIDFromString(id)
if err != nil {
return node.BootstrapConfig{}, fmt.Errorf("couldn't parse bootstrap peer id %s: %w", id, err)
bootstrapIDs := strings.Split(v.GetString(BootstrapIDsKey), ",")

bootstrapNodeIDs := make([]ids.NodeID, 0, len(bootstrapIDs))
for _, bootstrapID := range bootstrapIDs {
id := strings.TrimSpace(bootstrapID)
if id == "" {
continue
}
nodeID, err := ids.NodeIDFromString(id)
if err != nil {
return node.BootstrapConfig{}, fmt.Errorf("couldn't parse bootstrap peer id %s: %w", nodeID, err)
}
bootstrapNodeIDs = append(bootstrapNodeIDs, nodeID)
}
config.BootstrapIDs = append(config.BootstrapIDs, nodeID)
}

lenIPs := len(config.BootstrapIPs)
lenIDs := len(config.BootstrapIDs)
if lenIPs != lenIDs {
return node.BootstrapConfig{}, fmt.Errorf("expected the number of bootstrapIPs (%d) to match the number of bootstrapIDs (%d)", lenIPs, lenIDs)
if len(config.Bootstrappers) != len(bootstrapNodeIDs) {
return node.BootstrapConfig{}, fmt.Errorf("expected the number of bootstrapIPs (%d) to match the number of bootstrapNodeIDs (%d)", len(config.Bootstrappers), len(bootstrapNodeIDs))
}
for i, nodeID := range bootstrapNodeIDs {
config.Bootstrappers[i].ID = nodeID
}
}

return config, nil
Expand Down
2 changes: 2 additions & 0 deletions config/flags.go
Original file line number Diff line number Diff line change
Expand Up @@ -297,6 +297,8 @@ func addNodeFlags(fs *pflag.FlagSet) {
fs.String(StateSyncIDsKey, "", "Comma separated list of state sync peer ids to connect to. Example: NodeID-JR4dVmy6ffUGAKCBDkyCbeZbyHQBeDsET,NodeID-8CrVPQZ4VSqgL8zTdvL14G8HqAfrBr4z")

// Bootstrapping
fs.String(BootstrappersKey, "", "JSON-encoded list of bootstrap node ids and ips to connect to. If set, overrides --bootstrap-ips/ids. Example: '[{\"id\":\"NodeID-JR4dVmy6ffUGAKCBDkyCbeZbyHQBeDsET\",\"ip\":\"127.0.0.1:9630\"}]'")
// TODO: add [DEPRECATED] and deprecate
fs.String(BootstrapIPsKey, "", "Comma separated list of bootstrap peer ips to connect to. Example: 127.0.0.1:9630,127.0.0.1:9631")
fs.String(BootstrapIDsKey, "", "Comma separated list of bootstrap peer ids to connect to. Example: NodeID-JR4dVmy6ffUGAKCBDkyCbeZbyHQBeDsET,NodeID-8CrVPQZ4VSqgL8zTdvL14G8HqAfrBr4z")
fs.Bool(RetryBootstrapKey, true, "Specifies whether bootstrap should be retried")
Expand Down
1 change: 1 addition & 0 deletions config/keys.go
Original file line number Diff line number Diff line change
Expand Up @@ -65,6 +65,7 @@ const (
APIAuthPasswordFileKey = "api-auth-password-file"
StateSyncIPsKey = "state-sync-ips"
StateSyncIDsKey = "state-sync-ids"
BootstrappersKey = "bootstrappers"
BootstrapIPsKey = "bootstrap-ips"
BootstrapIDsKey = "bootstrap-ids"
StakingPortKey = "staking-port"
Expand Down
150 changes: 0 additions & 150 deletions genesis/beacons.go

This file was deleted.

54 changes: 54 additions & 0 deletions genesis/bootstrappers.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,54 @@
// Copyright (C) 2019-2023, Ava Labs, Inc. All rights reserved.
// See the file LICENSE for licensing terms.

package genesis

import (
_ "embed"
"encoding/json"
"fmt"

"github.com/ava-labs/avalanchego/ids"
"github.com/ava-labs/avalanchego/utils/constants"
"github.com/ava-labs/avalanchego/utils/ips"
"github.com/ava-labs/avalanchego/utils/math"
"github.com/ava-labs/avalanchego/utils/sampler"
)

var (
//go:embed bootstrappers.json
bootstrappersPerNetworkJSON []byte

bootstrappersPerNetwork map[string][]Bootstrapper
)

func init() {
if err := json.Unmarshal(bootstrappersPerNetworkJSON, &bootstrappersPerNetwork); err != nil {
panic(fmt.Sprintf("failed to decode bootstrappers.json %v", err))
}
}

// Represents the relationship between the nodeID and the nodeIP.
// The bootstrapper is sometimes called "anchor" or "beacon" node.
type Bootstrapper struct {
ID ids.NodeID `json:"id"`
IP ips.IPDesc `json:"ip"`
}

// SampleBootstrappers returns the some beacons this node should connect to
func SampleBootstrappers(networkID uint32, count int) []Bootstrapper {
networkName := constants.NetworkIDToNetworkName[networkID]
bootstrappers := bootstrappersPerNetwork[networkName]
count = math.Min(count, len(bootstrappers))

s := sampler.NewUniform()
s.Initialize(uint64(len(bootstrappers)))
indices, _ := s.Sample(count)

sampled := make([]Bootstrapper, 0, len(indices))
for _, index := range indices {
sampled = append(sampled, bootstrappers[int(index)])
}

return sampled
}
Loading