Skip to content

Commit baf3e76

Browse files
authored
Merge pull request #89 from ipfs/feat/update-bootstrappers
Update bootstrappers
2 parents 46ecb9d + b650735 commit baf3e76

File tree

7 files changed

+616
-2
lines changed

7 files changed

+616
-2
lines changed

Makefile

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -5,7 +5,7 @@ install:
55
test: test_go sharness
66

77
test_go:
8-
go test ./ipfs-5-to-6/... # go test ./... fails see #66
8+
go test ./ipfs-5-to-6/... ./ipfs-7-to-8/... # go test ./... fails see #66
99

1010
sharness:
1111
make -C sharness

ipfs-7-to-8/main.go

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,11 @@
1+
package main
2+
3+
import (
4+
migrate "github.com/ipfs/fs-repo-migrations/go-migrate"
5+
mg7 "github.com/ipfs/fs-repo-migrations/ipfs-7-to-8/migration"
6+
)
7+
8+
func main() {
9+
m := mg7.Migration{}
10+
migrate.Main(&m)
11+
}
Lines changed: 219 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,219 @@
1+
package mg7
2+
3+
import (
4+
"encoding/json"
5+
"fmt"
6+
"io"
7+
"io/ioutil"
8+
"os"
9+
"strings"
10+
)
11+
12+
var (
13+
dnsAddr = "bootstrap.libp2p.io"
14+
dnsBootstrapPeers = []string{
15+
"QmNnooDu7bfjPFoTZYxMNLWUQJyrVwtbZg5gBMjTezGAJN",
16+
"QmQCU2EcMqAqQPR2i9bChDtGNJchTbq5TbXJJ16u19uLTa",
17+
"QmbLHAnMoJPWSCR5Zhtx6BHJX9KiKNN6tpvbUcqanj75Nb",
18+
"QmcZf59bWwK5XFi76CZX8cbJ4BhTzzA3gU1ZjYZcYW3dwt",
19+
}
20+
smallKeyBootstrapPeers = []string{
21+
"QmSoLnSGccFuZQJzRadHn95W2CrSFmZuTdDWP8HXaHca9z",
22+
"QmSoLueR4xBeUbY9WZ9xGUUxunbKWcrNFTDAadQJmocnWm",
23+
"QmSoLMeWqB7YGVLJN3pNLQpmmEk35v6wYtsMGLzSr5QBU3",
24+
"QmSoLju6m7xTh3DuokvT3886QRYqxAzb1kShaanJgW36yx",
25+
"QmSoLPppuBtQSGwKDZT2M73ULpjvfd3aZ6ha4oFGL1KrGM",
26+
"QmSoLpPVmHKQ4XTPdz8tjDFgdeRFkpV8JgYq8JVJ69RrZm",
27+
"QmSoLSafTMBsPKadTEgaXctDQVcqN88CNLHXMkTNwMKPnu",
28+
"QmSoLV4Bbm51jM9C4gDYZQ9Cy3U6aXMJDAbzgu2fzaDs64",
29+
"QmSoLer265NRgSp2LA3dPaeykiS1J6DifTC88f5uVQKNAd",
30+
}
31+
oldBootstrapAddrs = []string{
32+
"/ip4/104.131.131.82/tcp/4001/p2p/QmaCpDMGvV2BGHeYERUEnRQAwe3N8SzbUtfsmvsqQLuvuJ",
33+
"/ip4/104.236.179.241/tcp/4001/p2p/QmSoLPppuBtQSGwKDZT2M73ULpjvfd3aZ6ha4oFGL1KrGM",
34+
"/ip4/128.199.219.111/tcp/4001/p2p/QmSoLSafTMBsPKadTEgaXctDQVcqN88CNLHXMkTNwMKPnu",
35+
"/ip4/104.236.76.40/tcp/4001/p2p/QmSoLV4Bbm51jM9C4gDYZQ9Cy3U6aXMJDAbzgu2fzaDs64",
36+
"/ip4/178.62.158.247/tcp/4001/p2p/QmSoLer265NRgSp2LA3dPaeykiS1J6DifTC88f5uVQKNAd",
37+
"/ip6/2604:a880:1:20::203:d001/tcp/4001/p2p/QmSoLPppuBtQSGwKDZT2M73ULpjvfd3aZ6ha4oFGL1KrGM",
38+
"/ip6/2400:6180:0:d0::151:6001/tcp/4001/p2p/QmSoLSafTMBsPKadTEgaXctDQVcqN88CNLHXMkTNwMKPnu",
39+
"/ip6/2604:a880:800:10::4a:5001/tcp/4001/p2p/QmSoLV4Bbm51jM9C4gDYZQ9Cy3U6aXMJDAbzgu2fzaDs64",
40+
"/ip6/2a03:b0c0:0:1010::23:1001/tcp/4001/p2p/QmSoLer265NRgSp2LA3dPaeykiS1J6DifTC88f5uVQKNAd",
41+
}
42+
)
43+
44+
// convFunc does an inplace conversion of the "Bootstrap"
45+
// configuration from one version to another
46+
type convFunc func([]string) []string
47+
48+
// convertFile converts a config file from one version to another, the
49+
// converted config is stored in
50+
func convertFile(orig string, new string, convFunc convFunc) error {
51+
in, err := os.Open(orig)
52+
if err != nil {
53+
return err
54+
}
55+
out, err := os.Create(new)
56+
if err != nil {
57+
return err
58+
}
59+
return convert(in, out, convFunc)
60+
}
61+
62+
// convert converts the config from one version to another, returns
63+
// the converted config as a map[string]interface{}
64+
func convert(in io.Reader, out io.Writer, convFunc convFunc) error {
65+
data, err := ioutil.ReadAll(in)
66+
if err != nil {
67+
return err
68+
}
69+
confMap := make(map[string]interface{})
70+
if err = json.Unmarshal(data, &confMap); err != nil {
71+
return err
72+
}
73+
bootstrapi, _ := confMap["Bootstrap"].([]interface{})
74+
if bootstrapi == nil {
75+
bootstrapi, _ := confMap["bootstrap"].([]interface{})
76+
if bootstrapi == nil {
77+
return fmt.Errorf("Bootstrap field missing or of the wrong type")
78+
}
79+
}
80+
bootstrap := make([]string, len(bootstrapi))
81+
for i := range bootstrapi {
82+
bootstrap[i] = bootstrapi[i].(string)
83+
}
84+
res := convFunc(bootstrap)
85+
confMap["Bootstrap"] = res
86+
fixed, err := json.MarshalIndent(confMap, "", " ")
87+
if err != nil {
88+
return err
89+
}
90+
out.Write(fixed)
91+
out.Write([]byte("\n"))
92+
return nil
93+
}
94+
95+
func ver7to8(bootstrap []string) []string {
96+
hasSmallKey := false
97+
for _, addr := range bootstrap {
98+
if ok, _ := isDNSBootstrapPeer(addr); ok {
99+
// Already has a dnsaddr key so assume the user has custom config
100+
// that we shouldn't override
101+
return bootstrap
102+
}
103+
if ok, _ := isSmallKeyPeer(addr); ok {
104+
hasSmallKey = true
105+
}
106+
}
107+
108+
if !hasSmallKey {
109+
// There are no peers with small keys in the bootstrap list so assume
110+
// the user has a custom config that we shouldn't override
111+
return bootstrap
112+
}
113+
114+
// Make sure the dnsaddrs bootstrap peers are included
115+
var res []string
116+
for _, p := range dnsBootstrapPeers {
117+
res = append(res, fmt.Sprintf("/dnsaddr/%s/p2p/%s", dnsAddr, p))
118+
}
119+
120+
// Filter out dnsaddr peers that we added above, or that have an ID known
121+
// to belong to a peer with a small key.
122+
// If we don't recognize the address format (err != nil), assume that the
123+
// user changed it for a reason and leave it in there.
124+
for _, addr := range bootstrap {
125+
if isDNSAddr, err := isDNSBootstrapPeer(addr); !isDNSAddr || err != nil {
126+
if isSmall, err := isSmallKeyPeer(addr); !isSmall || err != nil {
127+
// Change the protocol string from "ipfs" to "p2p".
128+
// Make sure we don't break addresses like
129+
// /dns4/ipfs-bootstrap.com/...
130+
// by matching specifically /ipfs/Qm or /ipfs/1...
131+
addr = strings.Replace(addr, "/ipfs/Qm", "/p2p/Qm", -1)
132+
addr = strings.Replace(addr, "/ipfs/1", "/p2p/1", -1)
133+
res = append(res, addr)
134+
}
135+
}
136+
}
137+
138+
return res
139+
}
140+
141+
func ver8to7(bootstrap []string) []string {
142+
// If the config doesn't have the new DNS addresses then assume it hasn't
143+
// been updated to version 8 and bail out
144+
hasDNSAddrs := false
145+
for _, addr := range bootstrap {
146+
if ok, _ := isDNSBootstrapPeer(addr); ok {
147+
hasDNSAddrs = true
148+
}
149+
}
150+
if !hasDNSAddrs {
151+
return bootstrap
152+
}
153+
154+
// Extract peer IDs from old bootstrap addresses
155+
var oldBootstrapPeerIDs []string
156+
for _, oldAddr := range oldBootstrapAddrs {
157+
if p, err := getAddrPeerID(oldAddr); err == nil {
158+
oldBootstrapPeerIDs = append(oldBootstrapPeerIDs, p)
159+
}
160+
}
161+
162+
// Make sure the old addresses are included in the result
163+
res := append([]string{}, oldBootstrapAddrs...)
164+
165+
// Filter out old addresses added above
166+
for _, addr := range bootstrap {
167+
isOldPeer, err := addrPeerIDInList(oldBootstrapPeerIDs, addr)
168+
169+
// If we don't recognize the address format, just assume the user
170+
// has changed it on purpose and include it in the results
171+
if !isOldPeer || err != nil {
172+
res = append(res, addr)
173+
}
174+
}
175+
176+
return res
177+
}
178+
179+
func parseErr(addr string) error {
180+
return fmt.Errorf("Could not parse peer ID from addr '%s'", addr)
181+
}
182+
183+
func getAddrPeerID(addr string) (string, error) {
184+
// eg /ip4/104.131.131.82/tcp/4001/ipfs/QmaCpDMGvV2BGHeYERUEnRQAwe3N8SzbUtfsmvsqQLuvuJ
185+
parts := strings.Split(addr, "/")
186+
if len(parts) < 2 {
187+
return "", parseErr(addr)
188+
}
189+
190+
// Just verify that the address ends with /p2p/something or /ipfs/something
191+
peerType := parts[len(parts)-2]
192+
if peerType != "p2p" && peerType != "ipfs" {
193+
return "", parseErr(addr)
194+
}
195+
196+
last := parts[len(parts)-1]
197+
return last, nil
198+
}
199+
200+
func addrPeerIDInList(peerIDs []string, addr string) (bool, error) {
201+
addrID, err := getAddrPeerID(addr)
202+
if err != nil {
203+
return false, err
204+
}
205+
for _, p := range peerIDs {
206+
if p == addrID {
207+
return true, nil
208+
}
209+
}
210+
return false, nil
211+
}
212+
213+
func isDNSBootstrapPeer(addr string) (bool, error) {
214+
return addrPeerIDInList(dnsBootstrapPeers, addr)
215+
}
216+
217+
func isSmallKeyPeer(addr string) (bool, error) {
218+
return addrPeerIDInList(smallKeyBootstrapPeers, addr)
219+
}

0 commit comments

Comments
 (0)