HttpClient support for multi-homed hosts

classic Classic list List threaded Threaded
4 messages Options
Reply | Threaded
Open this post in threaded view
|

HttpClient support for multi-homed hosts

John Gardiner Myers
I am looking into in contributing a change to add support for
multi-homed destinations to Jetty HttpClient. This would seem to involve
replacing SocketAddressResolver with something that uses
InetAddress.getAllByName(String).

I was thinking of an implementation that tries each address in order
(giving each one a full connectTimeout) until one connection succeeds.

This appears to require making incompatible changes to the public API.
For one, HttpClient exposes a getter and setter for its
SocketAddressResolver. For another, implementations of
HttpClientTransport could assume that there would be only one attempt to
call HttpClientTransport.connect(SocketAddress, Map<String, Object>) per
destination. For example, HttpClientTransportOverHTTP2 aborts the
HttpDestination on a connection failure.

Happy Eyeballs would break even more assumptions made by
HttpClientTransport implementations.

There's also the minor issue that it isn't possible to get a collection
of InetSocketAddress for a multi-homed hostname where each
InetSocketAddress knows its hostname.

Do the Jetty developers have any comments or suggestions? Is there any
such change that would have a chance of being accepted?

_______________________________________________
jetty-users mailing list
[hidden email]
To change your delivery options, retrieve your password, or unsubscribe from this list, visit
https://dev.eclipse.org/mailman/listinfo/jetty-users
Reply | Threaded
Open this post in threaded view
|

Re: HttpClient support for multi-homed hosts

Simone Bordet-3
Hi,

On Fri, Aug 21, 2015 at 1:23 AM, John Gardiner Myers
<[hidden email]> wrote:

> I am looking into in contributing a change to add support for multi-homed
> destinations to Jetty HttpClient. This would seem to involve replacing
> SocketAddressResolver with something that uses
> InetAddress.getAllByName(String).
>
> I was thinking of an implementation that tries each address in order (giving
> each one a full connectTimeout) until one connection succeeds.
>
> This appears to require making incompatible changes to the public API. For
> one, HttpClient exposes a getter and setter for its SocketAddressResolver.

This change has been made only very recently, and it's not out to a release yet.
So we can change SocketAddressResolver.resolve(...) to take a
Promise<List<SocketAddress>>.

> For another, implementations of HttpClientTransport could assume that there
> would be only one attempt to call HttpClientTransport.connect(SocketAddress,
> Map<String, Object>) per destination. For example,
> HttpClientTransportOverHTTP2 aborts the HttpDestination on a connection
> failure.

No, the connect() operation only notifies a callback.

If HttpClient.newConnection() is changed to call transport.connect()
passing in a local callback that detects whether the connection has
been successful or not, then we should be able to implement what you
want.
If the local callback fails, just go to the next SocketAddress.

> Happy Eyeballs would break even more assumptions made by HttpClientTransport
> implementations.

I don't think any assumption will be broken. The transport is asked to
connect and it is given a callback to notify that.
What the callback does after the connect is entirely replaceable.

> There's also the minor issue that it isn't possible to get a collection of
> InetSocketAddress for a multi-homed hostname where each InetSocketAddress
> knows its hostname.

This I don't follow. Can you expand ?

Just to recap your requisite:
You configure your DNS with multiple IPs for a single host name.
You would like to resolve the host name using getAllByName(String),
and try to connect to the IPs until the first succeeds, or all fail.

That is correct ?

> Do the Jetty developers have any comments or suggestions? Is there any such
> change that would have a chance of being accepted?

So far the change looks trivial: a signature change in a yet to be
released class that makes it more generic, and a loop in
HttpClient.newConnection().

--
Simone Bordet
----
http://cometd.org
http://webtide.com
Developer advice, training, services and support
from the Jetty & CometD experts.
_______________________________________________
jetty-users mailing list
[hidden email]
To change your delivery options, retrieve your password, or unsubscribe from this list, visit
https://dev.eclipse.org/mailman/listinfo/jetty-users
Reply | Threaded
Open this post in threaded view
|

Re: HttpClient support for multi-homed hosts

Simone Bordet-3
Hi,

On Fri, Aug 21, 2015 at 11:00 AM, Simone Bordet <[hidden email]> wrote:

>> There's also the minor issue that it isn't possible to get a collection of
>> InetSocketAddress for a multi-homed hostname where each InetSocketAddress
>> knows its hostname.
>
> This I don't follow. Can you expand ?
>
> Just to recap your requisite:
> You configure your DNS with multiple IPs for a single host name.
> You would like to resolve the host name using getAllByName(String),
> and try to connect to the IPs until the first succeeds, or all fail.
>
> That is correct ?

If so, please file a feature request at
https://bugs.eclipse.org/bugs/enter_bug.cgi?product=Jetty.

Thanks !

--
Simone Bordet
----
http://cometd.org
http://webtide.com
Developer advice, training, services and support
from the Jetty & CometD experts.
_______________________________________________
jetty-users mailing list
[hidden email]
To change your delivery options, retrieve your password, or unsubscribe from this list, visit
https://dev.eclipse.org/mailman/listinfo/jetty-users
Reply | Threaded
Open this post in threaded view
|

Re: HttpClient support for multi-homed hosts

John Gardiner Myers
In reply to this post by Simone Bordet-3
On 8/21/2015 2:00 AM, Simone Bordet wrote:
> This change has been made only very recently, and it's not out to a release yet.
> So we can change SocketAddressResolver.resolve(...) to take a
> Promise<List<SocketAddress>>.
Good, my request is timely.
>> For another, implementations of HttpClientTransport could assume that there
>> would be only one attempt to call HttpClientTransport.connect(SocketAddress,
>> Map<String, Object>) per destination. For example,
>> HttpClientTransportOverHTTP2 aborts the HttpDestination on a connection
>> failure.
> No, the connect() operation only notifies a callback.
A couple of the implementations appear to pull objects, such as the
HttpDestination, out of the Map<String, Object> and call modifying
operations on them.
>> There's also the minor issue that it isn't possible to get a collection of
>> InetSocketAddress for a multi-homed hostname where each InetSocketAddress
>> knows its hostname.
> This I don't follow. Can you expand ?
InetSocketAddress has three attributes, but there is no way to construct
an object through the public API specifying all three values. If the
code uses the InetSocketAddress(InetAddress, int) constructor, then were
any of the HttpClientTransport implementations to call the
InetSocketAddress.getHostName() accessor (to log or generate an error
message) that would cause a reverse-IP resolution.

_______________________________________________
jetty-users mailing list
[hidden email]
To change your delivery options, retrieve your password, or unsubscribe from this list, visit
https://dev.eclipse.org/mailman/listinfo/jetty-users