Skip to content
This repository has been archived by the owner on Dec 7, 2019. It is now read-only.

NoDial context option #42

Merged
merged 3 commits into from
Apr 10, 2019
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
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
4 changes: 4 additions & 0 deletions interface.go
Original file line number Diff line number Diff line change
Expand Up @@ -149,6 +149,10 @@ type Network interface {
// There are no addresses associated with a peer when they were needed.
var ErrNoRemoteAddrs = errors.New("no remote addresses")

// ErrNoConn is returned when attempting to open a stream to a peer with the NoDial
// option and no usable connection is available.
var ErrNoConn = errors.New("no usable connection to peer")

// Dialer represents a service that can dial out to peers
// (this is usually just a Network, but other services may not need the whole
// stack, and thus it becomes easier to mock)
Expand Down
25 changes: 25 additions & 0 deletions options.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,25 @@
package net

import (
"context"
)

type noDialCtxKey struct{}

var noDial = noDialCtxKey{}

// WithNoDial constructs a new context with an option that instructs the network
// to not attempt a new dial when opening a stream.
func WithNoDial(ctx context.Context, reason string) {
context.WithValue(ctx, noDial, reason)
}

// GetNoDial returns true if the no dial option is set in the context.
func GetNoDial(ctx context.Context) (nodial bool, reason string) {
v := ctx.Value(noDial)
if v != nil {
return true, v.(string)
}

return false, ""
}
Copy link
Member

Choose a reason for hiding this comment

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

So, personally, I'd not expose the NoDial var but instead expose a GetNoDial(ctx) (nodial bool, why string) function. That way, we can change how we implement all this internally.

For example, we may want to "lift" all of our options into an option struct if we end up chaining contexts too much (searching for a value in a context is O(n)).

Copy link
Contributor Author

Choose a reason for hiding this comment

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

ok, will do.

Copy link
Member

Choose a reason for hiding this comment

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

(I mean, this just comes down to "patterns" but I believe this is the more common pattern.)

Copy link
Contributor Author

Choose a reason for hiding this comment

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

done.