Skip to content
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

net: default dialer should accept list of IPs with fallback included #20782

Open
AlmogBaku opened this issue Jun 24, 2017 · 12 comments
Open

net: default dialer should accept list of IPs with fallback included #20782

AlmogBaku opened this issue Jun 24, 2017 · 12 comments

Comments

@AlmogBaku
Copy link

AlmogBaku commented Jun 24, 2017

Please answer these questions before submitting your issue. Thanks!

What version of Go are you using (go version)?

master

What did you do?

  1. In case you want to implement/extend your own dialer you might want to use the original dialer to handle all the TCP/UDP connection, but to still resolve the DNS.. in this scenario you can't wrap it and just send list of IPs because it won't use fallbacks
  2. In case you want to dial IP with fallbacks you can't do that.

What did you expect to see?

func (d *Dialer) DialContext(ctx context.Context, network string, addresses []string) (Conn, error) will accept list of addresses

Or at least

func (d *Dialer) DialContextWithFallbacks(ctx context.Context, network string, addresses []string) (Conn, error)

@bradfitz
Copy link
Contributor

I'm not sure I understand your problem enough yet to start discussion solutions yet.

Can you elaborate?

/cc @mikioh

@bradfitz bradfitz added the WaitingForInfo Issue is not actionable because of missing required information, which needs to be provided. label Jun 24, 2017
@bradfitz bradfitz added this to the Unplanned milestone Jun 24, 2017
@AlmogBaku
Copy link
Author

This feature enables few scenarios:

  1. My current issue - I want to create a custom dialer, that resolves the hostname, filter it results, and then dial to it. If i'll just use any other dialer i'll lose the option to have fallback IPs, or I'll have to implement it myself.
func DialContext(ctx context.Context, network, address string) (net.Conn, error) {
	ips, err := net.LookupIP(address)
	if err != nil {
		panic(err)
	}
	
	// Now we want to dial at least one of these IPs
}
  1. Allowing dialing list of IPs without hostname (this will call the primary IPs, and will try to reach at least one connection.. otherwise it'll fall to the fallback IPs)

@AlmogBaku
Copy link
Author

If you'll take a look at the Default Dialer, you can see that after it resolves the IPs it dial them and try to reach at least one of them:
https://github.com/golang/go/blob/master/src/net/dial.go#L394

In case you want to do the same with IPs, you can't do that without implementing the whole dialer by yourself (or at least copying it)

@as
Copy link
Contributor

as commented Jun 24, 2017

Based on context, it seems the proposal is to expose the behavior of concurrent name resolution and subsequent connection attempts by allowing a list of addresses to be passed in to DialContext instead of just one address (please correct me if I'm wrong). This change implies that addresses in this list are all IP addresses that do not require name resolution. One concern I have is what happens when []address contains names that need to be resolved too?

@AlmogBaku
Copy link
Author

AlmogBaku commented Jun 24, 2017

@as we can either expose the dialer of the steps other the resolution(then DialerContext() will call DialerContextWithFallbacks()) or to flatten the list of hosts.

Obviously the second one will introduce breaking news, so the first option is just easier to implement

@mikioh
Copy link
Contributor

mikioh commented Aug 2, 2017

@AlmogBaku,

I'm still not sure what is you really want but it looks like you want to use some internal functionality of the net package; it's probably part of TCP connection setup methods for RFC 3493-style (iterating each IP address) and RFC 6555-style (Happy Eyeballs).

FWIW, the Happy Eyeballs method will be updated to version 2 not far in future: https://tools.ietf.org/html/draft-ietf-v6ops-rfc6555bis.

As the I-D (6555bis) section 2 "Overview" describes, the connection setup methods comprise of distinct phases. I don't understand whether you want to make some tailor-made connection setup API just for your use case, or you want to make a bit flexible API that allows you to compose the distinct phases with concurrency support under your control. I personally much prefer the latter rather than the former.

@jfesler
Copy link

jfesler commented Jun 21, 2018

This issue interests me as well. I'd like to do DNS caching before dialing; and I'll lose all the wonderful happy eyeballs behavior if I can only send a single (resolved and cached) IP address. I'd rather pass the full list.

My alternative is to duplicate dial.go (and then track changes over go releases), with some kind of wrapper around resolveAddrList.

@bradfitz bradfitz added FeatureRequest and removed WaitingForInfo Issue is not actionable because of missing required information, which needs to be provided. labels Jun 21, 2018
@AlmogBaku
Copy link
Author

@bradfitz how can i help fill the gaps?

@bradfitz
Copy link
Contributor

In Go 1.9 we added https://golang.org/pkg/net/#Resolver.Dial to control how a DNS connection is created. You can use that to create a fake in-memory DNS connection that returns any A and/or AAAA records you want, and then use that Resolver with your *net.Dialer.

You can use the https://godoc.org/golang.org/x/net/dns/dnsmessage package to serialize the records in your net.Conn implementation.

@bradfitz
Copy link
Contributor

Actually, #12503 and https://golang.org/cl/115855 will make this even easier. So maybe you just wait for that.

@AlmogBaku
Copy link
Author

AlmogBaku commented Jun 25, 2018 via email

@tv42
Copy link

tv42 commented May 14, 2019

I think this could be safely closed in favor of #12503. This is asking for a specific, different, mechanism, but the underlying desire of not reimplementing Happy Eyeballs seems to be the same, and it seems like #12503 would be a clean route to this.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

No branches or pull requests

6 participants