Skip to content

Commit 94000e6

Browse files
committedAug 27, 2015
replace nodebuilder with a nicer interface
License: MIT Signed-off-by: Jeromy <jeromyj@gmail.com> use NewNode instead of NewIPFSNode in most of the codebase License: MIT Signed-off-by: Jeromy <jeromyj@gmail.com> make mocknet work with node constructor better License: MIT Signed-off-by: Jeromy <jeromyj@gmail.com> finish cleanup of old construction method License: MIT Signed-off-by: Jeromy <jeromyj@gmail.com> blockservice.New doesnt return an error anymore License: MIT Signed-off-by: Jeromy <jeromyj@gmail.com> break up node construction into separate function License: MIT Signed-off-by: Jeromy <jeromyj@gmail.com> add error case to default filling on node constructor License: MIT Signed-off-by: Jeromy <jeromyj@gmail.com>
1 parent 7abebb1 commit 94000e6

21 files changed

+253
-401
lines changed
 

‎cmd/ipfs/daemon.go

+8-5
Original file line numberDiff line numberDiff line change
@@ -192,9 +192,11 @@ func daemonFunc(req cmds.Request, res cmds.Response) {
192192
return
193193
}
194194

195-
// Start assembling corebuilder
196-
nb := core.NewNodeBuilder().Online()
197-
nb.SetRepo(repo)
195+
// Start assembling node config
196+
ncfg := &core.BuildCfg{
197+
Online: true,
198+
Repo: repo,
199+
}
198200

199201
routingOption, _, err := req.Option(routingOptionKwd).String()
200202
if err != nil {
@@ -215,10 +217,11 @@ func daemonFunc(req cmds.Request, res cmds.Response) {
215217
Addrs: []ma.Multiaddr{addr.Transport()},
216218
})
217219
}
218-
nb.SetRouting(corerouting.SupernodeClient(infos...))
220+
221+
ncfg.Routing = corerouting.SupernodeClient(infos...)
219222
}
220223

221-
node, err := nb.Build(req.Context())
224+
node, err := core.NewNode(req.Context(), ncfg)
222225
if err != nil {
223226
log.Error("error from node construction: ", err)
224227
res.SetError(err, cmds.ErrNormal)

‎cmd/ipfs/init.go

+2-2
Original file line numberDiff line numberDiff line change
@@ -157,7 +157,7 @@ func addDefaultAssets(out io.Writer, repoRoot string) error {
157157
return err
158158
}
159159

160-
nd, err := core.NewIPFSNode(ctx, core.Offline(r))
160+
nd, err := core.NewNode(ctx, &core.BuildCfg{Repo: r})
161161
if err != nil {
162162
return err
163163
}
@@ -191,7 +191,7 @@ func initializeIpnsKeyspace(repoRoot string) error {
191191
return err
192192
}
193193

194-
nd, err := core.NewIPFSNode(ctx, core.Offline(r))
194+
nd, err := core.NewNode(ctx, &core.BuildCfg{Repo: r})
195195
if err != nil {
196196
return err
197197
}

‎cmd/ipfs/main.go

+4-1
Original file line numberDiff line numberDiff line change
@@ -204,7 +204,10 @@ func (i *cmdInvocation) constructNodeFunc(ctx context.Context) func() (*core.Ipf
204204

205205
// ok everything is good. set it on the invocation (for ownership)
206206
// and return it.
207-
n, err := core.NewIPFSNode(ctx, core.Standard(r, cmdctx.Online))
207+
n, err := core.NewNode(ctx, &core.BuildCfg{
208+
Online: cmdctx.Online,
209+
Repo: r,
210+
})
208211
if err != nil {
209212
return nil, err
210213
}

‎cmd/ipfswatch/main.go

+5-1
Original file line numberDiff line numberDiff line change
@@ -71,7 +71,11 @@ func run(ipfsPath, watchPath string) error {
7171
// TODO handle case: repo doesn't exist or isn't initialized
7272
return err
7373
}
74-
node, err := core.NewIPFSNode(context.Background(), core.Online(r))
74+
75+
node, err := core.NewNode(context.Background(), &core.BuildCfg{
76+
Online: true,
77+
Repo: r,
78+
})
7579
if err != nil {
7680
return err
7781
}

‎core/builder.go

+98-53
Original file line numberDiff line numberDiff line change
@@ -7,31 +7,60 @@ import (
77

88
ds "github.com/ipfs/go-ipfs/Godeps/_workspace/src/github.com/jbenet/go-datastore"
99
dsync "github.com/ipfs/go-ipfs/Godeps/_workspace/src/github.com/jbenet/go-datastore/sync"
10+
goprocessctx "github.com/ipfs/go-ipfs/Godeps/_workspace/src/github.com/jbenet/goprocess/context"
1011
context "github.com/ipfs/go-ipfs/Godeps/_workspace/src/golang.org/x/net/context"
12+
bstore "github.com/ipfs/go-ipfs/blocks/blockstore"
1113
key "github.com/ipfs/go-ipfs/blocks/key"
14+
bserv "github.com/ipfs/go-ipfs/blockservice"
15+
offline "github.com/ipfs/go-ipfs/exchange/offline"
16+
dag "github.com/ipfs/go-ipfs/merkledag"
1217
ci "github.com/ipfs/go-ipfs/p2p/crypto"
18+
peer "github.com/ipfs/go-ipfs/p2p/peer"
19+
path "github.com/ipfs/go-ipfs/path"
20+
pin "github.com/ipfs/go-ipfs/pin"
1321
repo "github.com/ipfs/go-ipfs/repo"
1422
cfg "github.com/ipfs/go-ipfs/repo/config"
1523
)
1624

17-
var ErrAlreadyBuilt = errors.New("this builder has already been used")
25+
type BuildCfg struct {
26+
// If online is set, the node will have networking enabled
27+
Online bool
1828

19-
// NodeBuilder is an object used to generate an IpfsNode
20-
type NodeBuilder struct {
21-
online bool
22-
routing RoutingOption
23-
peerhost HostOption
24-
repo repo.Repo
25-
built bool
26-
nilrepo bool
29+
// If NilRepo is set, a repo backed by a nil datastore will be constructed
30+
NilRepo bool
31+
32+
Routing RoutingOption
33+
Host HostOption
34+
Repo repo.Repo
2735
}
2836

29-
func NewNodeBuilder() *NodeBuilder {
30-
return &NodeBuilder{
31-
online: false,
32-
routing: DHTOption,
33-
peerhost: DefaultHostOption,
37+
func (cfg *BuildCfg) fillDefaults() error {
38+
if cfg.Repo != nil && cfg.NilRepo {
39+
return errors.New("cannot set a repo and specify nilrepo at the same time")
3440
}
41+
42+
if cfg.Repo == nil {
43+
var d ds.Datastore
44+
d = ds.NewMapDatastore()
45+
if cfg.NilRepo {
46+
d = ds.NewNullDatastore()
47+
}
48+
r, err := defaultRepo(dsync.MutexWrap(d))
49+
if err != nil {
50+
return err
51+
}
52+
cfg.Repo = r
53+
}
54+
55+
if cfg.Routing == nil {
56+
cfg.Routing = DHTOption
57+
}
58+
59+
if cfg.Host == nil {
60+
cfg.Host = DefaultHostOption
61+
}
62+
63+
return nil
3564
}
3665

3766
func defaultRepo(dstore ds.ThreadSafeDatastore) (repo.Repo, error) {
@@ -62,53 +91,69 @@ func defaultRepo(dstore ds.ThreadSafeDatastore) (repo.Repo, error) {
6291
}, nil
6392
}
6493

65-
func (nb *NodeBuilder) Online() *NodeBuilder {
66-
nb.online = true
67-
return nb
68-
}
94+
func NewNode(ctx context.Context, cfg *BuildCfg) (*IpfsNode, error) {
95+
if cfg == nil {
96+
cfg = new(BuildCfg)
97+
}
6998

70-
func (nb *NodeBuilder) Offline() *NodeBuilder {
71-
nb.online = false
72-
return nb
73-
}
99+
err := cfg.fillDefaults()
100+
if err != nil {
101+
return nil, err
102+
}
74103

75-
func (nb *NodeBuilder) SetRouting(ro RoutingOption) *NodeBuilder {
76-
nb.routing = ro
77-
return nb
78-
}
104+
n := &IpfsNode{
105+
mode: offlineMode,
106+
Repo: cfg.Repo,
107+
ctx: ctx,
108+
Peerstore: peer.NewPeerstore(),
109+
}
110+
if cfg.Online {
111+
n.mode = onlineMode
112+
}
79113

80-
func (nb *NodeBuilder) SetHost(ho HostOption) *NodeBuilder {
81-
nb.peerhost = ho
82-
return nb
83-
}
114+
// TODO: this is a weird circular-ish dependency, rework it
115+
n.proc = goprocessctx.WithContextAndTeardown(ctx, n.teardown)
84116

85-
func (nb *NodeBuilder) SetRepo(r repo.Repo) *NodeBuilder {
86-
nb.repo = r
87-
return nb
88-
}
117+
if err := setupNode(ctx, n, cfg); err != nil {
118+
n.Close()
119+
return nil, err
120+
}
89121

90-
func (nb *NodeBuilder) NilRepo() *NodeBuilder {
91-
nb.nilrepo = true
92-
return nb
122+
return n, nil
93123
}
94124

95-
func (nb *NodeBuilder) Build(ctx context.Context) (*IpfsNode, error) {
96-
if nb.built {
97-
return nil, ErrAlreadyBuilt
125+
func setupNode(ctx context.Context, n *IpfsNode, cfg *BuildCfg) error {
126+
// setup local peer ID (private key is loaded in online setup)
127+
if err := n.loadID(); err != nil {
128+
return err
98129
}
99-
nb.built = true
100-
if nb.repo == nil {
101-
var d ds.Datastore
102-
d = ds.NewMapDatastore()
103-
if nb.nilrepo {
104-
d = ds.NewNullDatastore()
105-
}
106-
r, err := defaultRepo(dsync.MutexWrap(d))
107-
if err != nil {
108-
return nil, err
130+
131+
var err error
132+
n.Blockstore, err = bstore.WriteCached(bstore.NewBlockstore(n.Repo.Datastore()), kSizeBlockstoreWriteCache)
133+
if err != nil {
134+
return err
135+
}
136+
137+
if cfg.Online {
138+
do := setupDiscoveryOption(n.Repo.Config().Discovery)
139+
if err := n.startOnlineServices(ctx, cfg.Routing, cfg.Host, do); err != nil {
140+
return err
109141
}
110-
nb.repo = r
142+
} else {
143+
n.Exchange = offline.Exchange(n.Blockstore)
111144
}
112-
conf := standardWithRouting(nb.repo, nb.online, nb.routing, nb.peerhost)
113-
return NewIPFSNode(ctx, conf)
145+
146+
n.Blocks = bserv.New(n.Blockstore, n.Exchange)
147+
n.DAG = dag.NewDAGService(n.Blocks)
148+
n.Pinning, err = pin.LoadPinner(n.Repo.Datastore(), n.DAG)
149+
if err != nil {
150+
// TODO: we should move towards only running 'NewPinner' explicity on
151+
// node init instead of implicitly here as a result of the pinner keys
152+
// not being found in the datastore.
153+
// this is kinda sketchy and could cause data loss
154+
n.Pinning = pin.NewPinner(n.Repo.Datastore(), n.DAG)
155+
}
156+
n.Resolver = &path.Resolver{DAG: n.DAG}
157+
158+
return nil
114159
}

‎core/commands/add.go

+5-1
Original file line numberDiff line numberDiff line change
@@ -104,7 +104,11 @@ remains to be implemented.
104104
chunker, _, _ := req.Option(chunkerOptionName).String()
105105

106106
if hash {
107-
nilnode, err := core.NewNodeBuilder().Build(n.Context())
107+
nilnode, err := core.NewNode(n.Context(), &core.BuildCfg{
108+
//TODO: need this to be true or all files
109+
// hashed will be stored in memory!
110+
NilRepo: false,
111+
})
108112
if err != nil {
109113
res.SetError(err, cmds.ErrNormal)
110114
return

‎core/core.go

+4-121
Original file line numberDiff line numberDiff line change
@@ -20,7 +20,6 @@ import (
2020
ds "github.com/ipfs/go-ipfs/Godeps/_workspace/src/github.com/jbenet/go-datastore"
2121
ma "github.com/ipfs/go-ipfs/Godeps/_workspace/src/github.com/jbenet/go-multiaddr"
2222
goprocess "github.com/ipfs/go-ipfs/Godeps/_workspace/src/github.com/jbenet/goprocess"
23-
goprocessctx "github.com/ipfs/go-ipfs/Godeps/_workspace/src/github.com/jbenet/goprocess/context"
2423
mamask "github.com/ipfs/go-ipfs/Godeps/_workspace/src/github.com/whyrusleeping/multiaddr-filter"
2524
context "github.com/ipfs/go-ipfs/Godeps/_workspace/src/golang.org/x/net/context"
2625
diag "github.com/ipfs/go-ipfs/diagnostics"
@@ -46,7 +45,6 @@ import (
4645
exchange "github.com/ipfs/go-ipfs/exchange"
4746
bitswap "github.com/ipfs/go-ipfs/exchange/bitswap"
4847
bsnet "github.com/ipfs/go-ipfs/exchange/bitswap/network"
49-
offline "github.com/ipfs/go-ipfs/exchange/offline"
5048
rp "github.com/ipfs/go-ipfs/exchange/reprovide"
5149

5250
mount "github.com/ipfs/go-ipfs/fuse/mount"
@@ -123,124 +121,6 @@ type Mounts struct {
123121
Ipns mount.Mount
124122
}
125123

126-
type ConfigOption func(ctx context.Context) (*IpfsNode, error)
127-
128-
func NewIPFSNode(ctx context.Context, option ConfigOption) (*IpfsNode, error) {
129-
node, err := option(ctx)
130-
if err != nil {
131-
return nil, err
132-
}
133-
134-
if node.ctx == nil {
135-
node.ctx = ctx
136-
}
137-
if node.proc == nil {
138-
node.proc = goprocessctx.WithContextAndTeardown(node.ctx, node.teardown)
139-
}
140-
141-
success := false // flip to true after all sub-system inits succeed
142-
defer func() {
143-
if !success {
144-
node.proc.Close()
145-
}
146-
}()
147-
148-
// Need to make sure it's perfectly clear 1) which variables are expected
149-
// to be initialized at this point, and 2) which variables will be
150-
// initialized after this point.
151-
152-
node.Blocks = bserv.New(node.Blockstore, node.Exchange)
153-
154-
if node.Peerstore == nil {
155-
node.Peerstore = peer.NewPeerstore()
156-
}
157-
node.DAG = merkledag.NewDAGService(node.Blocks)
158-
node.Pinning, err = pin.LoadPinner(node.Repo.Datastore(), node.DAG)
159-
if err != nil {
160-
node.Pinning = pin.NewPinner(node.Repo.Datastore(), node.DAG)
161-
}
162-
node.Resolver = &path.Resolver{DAG: node.DAG}
163-
164-
success = true
165-
return node, nil
166-
}
167-
168-
func Offline(r repo.Repo) ConfigOption {
169-
return Standard(r, false)
170-
}
171-
172-
func OnlineWithOptions(r repo.Repo, router RoutingOption, ho HostOption) ConfigOption {
173-
return standardWithRouting(r, true, router, ho)
174-
}
175-
176-
func Online(r repo.Repo) ConfigOption {
177-
return Standard(r, true)
178-
}
179-
180-
// DEPRECATED: use Online, Offline functions
181-
func Standard(r repo.Repo, online bool) ConfigOption {
182-
return standardWithRouting(r, online, DHTOption, DefaultHostOption)
183-
}
184-
185-
// TODO refactor so maybeRouter isn't special-cased in this way
186-
func standardWithRouting(r repo.Repo, online bool, routingOption RoutingOption, hostOption HostOption) ConfigOption {
187-
return func(ctx context.Context) (n *IpfsNode, err error) {
188-
// FIXME perform node construction in the main constructor so it isn't
189-
// necessary to perform this teardown in this scope.
190-
success := false
191-
defer func() {
192-
if !success && n != nil {
193-
n.teardown()
194-
}
195-
}()
196-
197-
// TODO move as much of node initialization as possible into
198-
// NewIPFSNode. The larger these config options are, the harder it is
199-
// to test all node construction code paths.
200-
201-
if r == nil {
202-
return nil, fmt.Errorf("repo required")
203-
}
204-
n = &IpfsNode{
205-
mode: func() mode {
206-
if online {
207-
return onlineMode
208-
}
209-
return offlineMode
210-
}(),
211-
Repo: r,
212-
}
213-
214-
n.ctx = ctx
215-
n.proc = goprocessctx.WithContextAndTeardown(ctx, n.teardown)
216-
217-
// setup Peerstore
218-
n.Peerstore = peer.NewPeerstore()
219-
220-
// setup local peer ID (private key is loaded in online setup)
221-
if err := n.loadID(); err != nil {
222-
return nil, err
223-
}
224-
225-
n.Blockstore, err = bstore.WriteCached(bstore.NewBlockstore(n.Repo.Datastore()), kSizeBlockstoreWriteCache)
226-
if err != nil {
227-
return nil, err
228-
}
229-
230-
if online {
231-
do := setupDiscoveryOption(n.Repo.Config().Discovery)
232-
if err := n.startOnlineServices(ctx, routingOption, hostOption, do); err != nil {
233-
return nil, err
234-
}
235-
} else {
236-
n.Exchange = offline.Exchange(n.Blockstore)
237-
}
238-
239-
success = true
240-
return n, nil
241-
}
242-
}
243-
244124
func (n *IpfsNode) startOnlineServices(ctx context.Context, routingOption RoutingOption, hostOption HostOption, do DiscoveryOption) error {
245125

246126
if n.PeerHost != nil { // already online.
@@ -371,10 +251,13 @@ func (n *IpfsNode) teardown() error {
371251
// owned objects are closed in this teardown to ensure that they're closed
372252
// regardless of which constructor was used to add them to the node.
373253
closers := []io.Closer{
374-
n.Exchange,
375254
n.Repo,
376255
}
377256

257+
if n.Exchange != nil {
258+
closers = append(closers, n.Exchange)
259+
}
260+
378261
if n.Mounts.Ipfs != nil {
379262
closers = append(closers, mount.Closer(n.Mounts.Ipfs))
380263
}

‎core/core_test.go

+2-2
Original file line numberDiff line numberDiff line change
@@ -48,7 +48,7 @@ func TestInitialization(t *testing.T) {
4848
C: *c,
4949
D: testutil.ThreadSafeCloserMapDatastore(),
5050
}
51-
n, err := NewIPFSNode(ctx, Standard(r, false))
51+
n, err := NewNode(ctx, &BuildCfg{Repo: r})
5252
if n == nil || err != nil {
5353
t.Error("Should have constructed.", i, err)
5454
}
@@ -59,7 +59,7 @@ func TestInitialization(t *testing.T) {
5959
C: *c,
6060
D: testutil.ThreadSafeCloserMapDatastore(),
6161
}
62-
n, err := NewIPFSNode(ctx, Standard(r, false))
62+
n, err := NewNode(ctx, &BuildCfg{Repo: r})
6363
if n != nil || err == nil {
6464
t.Error("Should have failed to construct.", i)
6565
}

‎core/corehttp/gateway_test.go

+1-1
Original file line numberDiff line numberDiff line change
@@ -47,7 +47,7 @@ func newNodeWithMockNamesys(ns mockNamesys) (*core.IpfsNode, error) {
4747
C: c,
4848
D: testutil.ThreadSafeCloserMapDatastore(),
4949
}
50-
n, err := core.NewIPFSNode(context.Background(), core.Offline(r))
50+
n, err := core.NewNode(context.Background(), &core.BuildCfg{Repo: r})
5151
if err != nil {
5252
return nil, err
5353
}

‎core/coreunix/add_test.go

+1-1
Original file line numberDiff line numberDiff line change
@@ -25,7 +25,7 @@ func TestAddRecursive(t *testing.T) {
2525
},
2626
D: testutil.ThreadSafeCloserMapDatastore(),
2727
}
28-
node, err := core.NewIPFSNode(context.Background(), core.Offline(r))
28+
node, err := core.NewNode(context.Background(), &core.BuildCfg{Repo: r})
2929
if err != nil {
3030
t.Fatal(err)
3131
}

‎core/mock/mock.go

+19-62
Original file line numberDiff line numberDiff line change
@@ -1,86 +1,39 @@
11
package coremock
22

33
import (
4+
"net"
5+
46
"github.com/ipfs/go-ipfs/Godeps/_workspace/src/github.com/jbenet/go-datastore"
57
syncds "github.com/ipfs/go-ipfs/Godeps/_workspace/src/github.com/jbenet/go-datastore/sync"
68
context "github.com/ipfs/go-ipfs/Godeps/_workspace/src/golang.org/x/net/context"
79

8-
"github.com/ipfs/go-ipfs/blocks/blockstore"
9-
blockservice "github.com/ipfs/go-ipfs/blockservice"
1010
commands "github.com/ipfs/go-ipfs/commands"
1111
core "github.com/ipfs/go-ipfs/core"
12-
"github.com/ipfs/go-ipfs/exchange/offline"
13-
mdag "github.com/ipfs/go-ipfs/merkledag"
14-
nsys "github.com/ipfs/go-ipfs/namesys"
12+
metrics "github.com/ipfs/go-ipfs/metrics"
13+
host "github.com/ipfs/go-ipfs/p2p/host"
1514
mocknet "github.com/ipfs/go-ipfs/p2p/net/mock"
1615
peer "github.com/ipfs/go-ipfs/p2p/peer"
17-
path "github.com/ipfs/go-ipfs/path"
18-
pin "github.com/ipfs/go-ipfs/pin"
1916
"github.com/ipfs/go-ipfs/repo"
2017
config "github.com/ipfs/go-ipfs/repo/config"
21-
offrt "github.com/ipfs/go-ipfs/routing/offline"
2218
ds2 "github.com/ipfs/go-ipfs/util/datastore2"
2319
testutil "github.com/ipfs/go-ipfs/util/testutil"
2420
)
2521

26-
// TODO this is super sketch. Deprecate and initialize one that shares code
27-
// with the actual core constructor. Lots of fields aren't initialized.
28-
// "This is as good as broken." --- is it?
29-
3022
// NewMockNode constructs an IpfsNode for use in tests.
3123
func NewMockNode() (*core.IpfsNode, error) {
3224
ctx := context.Background()
3325

34-
// Generate Identity
35-
ident, err := testutil.RandIdentity()
36-
if err != nil {
37-
return nil, err
38-
}
39-
p := ident.ID()
40-
41-
c := config.Config{
42-
Identity: config.Identity{
43-
PeerID: p.String(),
44-
},
45-
}
46-
47-
nd, err := core.Offline(&repo.Mock{
48-
C: c,
49-
D: ds2.CloserWrap(syncds.MutexWrap(datastore.NewMapDatastore())),
50-
})(ctx)
51-
if err != nil {
52-
return nil, err
53-
}
54-
55-
nd.PrivateKey = ident.PrivateKey()
56-
nd.Peerstore = peer.NewPeerstore()
57-
nd.Peerstore.AddPrivKey(p, ident.PrivateKey())
58-
nd.Peerstore.AddPubKey(p, ident.PublicKey())
59-
nd.Identity = p
26+
// effectively offline, only peer in its network
27+
return core.NewNode(ctx, &core.BuildCfg{
28+
Online: true,
29+
Host: MockHostOption(mocknet.New(ctx)),
30+
})
31+
}
6032

61-
nd.PeerHost, err = mocknet.New(nd.Context()).AddPeer(ident.PrivateKey(), ident.Address()) // effectively offline
62-
if err != nil {
63-
return nil, err
33+
func MockHostOption(mn mocknet.Mocknet) core.HostOption {
34+
return func(ctx context.Context, id peer.ID, ps peer.Peerstore, bwr metrics.Reporter, fs []*net.IPNet) (host.Host, error) {
35+
return mn.AddPeerWithPeerstore(id, ps)
6436
}
65-
66-
// Routing
67-
nd.Routing = offrt.NewOfflineRouter(nd.Repo.Datastore(), nd.PrivateKey)
68-
69-
// Bitswap
70-
bstore := blockstore.NewBlockstore(nd.Repo.Datastore())
71-
bserv := blockservice.New(bstore, offline.Exchange(bstore))
72-
73-
nd.DAG = mdag.NewDAGService(bserv)
74-
75-
nd.Pinning = pin.NewPinner(nd.Repo.Datastore(), nd.DAG)
76-
77-
// Namespace resolver
78-
nd.Namesys = nsys.NewNameSystem(nd.Routing)
79-
80-
// Path resolver
81-
nd.Resolver = &path.Resolver{DAG: nd.DAG}
82-
83-
return nd, nil
8437
}
8538

8639
func MockCmdsCtx() (commands.Context, error) {
@@ -97,10 +50,14 @@ func MockCmdsCtx() (commands.Context, error) {
9750
},
9851
}
9952

100-
node, err := core.NewIPFSNode(context.Background(), core.Offline(&repo.Mock{
53+
r := &repo.Mock{
10154
D: ds2.CloserWrap(syncds.MutexWrap(datastore.NewMapDatastore())),
10255
C: conf,
103-
}))
56+
}
57+
58+
node, err := core.NewNode(context.Background(), &core.BuildCfg{
59+
Repo: r,
60+
})
10461

10562
return commands.Context{
10663
Online: true,

‎p2p/net/mock/interface.go

+1
Original file line numberDiff line numberDiff line change
@@ -25,6 +25,7 @@ type Mocknet interface {
2525
// AddPeer adds an existing peer. we need both a privkey and addr.
2626
// ID is derived from PrivKey
2727
AddPeer(ic.PrivKey, ma.Multiaddr) (host.Host, error)
28+
AddPeerWithPeerstore(peer.ID, peer.Peerstore) (host.Host, error)
2829

2930
// retrieve things (with randomized iteration order)
3031
Peers() []peer.ID

‎p2p/net/mock/mock_net.go

+15-2
Original file line numberDiff line numberDiff line change
@@ -64,13 +64,26 @@ func (mn *mocknet) GenPeer() (host.Host, error) {
6464
}
6565

6666
func (mn *mocknet) AddPeer(k ic.PrivKey, a ma.Multiaddr) (host.Host, error) {
67-
n, err := newPeernet(mn.ctx, mn, k, a)
67+
p, err := peer.IDFromPublicKey(k.GetPublic())
68+
if err != nil {
69+
return nil, err
70+
}
71+
72+
ps := peer.NewPeerstore()
73+
ps.AddAddr(p, a, peer.PermanentAddrTTL)
74+
ps.AddPrivKey(p, k)
75+
ps.AddPubKey(p, k.GetPublic())
76+
77+
return mn.AddPeerWithPeerstore(p, ps)
78+
}
79+
80+
func (mn *mocknet) AddPeerWithPeerstore(p peer.ID, ps peer.Peerstore) (host.Host, error) {
81+
n, err := newPeernet(mn.ctx, mn, p, ps)
6882
if err != nil {
6983
return nil, err
7084
}
7185

7286
h := bhost.New(n)
73-
log.Debugf("mocknet added listen addr for peer: %s -- %s", n.LocalPeer(), a)
7487

7588
mn.proc.AddChild(n.proc)
7689

‎p2p/net/mock/mock_peernet.go

+1-14
Original file line numberDiff line numberDiff line change
@@ -5,7 +5,6 @@ import (
55
"math/rand"
66
"sync"
77

8-
ic "github.com/ipfs/go-ipfs/p2p/crypto"
98
inet "github.com/ipfs/go-ipfs/p2p/net"
109
peer "github.com/ipfs/go-ipfs/p2p/peer"
1110

@@ -40,19 +39,7 @@ type peernet struct {
4039
}
4140

4241
// newPeernet constructs a new peernet
43-
func newPeernet(ctx context.Context, m *mocknet, k ic.PrivKey,
44-
a ma.Multiaddr) (*peernet, error) {
45-
46-
p, err := peer.IDFromPublicKey(k.GetPublic())
47-
if err != nil {
48-
return nil, err
49-
}
50-
51-
// create our own entirely, so that peers knowledge doesn't get shared
52-
ps := peer.NewPeerstore()
53-
ps.AddAddr(p, a, peer.PermanentAddrTTL)
54-
ps.AddPrivKey(p, k)
55-
ps.AddPubKey(p, k.GetPublic())
42+
func newPeernet(ctx context.Context, m *mocknet, p peer.ID, ps peer.Peerstore) (*peernet, error) {
5643

5744
n := &peernet{
5845
mocknet: m,

‎test/integration/addcat_test.go

+19-12
Original file line numberDiff line numberDiff line change
@@ -15,12 +15,16 @@ import (
1515

1616
"github.com/ipfs/go-ipfs/core"
1717
coreunix "github.com/ipfs/go-ipfs/core/coreunix"
18+
mock "github.com/ipfs/go-ipfs/core/mock"
1819
mocknet "github.com/ipfs/go-ipfs/p2p/net/mock"
1920
"github.com/ipfs/go-ipfs/p2p/peer"
21+
eventlog "github.com/ipfs/go-ipfs/thirdparty/eventlog"
2022
"github.com/ipfs/go-ipfs/thirdparty/unit"
2123
testutil "github.com/ipfs/go-ipfs/util/testutil"
2224
)
2325

26+
var log = eventlog.Logger("epictest")
27+
2428
const kSeed = 1
2529

2630
func Test1KBInstantaneous(t *testing.T) {
@@ -87,35 +91,38 @@ func RandomBytes(n int64) []byte {
8791
func DirectAddCat(data []byte, conf testutil.LatencyConfig) error {
8892
ctx, cancel := context.WithCancel(context.Background())
8993
defer cancel()
90-
const numPeers = 2
9194

9295
// create network
93-
mn, err := mocknet.FullMeshLinked(ctx, numPeers)
94-
if err != nil {
95-
return err
96-
}
96+
mn := mocknet.New(ctx)
9797
mn.SetLinkDefaults(mocknet.LinkOptions{
9898
Latency: conf.NetworkLatency,
9999
// TODO add to conf. This is tricky because we want 0 values to be functional.
100100
Bandwidth: math.MaxInt32,
101101
})
102102

103-
peers := mn.Peers()
104-
if len(peers) < numPeers {
105-
return errors.New("test initialization error")
106-
}
107-
108-
adder, err := core.NewIPFSNode(ctx, core.ConfigOption(MocknetTestRepo(peers[0], mn.Host(peers[0]), conf, core.DHTOption)))
103+
adder, err := core.NewNode(ctx, &core.BuildCfg{
104+
Online: true,
105+
Host: mock.MockHostOption(mn),
106+
})
109107
if err != nil {
110108
return err
111109
}
112110
defer adder.Close()
113-
catter, err := core.NewIPFSNode(ctx, core.ConfigOption(MocknetTestRepo(peers[1], mn.Host(peers[1]), conf, core.DHTOption)))
111+
112+
catter, err := core.NewNode(ctx, &core.BuildCfg{
113+
Online: true,
114+
Host: mock.MockHostOption(mn),
115+
})
114116
if err != nil {
115117
return err
116118
}
117119
defer catter.Close()
118120

121+
err = mn.LinkAll()
122+
if err != nil {
123+
return err
124+
}
125+
119126
bs1 := []peer.PeerInfo{adder.Peerstore.PeerInfo(adder.Identity)}
120127
bs2 := []peer.PeerInfo{catter.Peerstore.PeerInfo(catter.Identity)}
121128

‎test/integration/bench_cat_test.go

+16-12
Original file line numberDiff line numberDiff line change
@@ -10,6 +10,7 @@ import (
1010
context "github.com/ipfs/go-ipfs/Godeps/_workspace/src/golang.org/x/net/context"
1111
"github.com/ipfs/go-ipfs/core"
1212
coreunix "github.com/ipfs/go-ipfs/core/coreunix"
13+
mock "github.com/ipfs/go-ipfs/core/mock"
1314
mocknet "github.com/ipfs/go-ipfs/p2p/net/mock"
1415
"github.com/ipfs/go-ipfs/p2p/peer"
1516
"github.com/ipfs/go-ipfs/thirdparty/unit"
@@ -35,35 +36,38 @@ func benchCat(b *testing.B, data []byte, conf testutil.LatencyConfig) error {
3536
b.StopTimer()
3637
ctx, cancel := context.WithCancel(context.Background())
3738
defer cancel()
38-
const numPeers = 2
3939

4040
// create network
41-
mn, err := mocknet.FullMeshLinked(ctx, numPeers)
42-
if err != nil {
43-
return err
44-
}
41+
mn := mocknet.New(ctx)
4542
mn.SetLinkDefaults(mocknet.LinkOptions{
4643
Latency: conf.NetworkLatency,
4744
// TODO add to conf. This is tricky because we want 0 values to be functional.
4845
Bandwidth: math.MaxInt32,
4946
})
5047

51-
peers := mn.Peers()
52-
if len(peers) < numPeers {
53-
return errors.New("test initialization error")
54-
}
55-
56-
adder, err := core.NewIPFSNode(ctx, core.ConfigOption(MocknetTestRepo(peers[0], mn.Host(peers[0]), conf, core.DHTOption)))
48+
adder, err := core.NewNode(ctx, &core.BuildCfg{
49+
Online: true,
50+
Host: mock.MockHostOption(mn),
51+
})
5752
if err != nil {
5853
return err
5954
}
6055
defer adder.Close()
61-
catter, err := core.NewIPFSNode(ctx, core.ConfigOption(MocknetTestRepo(peers[1], mn.Host(peers[1]), conf, core.DHTOption)))
56+
57+
catter, err := core.NewNode(ctx, &core.BuildCfg{
58+
Online: true,
59+
Host: mock.MockHostOption(mn),
60+
})
6261
if err != nil {
6362
return err
6463
}
6564
defer catter.Close()
6665

66+
err = mn.LinkAll()
67+
if err != nil {
68+
return err
69+
}
70+
6771
bs1 := []peer.PeerInfo{adder.Peerstore.PeerInfo(adder.Identity)}
6872
bs2 := []peer.PeerInfo{catter.Peerstore.PeerInfo(catter.Identity)}
6973

‎test/integration/bitswap_wo_routing_test.go

+10-17
Original file line numberDiff line numberDiff line change
@@ -2,15 +2,13 @@ package integrationtest
22

33
import (
44
"bytes"
5-
"errors"
65
"testing"
7-
"time"
86

97
context "github.com/ipfs/go-ipfs/Godeps/_workspace/src/golang.org/x/net/context"
108
"github.com/ipfs/go-ipfs/blocks"
119
"github.com/ipfs/go-ipfs/core"
10+
"github.com/ipfs/go-ipfs/core/mock"
1211
mocknet "github.com/ipfs/go-ipfs/p2p/net/mock"
13-
testutil "github.com/ipfs/go-ipfs/util/testutil"
1412
)
1513

1614
func TestBitswapWithoutRouting(t *testing.T) {
@@ -19,29 +17,24 @@ func TestBitswapWithoutRouting(t *testing.T) {
1917
const numPeers = 4
2018

2119
// create network
22-
mn, err := mocknet.FullMeshLinked(ctx, numPeers)
23-
if err != nil {
24-
t.Fatal(err)
25-
}
26-
27-
peers := mn.Peers()
28-
if len(peers) < numPeers {
29-
t.Fatal(errors.New("test initialization error"))
30-
}
31-
32-
// set the routing latency to infinity.
33-
conf := testutil.LatencyConfig{RoutingLatency: (525600 * time.Minute)}
20+
mn := mocknet.New(ctx)
3421

3522
var nodes []*core.IpfsNode
36-
for _, p := range peers {
37-
n, err := core.NewIPFSNode(ctx, core.ConfigOption(MocknetTestRepo(p, mn.Host(p), conf, core.NilRouterOption)))
23+
for i := 0; i < numPeers; i++ {
24+
n, err := core.NewNode(ctx, &core.BuildCfg{
25+
Online: true,
26+
Host: coremock.MockHostOption(mn),
27+
Routing: core.NilRouterOption, // no routing
28+
})
3829
if err != nil {
3930
t.Fatal(err)
4031
}
4132
defer n.Close()
4233
nodes = append(nodes, n)
4334
}
4435

36+
mn.LinkAll()
37+
4538
// connect them
4639
for _, n1 := range nodes {
4740
for _, n2 := range nodes {

‎test/integration/core.go

-54
This file was deleted.

‎test/integration/grandcentral_test.go

+15-19
Original file line numberDiff line numberDiff line change
@@ -16,9 +16,9 @@ import (
1616
core "github.com/ipfs/go-ipfs/core"
1717
"github.com/ipfs/go-ipfs/core/corerouting"
1818
"github.com/ipfs/go-ipfs/core/coreunix"
19+
mock "github.com/ipfs/go-ipfs/core/mock"
1920
mocknet "github.com/ipfs/go-ipfs/p2p/net/mock"
2021
"github.com/ipfs/go-ipfs/p2p/peer"
21-
"github.com/ipfs/go-ipfs/thirdparty/iter"
2222
"github.com/ipfs/go-ipfs/thirdparty/unit"
2323
ds2 "github.com/ipfs/go-ipfs/util/datastore2"
2424
testutil "github.com/ipfs/go-ipfs/util/testutil"
@@ -82,28 +82,21 @@ func InitializeSupernodeNetwork(
8282
conf testutil.LatencyConfig) ([]*core.IpfsNode, []*core.IpfsNode, error) {
8383

8484
// create network
85-
mn, err := mocknet.FullMeshLinked(ctx, numServers+numClients)
86-
if err != nil {
87-
return nil, nil, err
88-
}
85+
mn := mocknet.New(ctx)
8986

9087
mn.SetLinkDefaults(mocknet.LinkOptions{
9188
Latency: conf.NetworkLatency,
9289
Bandwidth: math.MaxInt32,
9390
})
9491

95-
peers := mn.Peers()
96-
if len(peers) < numServers+numClients {
97-
return nil, nil, errors.New("test initialization error")
98-
}
99-
clientPeers, serverPeers := peers[0:numClients], peers[numClients:]
100-
10192
routingDatastore := ds2.CloserWrap(syncds.MutexWrap(datastore.NewMapDatastore()))
10293
var servers []*core.IpfsNode
103-
for i := range iter.N(numServers) {
104-
p := serverPeers[i]
105-
bootstrap, err := core.NewIPFSNode(ctx, MocknetTestRepo(p, mn.Host(p), conf,
106-
corerouting.SupernodeServer(routingDatastore)))
94+
for i := 0; i < numServers; i++ {
95+
bootstrap, err := core.NewNode(ctx, &core.BuildCfg{
96+
Online: true,
97+
Host: mock.MockHostOption(mn),
98+
Routing: corerouting.SupernodeServer(routingDatastore),
99+
})
107100
if err != nil {
108101
return nil, nil, err
109102
}
@@ -117,15 +110,18 @@ func InitializeSupernodeNetwork(
117110
}
118111

119112
var clients []*core.IpfsNode
120-
for i := range iter.N(numClients) {
121-
p := clientPeers[i]
122-
n, err := core.NewIPFSNode(ctx, MocknetTestRepo(p, mn.Host(p), conf,
123-
corerouting.SupernodeClient(bootstrapInfos...)))
113+
for i := 0; i < numClients; i++ {
114+
n, err := core.NewNode(ctx, &core.BuildCfg{
115+
Online: true,
116+
Host: mock.MockHostOption(mn),
117+
Routing: corerouting.SupernodeClient(bootstrapInfos...),
118+
})
124119
if err != nil {
125120
return nil, nil, err
126121
}
127122
clients = append(clients, n)
128123
}
124+
mn.LinkAll()
129125

130126
bcfg := core.BootstrapConfigWithPeers(bootstrapInfos)
131127
for _, n := range clients {

‎test/integration/three_legged_cat_test.go

+17-11
Original file line numberDiff line numberDiff line change
@@ -12,6 +12,7 @@ import (
1212

1313
core "github.com/ipfs/go-ipfs/core"
1414
coreunix "github.com/ipfs/go-ipfs/core/coreunix"
15+
mock "github.com/ipfs/go-ipfs/core/mock"
1516
mocknet "github.com/ipfs/go-ipfs/p2p/net/mock"
1617
"github.com/ipfs/go-ipfs/p2p/peer"
1718
"github.com/ipfs/go-ipfs/thirdparty/unit"
@@ -67,35 +68,40 @@ func RunThreeLeggedCat(data []byte, conf testutil.LatencyConfig) error {
6768
const numPeers = 3
6869

6970
// create network
70-
mn, err := mocknet.FullMeshLinked(ctx, numPeers)
71-
if err != nil {
72-
return err
73-
}
71+
mn := mocknet.New(ctx)
7472
mn.SetLinkDefaults(mocknet.LinkOptions{
7573
Latency: conf.NetworkLatency,
7674
// TODO add to conf. This is tricky because we want 0 values to be functional.
7775
Bandwidth: math.MaxInt32,
7876
})
7977

80-
peers := mn.Peers()
81-
if len(peers) < numPeers {
82-
return errors.New("test initialization error")
83-
}
84-
bootstrap, err := core.NewIPFSNode(ctx, MocknetTestRepo(peers[2], mn.Host(peers[2]), conf, core.DHTOption))
78+
bootstrap, err := core.NewNode(ctx, &core.BuildCfg{
79+
Online: true,
80+
Host: mock.MockHostOption(mn),
81+
})
8582
if err != nil {
8683
return err
8784
}
8885
defer bootstrap.Close()
89-
adder, err := core.NewIPFSNode(ctx, MocknetTestRepo(peers[0], mn.Host(peers[0]), conf, core.DHTOption))
86+
87+
adder, err := core.NewNode(ctx, &core.BuildCfg{
88+
Online: true,
89+
Host: mock.MockHostOption(mn),
90+
})
9091
if err != nil {
9192
return err
9293
}
9394
defer adder.Close()
94-
catter, err := core.NewIPFSNode(ctx, MocknetTestRepo(peers[1], mn.Host(peers[1]), conf, core.DHTOption))
95+
96+
catter, err := core.NewNode(ctx, &core.BuildCfg{
97+
Online: true,
98+
Host: mock.MockHostOption(mn),
99+
})
95100
if err != nil {
96101
return err
97102
}
98103
defer catter.Close()
104+
mn.LinkAll()
99105

100106
bis := bootstrap.Peerstore.PeerInfo(bootstrap.PeerHost.ID())
101107
bcfg := core.BootstrapConfigWithPeers([]peer.PeerInfo{bis})

‎test/supernode_client/main.go

+10-10
Original file line numberDiff line numberDiff line change
@@ -93,14 +93,11 @@ func run() error {
9393
})
9494
}
9595

96-
node, err := core.NewIPFSNode(
97-
ctx,
98-
core.OnlineWithOptions(
99-
repo,
100-
corerouting.SupernodeClient(infos...),
101-
core.DefaultHostOption,
102-
),
103-
)
96+
node, err := core.NewNode(ctx, &core.BuildCfg{
97+
Online: true,
98+
Repo: repo,
99+
Routing: corerouting.SupernodeClient(infos...),
100+
})
104101
if err != nil {
105102
return err
106103
}
@@ -168,10 +165,13 @@ func runFileCattingWorker(ctx context.Context, n *core.IpfsNode) error {
168165
return err
169166
}
170167

171-
dummy, err := core.NewIPFSNode(ctx, core.Offline(&repo.Mock{
168+
r := &repo.Mock{
172169
D: ds2.CloserWrap(syncds.MutexWrap(datastore.NewMapDatastore())),
173170
C: *conf,
174-
}))
171+
}
172+
dummy, err := core.NewNode(ctx, &core.BuildCfg{
173+
Repo: r,
174+
})
175175
if err != nil {
176176
return err
177177
}

0 commit comments

Comments
 (0)
Please sign in to comment.