@cryptotaxi247 / kubo / commits / e8f79c880

Use variadic options

License: MIT Signed-off-by: Dirk McCormick <dirkmdev@gmail.com>

Dirk McCormick committed Feb 28, 2018 at 16:57 UTC e8f79c88036362d99d2b06e3fa7fae974090cd6f
23 files changed +172 -131
core/commands/dns.go
+5 -3
@@ -7,6 +7,7 @@ import (
7 cmds "github.com/ipfs/go-ipfs/commands"
8 e "github.com/ipfs/go-ipfs/core/commands/e"
9 namesys "github.com/ipfs/go-ipfs/namesys"
10 + nsopts "github.com/ipfs/go-ipfs/namesys/opts"
11
12 "gx/ipfs/QmceUdzxkimdYsgtX733uNgzf1DLHyBKN6ehGSp85ayppM/go-ipfs-cmdkit"
13 )
@@ -57,11 +58,12 @@ The resolver can recursively resolve:
58 name := req.Arguments()[0]
59 resolver := namesys.NewDNSResolver()
60
60 - opts := namesys.DefaultResolveOpts()
61 + ropts := []nsopts.ResolveOpt{}
62 if !recursive {
62 - opts.Depth = 1
63 + ropts = append(ropts, nsopts.Depth(1))
64 }
64 - output, err := resolver.Resolve(req.Context(), name, opts)
65 +
66 + output, err := resolver.Resolve(req.Context(), name, ropts...)
67 if err == namesys.ErrResolveFailed {
68 res.SetError(err, cmdkit.ErrNotFound)
69 return
core/commands/ipns.go
+6 -5
@@ -9,6 +9,7 @@ import (
9 cmds "github.com/ipfs/go-ipfs/commands"
10 e "github.com/ipfs/go-ipfs/core/commands/e"
11 namesys "github.com/ipfs/go-ipfs/namesys"
12 + nsopts "github.com/ipfs/go-ipfs/namesys/opts"
13
14 offline "gx/ipfs/QmZRcGYvxdauCd7hHnMYLYqcZRaDjv24c7eUNyJojAcdBb/go-ipfs-routing/offline"
15 "gx/ipfs/QmceUdzxkimdYsgtX733uNgzf1DLHyBKN6ehGSp85ayppM/go-ipfs-cmdkit"
@@ -111,22 +112,22 @@ Resolve the value of a dnslink:
112 recursive, _, _ := req.Option("recursive").Bool()
113 rc, rcok, _ := req.Option("dht-record-count").Int()
114 dhtt, dhttok, _ := req.Option("dht-timeout").Int()
114 - opts := namesys.DefaultResolveOpts()
115 + ropts := []nsopts.ResolveOpt{}
116 if !recursive {
116 - opts.Depth = 1
117 + ropts = append(ropts, nsopts.Depth(1))
118 }
119 if rcok {
119 - opts.DhtRecordCount = uint(rc)
120 + ropts = append(ropts, nsopts.DhtRecordCount(uint(rc)))
121 }
122 if dhttok {
122 - opts.DhtTimeout = time.Duration(dhtt) * time.Second
123 + ropts = append(ropts, nsopts.DhtTimeout(time.Duration(dhtt)*time.Second))
124 }
125
126 if !strings.HasPrefix(name, "/ipns/") {
127 name = "/ipns/" + name
128 }
129
129 - output, err := resolver.Resolve(req.Context(), name, opts)
130 + output, err := resolver.Resolve(req.Context(), name, ropts...)
131 if err != nil {
132 res.SetError(err, cmdkit.ErrNormal)
133 return
core/commands/resolve.go
+5 -5
@@ -9,6 +9,7 @@ import (
9 "github.com/ipfs/go-ipfs/core"
10 e "github.com/ipfs/go-ipfs/core/commands/e"
11 ns "github.com/ipfs/go-ipfs/namesys"
12 + nsopts "github.com/ipfs/go-ipfs/namesys/opts"
13 path "github.com/ipfs/go-ipfs/path"
14
15 "gx/ipfs/QmceUdzxkimdYsgtX733uNgzf1DLHyBKN6ehGSp85ayppM/go-ipfs-cmdkit"
@@ -89,15 +90,14 @@ Resolve the value of an IPFS DAG path:
90 if strings.HasPrefix(name, "/ipns/") && !recursive {
91 rc, rcok, _ := req.Option("dht-record-count").Int()
92 dhtt, dhttok, _ := req.Option("dht-timeout").Int()
92 - opts := ns.DefaultResolveOpts()
93 - opts.Depth = 1
93 + ropts := []nsopts.ResolveOpt{nsopts.Depth(1)}
94 if rcok {
95 - opts.DhtRecordCount = uint(rc)
95 + ropts = append(ropts, nsopts.DhtRecordCount(uint(rc)))
96 }
97 if dhttok {
98 - opts.DhtTimeout = time.Duration(dhtt) * time.Second
98 + ropts = append(ropts, nsopts.DhtTimeout(time.Duration(dhtt)*time.Second))
99 }
100 - p, err := n.Namesys.Resolve(req.Context(), name, opts)
100 + p, err := n.Namesys.Resolve(req.Context(), name, ropts...)
101 // ErrResolveRecursion is fine
102 if err != nil && err != ns.ErrResolveRecursion {
103 res.SetError(err, cmdkit.ErrNormal)
core/coreapi/name.go
+7 -6
@@ -12,6 +12,7 @@ import (
12 caopts "github.com/ipfs/go-ipfs/core/coreapi/interface/options"
13 keystore "github.com/ipfs/go-ipfs/keystore"
14 namesys "github.com/ipfs/go-ipfs/namesys"
15 + nsopts "github.com/ipfs/go-ipfs/namesys/opts"
16 ipath "github.com/ipfs/go-ipfs/path"
17
18 offline "gx/ipfs/QmZRcGYvxdauCd7hHnMYLYqcZRaDjv24c7eUNyJojAcdBb/go-ipfs-routing/offline"
@@ -117,16 +118,16 @@ func (api *NameAPI) Resolve(ctx context.Context, name string, opts ...caopts.Nam
118 resolver = namesys.NewNameSystem(n.Routing, n.Repo.Datastore(), 0)
119 }
120
120 - ropts := namesys.DefaultResolveOpts()
121 - if !options.Recursive {
122 - ropts.Depth = 1
123 - }
124 -
121 if !strings.HasPrefix(name, "/ipns/") {
122 name = "/ipns/" + name
123 }
124
129 - output, err := resolver.Resolve(ctx, name, ropts)
125 + ropts := []nsopts.ResolveOpt{}
126 + if !options.Recursive {
127 + ropts = append(ropts, nsopts.Depth(1))
128 + }
129 +
130 + output, err := resolver.Resolve(ctx, name, ropts...)
131 if err != nil {
132 return nil, err
133 }
core/corehttp/gateway_test.go
+2 -1
@@ -14,6 +14,7 @@ import (
14 coreunix "github.com/ipfs/go-ipfs/core/coreunix"
15 dag "github.com/ipfs/go-ipfs/merkledag"
16 namesys "github.com/ipfs/go-ipfs/namesys"
17 + nsopts "github.com/ipfs/go-ipfs/namesys/opts"
18 path "github.com/ipfs/go-ipfs/path"
19 repo "github.com/ipfs/go-ipfs/repo"
20 config "github.com/ipfs/go-ipfs/repo/config"
@@ -28,7 +29,7 @@ var emptyDir = "/ipfs/QmUNLLsPACCz1vLxQVkXqqLX5R1X345qqfHbsf67hvA3Nn"
29
30 type mockNamesys map[string]path.Path
31
31 -func (m mockNamesys) Resolve(ctx context.Context, name string, opts *namesys.ResolveOpts) (value path.Path, err error) {
32 +func (m mockNamesys) Resolve(ctx context.Context, name string, opts ...nsopts.ResolveOpt) (value path.Path, err error) {
33 p, ok := m[name]
34 if !ok {
35 return "", namesys.ErrResolveFailed
core/corehttp/ipns_hostname.go
+1 -2
@@ -7,7 +7,6 @@ import (
7 "strings"
8
9 "github.com/ipfs/go-ipfs/core"
10 - namesys "github.com/ipfs/go-ipfs/namesys"
10
11 isd "gx/ipfs/QmZmmuAXgX73UQmX1jRKjTGmjzq24Jinqkq8vzkBtno4uX/go-is-domain"
12 )
@@ -25,7 +24,7 @@ func IPNSHostnameOption() ServeOption {
24 host := strings.SplitN(r.Host, ":", 2)[0]
25 if len(host) > 0 && isd.IsDomain(host) {
26 name := "/ipns/" + host
28 - if _, err := n.Namesys.Resolve(ctx, name, namesys.DefaultResolveOpts()); err == nil {
27 + if _, err := n.Namesys.Resolve(ctx, name); err == nil {
28 r.Header["X-Ipns-Original-Path"] = []string{r.URL.Path}
29 r.URL.Path = name + r.URL.Path
30 }
core/pathresolver.go
+1 -1
@@ -48,7 +48,7 @@ func Resolve(ctx context.Context, nsys namesys.NameSystem, r *resolver.Resolver,
48 return nil, err
49 }
50
51 - respath, err := nsys.Resolve(ctx, resolvable.String(), namesys.DefaultResolveOpts())
51 + respath, err := nsys.Resolve(ctx, resolvable.String())
52 if err != nil {
53 evt.Append(logging.LoggableMap{"error": err.Error()})
54 return nil, err
fuse/ipns/ipns_unix.go
+1 -1
@@ -203,7 +203,7 @@ func (s *Root) Lookup(ctx context.Context, name string) (fs.Node, error) {
203 }
204
205 // other links go through ipns resolution and are symlinked into the ipfs mountpoint
206 - resolved, err := s.Ipfs.Namesys.Resolve(s.Ipfs.Context(), name, namesys.DefaultResolveOpts())
206 + resolved, err := s.Ipfs.Namesys.Resolve(s.Ipfs.Context(), name)
207 if err != nil {
208 log.Warningf("ipns: namesys resolve error: %s", err)
209 return nil, fuse.ENOENT
namesys/base.go
+5 -4
@@ -5,19 +5,20 @@ import (
5
6 context "context"
7
8 + opts "github.com/ipfs/go-ipfs/namesys/opts"
9 path "github.com/ipfs/go-ipfs/path"
10 )
11
12 type resolver interface {
13 // resolveOnce looks up a name once (without recursion).
13 - resolveOnce(ctx context.Context, name string, opts *ResolveOpts) (value path.Path, err error)
14 + resolveOnce(ctx context.Context, name string, options *opts.ResolveOpts) (value path.Path, err error)
15 }
16
17 // resolve is a helper for implementing Resolver.ResolveN using resolveOnce.
17 -func resolve(ctx context.Context, r resolver, name string, opts *ResolveOpts, prefixes ...string) (path.Path, error) {
18 - depth := opts.Depth
18 +func resolve(ctx context.Context, r resolver, name string, options *opts.ResolveOpts, prefixes ...string) (path.Path, error) {
19 + depth := options.Depth
20 for {
20 - p, err := r.resolveOnce(ctx, name, opts)
21 + p, err := r.resolveOnce(ctx, name, options)
22 if err != nil {
23 return "", err
24 }
namesys/dns.go
+4 -3
@@ -6,6 +6,7 @@ import (
6 "net"
7 "strings"
8
9 + opts "github.com/ipfs/go-ipfs/namesys/opts"
10 path "github.com/ipfs/go-ipfs/path"
11 isd "gx/ipfs/QmZmmuAXgX73UQmX1jRKjTGmjzq24Jinqkq8vzkBtno4uX/go-is-domain"
12 )
@@ -31,8 +32,8 @@ func newDNSResolver() resolver {
32 }
33
34 // Resolve implements Resolver.
34 -func (r *DNSResolver) Resolve(ctx context.Context, name string, opts *ResolveOpts) (path.Path, error) {
35 - return resolve(ctx, r, name, opts, "/ipns/")
35 +func (r *DNSResolver) Resolve(ctx context.Context, name string, options ...opts.ResolveOpt) (path.Path, error) {
36 + return resolve(ctx, r, name, opts.ProcessOpts(options), "/ipns/")
37 }
38
39 type lookupRes struct {
@@ -43,7 +44,7 @@ type lookupRes struct {
44 // resolveOnce implements resolver.
45 // TXT records for a given domain name should contain a b58
46 // encoded multihash.
46 -func (r *DNSResolver) resolveOnce(ctx context.Context, name string, opts *ResolveOpts) (path.Path, error) {
47 +func (r *DNSResolver) resolveOnce(ctx context.Context, name string, options *opts.ResolveOpts) (path.Path, error) {
48 segments := strings.SplitN(name, "/", 2)
49 domain := segments[0]
50
namesys/dns_test.go
+20 -18
@@ -3,6 +3,8 @@ package namesys
3 import (
4 "fmt"
5 "testing"
6 +
7 + opts "github.com/ipfs/go-ipfs/namesys/opts"
8 )
9
10 type mockDNS struct {
@@ -128,33 +130,33 @@ func newMockDNS() *mockDNS {
130 func TestDNSResolution(t *testing.T) {
131 mock := newMockDNS()
132 r := &DNSResolver{lookupTXT: mock.lookupTXT}
131 - testResolution(t, r, "multihash.example.com", DefaultDepthLimit, "/ipfs/QmY3hE8xgFCjGcz6PHgnvJz5HZi1BaKRfPkn1ghZUcYMjD", nil)
132 - testResolution(t, r, "ipfs.example.com", DefaultDepthLimit, "/ipfs/QmY3hE8xgFCjGcz6PHgnvJz5HZi1BaKRfPkn1ghZUcYMjD", nil)
133 - testResolution(t, r, "dipfs.example.com", DefaultDepthLimit, "/ipfs/QmY3hE8xgFCjGcz6PHgnvJz5HZi1BaKRfPkn1ghZUcYMjD", nil)
134 - testResolution(t, r, "dns1.example.com", DefaultDepthLimit, "/ipfs/QmY3hE8xgFCjGcz6PHgnvJz5HZi1BaKRfPkn1ghZUcYMjD", nil)
133 + testResolution(t, r, "multihash.example.com", opts.DefaultDepthLimit, "/ipfs/QmY3hE8xgFCjGcz6PHgnvJz5HZi1BaKRfPkn1ghZUcYMjD", nil)
134 + testResolution(t, r, "ipfs.example.com", opts.DefaultDepthLimit, "/ipfs/QmY3hE8xgFCjGcz6PHgnvJz5HZi1BaKRfPkn1ghZUcYMjD", nil)
135 + testResolution(t, r, "dipfs.example.com", opts.DefaultDepthLimit, "/ipfs/QmY3hE8xgFCjGcz6PHgnvJz5HZi1BaKRfPkn1ghZUcYMjD", nil)
136 + testResolution(t, r, "dns1.example.com", opts.DefaultDepthLimit, "/ipfs/QmY3hE8xgFCjGcz6PHgnvJz5HZi1BaKRfPkn1ghZUcYMjD", nil)
137 testResolution(t, r, "dns1.example.com", 1, "/ipns/ipfs.example.com", ErrResolveRecursion)
136 - testResolution(t, r, "dns2.example.com", DefaultDepthLimit, "/ipfs/QmY3hE8xgFCjGcz6PHgnvJz5HZi1BaKRfPkn1ghZUcYMjD", nil)
138 + testResolution(t, r, "dns2.example.com", opts.DefaultDepthLimit, "/ipfs/QmY3hE8xgFCjGcz6PHgnvJz5HZi1BaKRfPkn1ghZUcYMjD", nil)
139 testResolution(t, r, "dns2.example.com", 1, "/ipns/dns1.example.com", ErrResolveRecursion)
140 testResolution(t, r, "dns2.example.com", 2, "/ipns/ipfs.example.com", ErrResolveRecursion)
139 - testResolution(t, r, "multi.example.com", DefaultDepthLimit, "/ipfs/QmY3hE8xgFCjGcz6PHgnvJz5HZi1BaKRfPkn1ghZUcYMjD", nil)
141 + testResolution(t, r, "multi.example.com", opts.DefaultDepthLimit, "/ipfs/QmY3hE8xgFCjGcz6PHgnvJz5HZi1BaKRfPkn1ghZUcYMjD", nil)
142 testResolution(t, r, "multi.example.com", 1, "/ipns/dns1.example.com", ErrResolveRecursion)
143 testResolution(t, r, "multi.example.com", 2, "/ipns/ipfs.example.com", ErrResolveRecursion)
142 - testResolution(t, r, "equals.example.com", DefaultDepthLimit, "/ipfs/QmY3hE8xgFCjGcz6PHgnvJz5HZi1BaKRfPkn1ghZUcYMjD/=equals", nil)
144 + testResolution(t, r, "equals.example.com", opts.DefaultDepthLimit, "/ipfs/QmY3hE8xgFCjGcz6PHgnvJz5HZi1BaKRfPkn1ghZUcYMjD/=equals", nil)
145 testResolution(t, r, "loop1.example.com", 1, "/ipns/loop2.example.com", ErrResolveRecursion)
146 testResolution(t, r, "loop1.example.com", 2, "/ipns/loop1.example.com", ErrResolveRecursion)
147 testResolution(t, r, "loop1.example.com", 3, "/ipns/loop2.example.com", ErrResolveRecursion)
146 - testResolution(t, r, "loop1.example.com", DefaultDepthLimit, "/ipns/loop1.example.com", ErrResolveRecursion)
148 + testResolution(t, r, "loop1.example.com", opts.DefaultDepthLimit, "/ipns/loop1.example.com", ErrResolveRecursion)
149 testResolution(t, r, "dloop1.example.com", 1, "/ipns/loop2.example.com", ErrResolveRecursion)
150 testResolution(t, r, "dloop1.example.com", 2, "/ipns/loop1.example.com", ErrResolveRecursion)
151 testResolution(t, r, "dloop1.example.com", 3, "/ipns/loop2.example.com", ErrResolveRecursion)
150 - testResolution(t, r, "dloop1.example.com", DefaultDepthLimit, "/ipns/loop1.example.com", ErrResolveRecursion)
151 - testResolution(t, r, "bad.example.com", DefaultDepthLimit, "", ErrResolveFailed)
152 - testResolution(t, r, "withsegment.example.com", DefaultDepthLimit, "/ipfs/QmY3hE8xgFCjGcz6PHgnvJz5HZi1BaKRfPkn1ghZUcYMjD/sub/segment", nil)
153 - testResolution(t, r, "withrecsegment.example.com", DefaultDepthLimit, "/ipfs/QmY3hE8xgFCjGcz6PHgnvJz5HZi1BaKRfPkn1ghZUcYMjD/sub/segment/subsub", nil)
154 - testResolution(t, r, "withsegment.example.com/test1", DefaultDepthLimit, "/ipfs/QmY3hE8xgFCjGcz6PHgnvJz5HZi1BaKRfPkn1ghZUcYMjD/sub/segment/test1", nil)
155 - testResolution(t, r, "withrecsegment.example.com/test2", DefaultDepthLimit, "/ipfs/QmY3hE8xgFCjGcz6PHgnvJz5HZi1BaKRfPkn1ghZUcYMjD/sub/segment/subsub/test2", nil)
156 - testResolution(t, r, "withrecsegment.example.com/test3/", DefaultDepthLimit, "/ipfs/QmY3hE8xgFCjGcz6PHgnvJz5HZi1BaKRfPkn1ghZUcYMjD/sub/segment/subsub/test3/", nil)
157 - testResolution(t, r, "withtrailingrec.example.com", DefaultDepthLimit, "/ipfs/QmY3hE8xgFCjGcz6PHgnvJz5HZi1BaKRfPkn1ghZUcYMjD/sub/segment/", nil)
158 - testResolution(t, r, "double.example.com", DefaultDepthLimit, "/ipfs/QmY3hE8xgFCjGcz6PHgnvJz5HZi1BaKRfPkn1ghZUcYMjD", nil)
159 - testResolution(t, r, "conflict.example.com", DefaultDepthLimit, "/ipfs/QmY3hE8xgFCjGcz6PHgnvJz5HZi1BaKRfPkn1ghZUcYMjE", nil)
152 + testResolution(t, r, "dloop1.example.com", opts.DefaultDepthLimit, "/ipns/loop1.example.com", ErrResolveRecursion)
153 + testResolution(t, r, "bad.example.com", opts.DefaultDepthLimit, "", ErrResolveFailed)
154 + testResolution(t, r, "withsegment.example.com", opts.DefaultDepthLimit, "/ipfs/QmY3hE8xgFCjGcz6PHgnvJz5HZi1BaKRfPkn1ghZUcYMjD/sub/segment", nil)
155 + testResolution(t, r, "withrecsegment.example.com", opts.DefaultDepthLimit, "/ipfs/QmY3hE8xgFCjGcz6PHgnvJz5HZi1BaKRfPkn1ghZUcYMjD/sub/segment/subsub", nil)
156 + testResolution(t, r, "withsegment.example.com/test1", opts.DefaultDepthLimit, "/ipfs/QmY3hE8xgFCjGcz6PHgnvJz5HZi1BaKRfPkn1ghZUcYMjD/sub/segment/test1", nil)
157 + testResolution(t, r, "withrecsegment.example.com/test2", opts.DefaultDepthLimit, "/ipfs/QmY3hE8xgFCjGcz6PHgnvJz5HZi1BaKRfPkn1ghZUcYMjD/sub/segment/subsub/test2", nil)
158 + testResolution(t, r, "withrecsegment.example.com/test3/", opts.DefaultDepthLimit, "/ipfs/QmY3hE8xgFCjGcz6PHgnvJz5HZi1BaKRfPkn1ghZUcYMjD/sub/segment/subsub/test3/", nil)
159 + testResolution(t, r, "withtrailingrec.example.com", opts.DefaultDepthLimit, "/ipfs/QmY3hE8xgFCjGcz6PHgnvJz5HZi1BaKRfPkn1ghZUcYMjD/sub/segment/", nil)
160 + testResolution(t, r, "double.example.com", opts.DefaultDepthLimit, "/ipfs/QmY3hE8xgFCjGcz6PHgnvJz5HZi1BaKRfPkn1ghZUcYMjD", nil)
161 + testResolution(t, r, "conflict.example.com", opts.DefaultDepthLimit, "/ipfs/QmY3hE8xgFCjGcz6PHgnvJz5HZi1BaKRfPkn1ghZUcYMjE", nil)
162 }
namesys/interface.go
+2 -12
@@ -35,21 +35,11 @@ import (
35
36 context "context"
37
38 + opts "github.com/ipfs/go-ipfs/namesys/opts"
39 path "github.com/ipfs/go-ipfs/path"
40 ci "gx/ipfs/QmaPbCnUMBohSGo3KnxEa2bHqyJVVeEEcwtqJAYxerieBo/go-libp2p-crypto"
41 )
42
42 -const (
43 - // DefaultDepthLimit is the default depth limit used by Resolve.
44 - DefaultDepthLimit = 32
45 -
46 - // UnlimitedDepth allows infinite recursion in ResolveN. You
47 - // probably don't want to use this, but it's here if you absolutely
48 - // trust resolution to eventually complete and can't put an upper
49 - // limit on how many steps it will take.
50 - UnlimitedDepth = 0
51 -)
52 -
43 // ErrResolveFailed signals an error when attempting to resolve.
44 var ErrResolveFailed = errors.New("Could not resolve name.")
45
@@ -90,7 +80,7 @@ type Resolver interface {
80 // There is a default depth-limit to avoid infinite recursion. Most
81 // users will be fine with this default limit, but if you need to
82 // adjust the limit you can specify it as an option.
93 - Resolve(ctx context.Context, name string, opts *ResolveOpts) (value path.Path, err error)
83 + Resolve(ctx context.Context, name string, options ...opts.ResolveOpt) (value path.Path, err error)
84 }
85
86 // Publisher is an object capable of publishing particular names.
namesys/ipns_validate_test.go
+6 -5
@@ -6,6 +6,7 @@ import (
6 "testing"
7 "time"
8
9 + opts "github.com/ipfs/go-ipfs/namesys/opts"
10 path "github.com/ipfs/go-ipfs/path"
11
12 u "gx/ipfs/QmNiJuT8Ja3hMVpBHXv3Q6dwmperaQ6JjLtpMQgMCD7xvx/go-ipfs-util"
@@ -115,7 +116,7 @@ func TestResolverValidation(t *testing.T) {
116 }
117
118 // Resolve entry
118 - resp, err := resolver.resolveOnce(ctx, id.Pretty(), DefaultResolveOpts())
119 + resp, err := resolver.resolveOnce(ctx, id.Pretty(), opts.DefaultResolveOpts())
120 if err != nil {
121 t.Fatal(err)
122 }
@@ -136,7 +137,7 @@ func TestResolverValidation(t *testing.T) {
137 }
138
139 // Record should fail validation because entry is expired
139 - _, err = resolver.resolveOnce(ctx, id.Pretty(), DefaultResolveOpts())
140 + _, err = resolver.resolveOnce(ctx, id.Pretty(), opts.DefaultResolveOpts())
141 if err == nil {
142 t.Fatal("ValidateIpnsRecord should have returned error")
143 }
@@ -158,7 +159,7 @@ func TestResolverValidation(t *testing.T) {
159
160 // Record should fail validation because public key defined by
161 // ipns path doesn't match record signature
161 - _, err = resolver.resolveOnce(ctx, id2.Pretty(), DefaultResolveOpts())
162 + _, err = resolver.resolveOnce(ctx, id2.Pretty(), opts.DefaultResolveOpts())
163 if err == nil {
164 t.Fatal("ValidateIpnsRecord should have failed signature verification")
165 }
@@ -176,7 +177,7 @@ func TestResolverValidation(t *testing.T) {
177
178 // Record should fail validation because public key is not available
179 // in peer store or on network
179 - _, err = resolver.resolveOnce(ctx, id3.Pretty(), DefaultResolveOpts())
180 + _, err = resolver.resolveOnce(ctx, id3.Pretty(), opts.DefaultResolveOpts())
181 if err == nil {
182 t.Fatal("ValidateIpnsRecord should have failed because public key was not found")
183 }
@@ -191,7 +192,7 @@ func TestResolverValidation(t *testing.T) {
192 // public key is available in the peer store by looking it up in
193 // the DHT, which causes the DHT to fetch it and cache it in the
194 // peer store
194 - _, err = resolver.resolveOnce(ctx, id3.Pretty(), DefaultResolveOpts())
195 + _, err = resolver.resolveOnce(ctx, id3.Pretty(), opts.DefaultResolveOpts())
196 if err != nil {
197 t.Fatal(err)
198 }
namesys/namesys.go
+8 -7
@@ -7,6 +7,7 @@ import (
7 "sync"
8 "time"
9
10 + opts "github.com/ipfs/go-ipfs/namesys/opts"
11 path "github.com/ipfs/go-ipfs/path"
12
13 p2phost "gx/ipfs/QmNmJZL7FQySMtE2BQuLMuZg2EB2CLEunJJUSVSc9YnnbV/go-libp2p-host"
@@ -67,7 +68,7 @@ func AddPubsubNameSystem(ctx context.Context, ns NameSystem, host p2phost.Host,
68 const DefaultResolverCacheTTL = time.Minute
69
70 // Resolve implements Resolver.
70 -func (ns *mpns) Resolve(ctx context.Context, name string, opts *ResolveOpts) (path.Path, error) {
71 +func (ns *mpns) Resolve(ctx context.Context, name string, options ...opts.ResolveOpt) (path.Path, error) {
72 if strings.HasPrefix(name, "/ipfs/") {
73 return path.ParsePath(name)
74 }
@@ -76,11 +77,11 @@ func (ns *mpns) Resolve(ctx context.Context, name string, opts *ResolveOpts) (pa
77 return path.ParsePath("/ipfs/" + name)
78 }
79
79 - return resolve(ctx, ns, name, opts, "/ipns/")
80 + return resolve(ctx, ns, name, opts.ProcessOpts(options), "/ipns/")
81 }
82
83 // resolveOnce implements resolver.
83 -func (ns *mpns) resolveOnce(ctx context.Context, name string, opts *ResolveOpts) (path.Path, error) {
84 +func (ns *mpns) resolveOnce(ctx context.Context, name string, options *opts.ResolveOpts) (path.Path, error) {
85 if !strings.HasPrefix(name, "/ipns/") {
86 name = "/ipns/" + name
87 }
@@ -109,7 +110,7 @@ func (ns *mpns) resolveOnce(ctx context.Context, name string, opts *ResolveOpts)
110 if err == nil {
111 res, ok := ns.resolvers["pubsub"]
112 if ok {
112 - p, err := res.resolveOnce(ctx, key, opts)
113 + p, err := res.resolveOnce(ctx, key, options)
114 if err == nil {
115 return makePath(p)
116 }
@@ -117,7 +118,7 @@ func (ns *mpns) resolveOnce(ctx context.Context, name string, opts *ResolveOpts)
118
119 res, ok = ns.resolvers["dht"]
120 if ok {
120 - p, err := res.resolveOnce(ctx, key, opts)
121 + p, err := res.resolveOnce(ctx, key, options)
122 if err == nil {
123 return makePath(p)
124 }
@@ -129,7 +130,7 @@ func (ns *mpns) resolveOnce(ctx context.Context, name string, opts *ResolveOpts)
130 if isd.IsDomain(key) {
131 res, ok := ns.resolvers["dns"]
132 if ok {
132 - p, err := res.resolveOnce(ctx, key, opts)
133 + p, err := res.resolveOnce(ctx, key, options)
134 if err == nil {
135 return makePath(p)
136 }
@@ -140,7 +141,7 @@ func (ns *mpns) resolveOnce(ctx context.Context, name string, opts *ResolveOpts)
141
142 res, ok := ns.resolvers["proquint"]
143 if ok {
143 - p, err := res.resolveOnce(ctx, key, opts)
144 + p, err := res.resolveOnce(ctx, key, options)
145 if err == nil {
146 return makePath(p)
147 }
namesys/namesys_test.go
+8 -9
@@ -6,6 +6,7 @@ import (
6
7 context "context"
8
9 + opts "github.com/ipfs/go-ipfs/namesys/opts"
10 path "github.com/ipfs/go-ipfs/path"
11 "github.com/ipfs/go-ipfs/unixfs"
12
@@ -20,9 +21,7 @@ type mockResolver struct {
21 }
22
23 func testResolution(t *testing.T, resolver Resolver, name string, depth uint, expected string, expError error) {
23 - opts := DefaultResolveOpts()
24 - opts.Depth = depth
25 - p, err := resolver.Resolve(context.Background(), name, opts)
24 + p, err := resolver.Resolve(context.Background(), name, opts.Depth(depth))
25 if err != expError {
26 t.Fatal(fmt.Errorf(
27 "Expected %s with a depth of %d to have a '%s' error, but got '%s'",
@@ -35,7 +34,7 @@ func testResolution(t *testing.T, resolver Resolver, name string, depth uint, ex
34 }
35 }
36
38 -func (r *mockResolver) resolveOnce(ctx context.Context, name string, opts *ResolveOpts) (path.Path, error) {
37 +func (r *mockResolver) resolveOnce(ctx context.Context, name string, opts *opts.ResolveOpts) (path.Path, error) {
38 return path.ParsePath(r.entries[name])
39 }
40
@@ -65,14 +64,14 @@ func TestNamesysResolution(t *testing.T) {
64 },
65 }
66
68 - testResolution(t, r, "Qmcqtw8FfrVSBaRmbWwHxt3AuySBhJLcvmFYi3Lbc4xnwj", DefaultDepthLimit, "/ipfs/Qmcqtw8FfrVSBaRmbWwHxt3AuySBhJLcvmFYi3Lbc4xnwj", nil)
69 - testResolution(t, r, "/ipns/QmatmE9msSfkKxoffpHwNLNKgwZG8eT9Bud6YoPab52vpy", DefaultDepthLimit, "/ipfs/Qmcqtw8FfrVSBaRmbWwHxt3AuySBhJLcvmFYi3Lbc4xnwj", nil)
70 - testResolution(t, r, "/ipns/QmbCMUZw6JFeZ7Wp9jkzbye3Fzp2GGcPgC3nmeUjfVF87n", DefaultDepthLimit, "/ipfs/Qmcqtw8FfrVSBaRmbWwHxt3AuySBhJLcvmFYi3Lbc4xnwj", nil)
67 + testResolution(t, r, "Qmcqtw8FfrVSBaRmbWwHxt3AuySBhJLcvmFYi3Lbc4xnwj", opts.DefaultDepthLimit, "/ipfs/Qmcqtw8FfrVSBaRmbWwHxt3AuySBhJLcvmFYi3Lbc4xnwj", nil)
68 + testResolution(t, r, "/ipns/QmatmE9msSfkKxoffpHwNLNKgwZG8eT9Bud6YoPab52vpy", opts.DefaultDepthLimit, "/ipfs/Qmcqtw8FfrVSBaRmbWwHxt3AuySBhJLcvmFYi3Lbc4xnwj", nil)
69 + testResolution(t, r, "/ipns/QmbCMUZw6JFeZ7Wp9jkzbye3Fzp2GGcPgC3nmeUjfVF87n", opts.DefaultDepthLimit, "/ipfs/Qmcqtw8FfrVSBaRmbWwHxt3AuySBhJLcvmFYi3Lbc4xnwj", nil)
70 testResolution(t, r, "/ipns/QmbCMUZw6JFeZ7Wp9jkzbye3Fzp2GGcPgC3nmeUjfVF87n", 1, "/ipns/QmatmE9msSfkKxoffpHwNLNKgwZG8eT9Bud6YoPab52vpy", ErrResolveRecursion)
72 - testResolution(t, r, "/ipns/ipfs.io", DefaultDepthLimit, "/ipfs/Qmcqtw8FfrVSBaRmbWwHxt3AuySBhJLcvmFYi3Lbc4xnwj", nil)
71 + testResolution(t, r, "/ipns/ipfs.io", opts.DefaultDepthLimit, "/ipfs/Qmcqtw8FfrVSBaRmbWwHxt3AuySBhJLcvmFYi3Lbc4xnwj", nil)
72 testResolution(t, r, "/ipns/ipfs.io", 1, "/ipns/QmbCMUZw6JFeZ7Wp9jkzbye3Fzp2GGcPgC3nmeUjfVF87n", ErrResolveRecursion)
73 testResolution(t, r, "/ipns/ipfs.io", 2, "/ipns/QmatmE9msSfkKxoffpHwNLNKgwZG8eT9Bud6YoPab52vpy", ErrResolveRecursion)
75 - testResolution(t, r, "/ipns/QmY3hE8xgFCjGcz6PHgnvJz5HZi1BaKRfPkn1ghZUcYMjD", DefaultDepthLimit, "/ipfs/Qmcqtw8FfrVSBaRmbWwHxt3AuySBhJLcvmFYi3Lbc4xnwj", nil)
74 + testResolution(t, r, "/ipns/QmY3hE8xgFCjGcz6PHgnvJz5HZi1BaKRfPkn1ghZUcYMjD", opts.DefaultDepthLimit, "/ipfs/Qmcqtw8FfrVSBaRmbWwHxt3AuySBhJLcvmFYi3Lbc4xnwj", nil)
75 testResolution(t, r, "/ipns/QmY3hE8xgFCjGcz6PHgnvJz5HZi1BaKRfPkn1ghZUcYMjD", 1, "/ipns/ipfs.io", ErrResolveRecursion)
76 testResolution(t, r, "/ipns/QmY3hE8xgFCjGcz6PHgnvJz5HZi1BaKRfPkn1ghZUcYMjD", 2, "/ipns/QmbCMUZw6JFeZ7Wp9jkzbye3Fzp2GGcPgC3nmeUjfVF87n", ErrResolveRecursion)
77 testResolution(t, r, "/ipns/QmY3hE8xgFCjGcz6PHgnvJz5HZi1BaKRfPkn1ghZUcYMjD", 3, "/ipns/QmatmE9msSfkKxoffpHwNLNKgwZG8eT9Bud6YoPab52vpy", ErrResolveRecursion)
namesys/opts.go deleted
-29
@@ -1,29 +0,0 @@
1 -package namesys
2 -
3 -import (
4 - "time"
5 -)
6 -
7 -// ResolveOpts specifies options for resolving an IPNS path
8 -type ResolveOpts struct {
9 - // Recursion depth limit
10 - Depth uint
11 - // The number of IPNS records to retrieve from the DHT
12 - // (the best record is selected from this set)
13 - DhtRecordCount uint
14 - // The amount of time to wait for DHT records to be fetched
15 - // and verified. A zero value indicates that there is no explicit
16 - // timeout (although there is an implicit timeout due to dial
17 - // timeouts within the DHT)
18 - DhtTimeout time.Duration
19 -}
20 -
21 -// DefaultResolveOpts returns the default options for resolving
22 -// an IPNS path
23 -func DefaultResolveOpts() *ResolveOpts {
24 - return &ResolveOpts{
25 - Depth: DefaultDepthLimit,
26 - DhtRecordCount: 16,
27 - DhtTimeout: time.Minute,
28 - }
29 -}
namesys/opts/opts.go new
+68
@@ -0,0 +1,68 @@
1 +package namesys_opts
2 +
3 +import (
4 + "time"
5 +)
6 +
7 +const (
8 + // DefaultDepthLimit is the default depth limit used by Resolve.
9 + DefaultDepthLimit = 32
10 +
11 + // UnlimitedDepth allows infinite recursion in Resolve. You
12 + // probably don't want to use this, but it's here if you absolutely
13 + // trust resolution to eventually complete and can't put an upper
14 + // limit on how many steps it will take.
15 + UnlimitedDepth = 0
16 +)
17 +
18 +// ResolveOpts specifies options for resolving an IPNS path
19 +type ResolveOpts struct {
20 + // Recursion depth limit
21 + Depth uint
22 + // The number of IPNS records to retrieve from the DHT
23 + // (the best record is selected from this set)
24 + DhtRecordCount uint
25 + // The amount of time to wait for DHT records to be fetched
26 + // and verified. A zero value indicates that there is no explicit
27 + // timeout (although there is an implicit timeout due to dial
28 + // timeouts within the DHT)
29 + DhtTimeout time.Duration
30 +}
31 +
32 +// DefaultResolveOpts returns the default options for resolving
33 +// an IPNS path
34 +func DefaultResolveOpts() *ResolveOpts {
35 + return &ResolveOpts{
36 + Depth: DefaultDepthLimit,
37 + DhtRecordCount: 16,
38 + DhtTimeout: time.Minute,
39 + }
40 +}
41 +
42 +type ResolveOpt func(*ResolveOpts)
43 +
44 +func Depth(depth uint) ResolveOpt {
45 + return func(o *ResolveOpts) {
46 + o.Depth = depth
47 + }
48 +}
49 +
50 +func DhtRecordCount(count uint) ResolveOpt {
51 + return func(o *ResolveOpts) {
52 + o.DhtRecordCount = count
53 + }
54 +}
55 +
56 +func DhtTimeout(timeout time.Duration) ResolveOpt {
57 + return func(o *ResolveOpts) {
58 + o.DhtTimeout = timeout
59 + }
60 +}
61 +
62 +func ProcessOpts(opts []ResolveOpt) *ResolveOpts {
63 + rsopts := DefaultResolveOpts()
64 + for _, option := range opts {
65 + option(rsopts)
66 + }
67 + return rsopts
68 +}
namesys/proquint.go
+4 -3
@@ -5,6 +5,7 @@ import (
5
6 context "context"
7
8 + opts "github.com/ipfs/go-ipfs/namesys/opts"
9 path "github.com/ipfs/go-ipfs/path"
10 proquint "gx/ipfs/QmYnf27kzqR2cxt6LFZdrAFJuQd6785fTkBvMuEj9EeRxM/proquint"
11 )
@@ -12,12 +13,12 @@ import (
13 type ProquintResolver struct{}
14
15 // Resolve implements Resolver.
15 -func (r *ProquintResolver) Resolve(ctx context.Context, name string, opts *ResolveOpts) (path.Path, error) {
16 - return resolve(ctx, r, name, opts, "/ipns/")
16 +func (r *ProquintResolver) Resolve(ctx context.Context, name string, options ...opts.ResolveOpt) (path.Path, error) {
17 + return resolve(ctx, r, name, opts.ProcessOpts(options), "/ipns/")
18 }
19
20 // resolveOnce implements resolver. Decodes the proquint string.
20 -func (r *ProquintResolver) resolveOnce(ctx context.Context, name string, opts *ResolveOpts) (path.Path, error) {
21 +func (r *ProquintResolver) resolveOnce(ctx context.Context, name string, options *opts.ResolveOpts) (path.Path, error) {
22 ok, err := proquint.IsProquint(name)
23 if err != nil || !ok {
24 return "", errors.New("not a valid proquint string")
namesys/pubsub.go
+4 -3
@@ -8,6 +8,7 @@ import (
8 "sync"
9 "time"
10
11 + opts "github.com/ipfs/go-ipfs/namesys/opts"
12 pb "github.com/ipfs/go-ipfs/namesys/pb"
13 path "github.com/ipfs/go-ipfs/path"
14
@@ -185,11 +186,11 @@ func (p *PubsubPublisher) publishRecord(ctx context.Context, k ci.PrivKey, value
186 }
187
188 // Resolve resolves a name through pubsub and default depth limit
188 -func (r *PubsubResolver) Resolve(ctx context.Context, name string, opts *ResolveOpts) (path.Path, error) {
189 - return resolve(ctx, r, name, opts, "/ipns/")
189 +func (r *PubsubResolver) Resolve(ctx context.Context, name string, options ...opts.ResolveOpt) (path.Path, error) {
190 + return resolve(ctx, r, name, opts.ProcessOpts(options), "/ipns/")
191 }
192
192 -func (r *PubsubResolver) resolveOnce(ctx context.Context, name string, opts *ResolveOpts) (path.Path, error) {
193 +func (r *PubsubResolver) resolveOnce(ctx context.Context, name string, options *opts.ResolveOpts) (path.Path, error) {
194 log.Debugf("PubsubResolve: resolve '%s'", name)
195
196 // retrieve the public key once (for verifying messages)
namesys/pubsub_test.go
+2 -2
@@ -180,14 +180,14 @@ func TestPubsubPublishSubscribe(t *testing.T) {
180 }
181
182 func checkResolveNotFound(ctx context.Context, t *testing.T, i int, resolver Resolver, name string) {
183 - _, err := resolver.Resolve(ctx, name, DefaultResolveOpts())
183 + _, err := resolver.Resolve(ctx, name)
184 if err != ErrResolveFailed {
185 t.Fatalf("[resolver %d] unexpected error: %s", i, err.Error())
186 }
187 }
188
189 func checkResolve(ctx context.Context, t *testing.T, i int, resolver Resolver, name string, val path.Path) {
190 - xval, err := resolver.Resolve(ctx, name, DefaultResolveOpts())
190 + xval, err := resolver.Resolve(ctx, name)
191 if err != nil {
192 t.Fatalf("[resolver %d] resolve failed: %s", i, err.Error())
193 }
namesys/republisher/repub_test.go
+2 -2
@@ -98,7 +98,7 @@ func verifyResolution(nodes []*core.IpfsNode, key string, exp path.Path) error {
98 ctx, cancel := context.WithCancel(context.Background())
99 defer cancel()
100 for _, n := range nodes {
101 - val, err := n.Namesys.Resolve(ctx, key, namesys.DefaultResolveOpts())
101 + val, err := n.Namesys.Resolve(ctx, key)
102 if err != nil {
103 return err
104 }
@@ -114,7 +114,7 @@ func verifyResolutionFails(nodes []*core.IpfsNode, key string) error {
114 ctx, cancel := context.WithCancel(context.Background())
115 defer cancel()
116 for _, n := range nodes {
117 - _, err := n.Namesys.Resolve(ctx, key, namesys.DefaultResolveOpts())
117 + _, err := n.Namesys.Resolve(ctx, key)
118 if err == nil {
119 return errors.New("expected resolution to fail")
120 }
namesys/resolve_test.go
+2 -2
@@ -40,7 +40,7 @@ func TestRoutingResolve(t *testing.T) {
40 t.Fatal(err)
41 }
42
43 - res, err := resolver.Resolve(context.Background(), pid.Pretty(), DefaultResolveOpts())
43 + res, err := resolver.Resolve(context.Background(), pid.Pretty())
44 if err != nil {
45 t.Fatal(err)
46 }
@@ -125,7 +125,7 @@ func TestPrexistingRecord(t *testing.T) {
125 }
126
127 func verifyCanResolve(r Resolver, name string, exp path.Path) error {
128 - res, err := r.Resolve(context.Background(), name, DefaultResolveOpts())
128 + res, err := r.Resolve(context.Background(), name)
129 if err != nil {
130 return err
131 }
namesys/routing.go
+9 -8
@@ -5,6 +5,7 @@ import (
5 "strings"
6 "time"
7
8 + opts "github.com/ipfs/go-ipfs/namesys/opts"
9 pb "github.com/ipfs/go-ipfs/namesys/pb"
10 path "github.com/ipfs/go-ipfs/path"
11
@@ -104,23 +105,23 @@ func NewRoutingResolver(route routing.ValueStore, cachesize int) *routingResolve
105 }
106
107 // Resolve implements Resolver.
107 -func (r *routingResolver) Resolve(ctx context.Context, name string, opts *ResolveOpts) (path.Path, error) {
108 - return resolve(ctx, r, name, opts, "/ipns/")
108 +func (r *routingResolver) Resolve(ctx context.Context, name string, options ...opts.ResolveOpt) (path.Path, error) {
109 + return resolve(ctx, r, name, opts.ProcessOpts(options), "/ipns/")
110 }
111
112 // resolveOnce implements resolver. Uses the IPFS routing system to
113 // resolve SFS-like names.
113 -func (r *routingResolver) resolveOnce(ctx context.Context, name string, opts *ResolveOpts) (path.Path, error) {
114 +func (r *routingResolver) resolveOnce(ctx context.Context, name string, options *opts.ResolveOpts) (path.Path, error) {
115 log.Debugf("RoutingResolver resolving %s", name)
116 cached, ok := r.cacheGet(name)
117 if ok {
118 return cached, nil
119 }
120
120 - if opts.DhtTimeout != 0 {
121 + if options.DhtTimeout != 0 {
122 // Resolution must complete within the timeout
123 var cancel context.CancelFunc
123 - ctx, cancel = context.WithTimeout(ctx, opts.DhtTimeout)
124 + ctx, cancel = context.WithTimeout(ctx, options.DhtTimeout)
125 defer cancel()
126 }
127
@@ -153,7 +154,7 @@ func (r *routingResolver) resolveOnce(ctx context.Context, name string, opts *Re
154 // Note that the DHT will call the ipns validator when retrieving
155 // the value, which in turn verifies the ipns record signature
156 _, ipnsKey := IpnsKeysForID(pid)
156 - val, err := r.getValue(ctx, ipnsKey, opts)
157 + val, err := r.getValue(ctx, ipnsKey, options)
158 if err != nil {
159 log.Debugf("RoutingResolver: dht get for name %s failed: %s", name, err)
160 return "", err
@@ -186,9 +187,9 @@ func (r *routingResolver) resolveOnce(ctx context.Context, name string, opts *Re
187 }
188 }
189
189 -func (r *routingResolver) getValue(ctx context.Context, ipnsKey string, opts *ResolveOpts) ([]byte, error) {
190 +func (r *routingResolver) getValue(ctx context.Context, ipnsKey string, options *opts.ResolveOpts) ([]byte, error) {
191 // Get specified number of values from the DHT
191 - vals, err := r.routing.GetValues(ctx, ipnsKey, int(opts.DhtRecordCount))
192 + vals, err := r.routing.GetValues(ctx, ipnsKey, int(options.DhtRecordCount))
193 if err != nil {
194 return nil, err
195 }