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

New HTTP client connection pooling #8100

Merged
merged 86 commits into from
Oct 19, 2022
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
86 commits
Select commit Hold shift + click to select a range
25c1d35
new http2 pool
yawkat Sep 19, 2022
434fd9e
streaming get
yawkat Sep 19, 2022
2b620de
http1 plaintext support
yawkat Sep 19, 2022
8f0e4b4
test http2 connection reuse
yawkat Sep 19, 2022
b19ef74
http1 connection reuse
yawkat Sep 20, 2022
5704549
restructure tests a bit
yawkat Sep 20, 2022
3aa1226
reuse streaming http1 connections
yawkat Sep 20, 2022
f7bb5c0
http1 tls
yawkat Sep 20, 2022
f82bfca
h2c
yawkat Sep 20, 2022
47fbed1
channel customization
yawkat Sep 21, 2022
b06fb15
test h2c customization
yawkat Sep 21, 2022
c966519
test http1 compression
yawkat Sep 21, 2022
c0aa9f3
http2 compression
yawkat Sep 21, 2022
ff1c897
http2 frame logging
yawkat Sep 21, 2022
c20542b
remove some code, implement connection read timeout
yawkat Sep 22, 2022
d1b2e13
delete some code
yawkat Sep 23, 2022
32b2025
implement connection ttl
yawkat Sep 23, 2022
f780749
implement connection idle timeout
yawkat Sep 23, 2022
f7509c1
fix h2c
yawkat Sep 23, 2022
163a27a
add log handler for http1
yawkat Sep 23, 2022
e38e484
ssl handshake timeout
yawkat Sep 23, 2022
aafe969
sse support
yawkat Sep 23, 2022
ca40d1a
websocket support
yawkat Sep 23, 2022
4deebe0
new http version infrastructure
yawkat Sep 26, 2022
10fcbca
connection pool size settings
yawkat Sep 26, 2022
6f190ac
fix some todos
yawkat Sep 26, 2022
e96d8f6
handle cancelled pool acquisition
yawkat Sep 26, 2022
13a70f6
fix multipart requests
yawkat Sep 26, 2022
045b731
improve channel emulation
yawkat Sep 26, 2022
6989154
fix publisher requests
yawkat Sep 27, 2022
39973e6
add missing read call in server
yawkat Sep 27, 2022
f43b0b1
improve error messages
yawkat Sep 27, 2022
0f43b5d
fix http1 pool sizing
yawkat Sep 28, 2022
88c0f7a
move request dispatch logic into PoolResizer to avoid concurrency issues
yawkat Sep 28, 2022
0419a3e
improve error handling for dispatch
yawkat Sep 28, 2022
e177515
improve handshake error handling
yawkat Sep 28, 2022
dc50736
fix ssl handshake timeout error
yawkat Sep 28, 2022
ea74a0b
fix duplicate handler
yawkat Sep 28, 2022
4a21439
fix http version selection
yawkat Sep 28, 2022
4069329
remove obsolete Http2Stream handling for sse
yawkat Sep 28, 2022
66a24ce
Merge branch '4.0.x' into request-channel-4x
yawkat Sep 28, 2022
84a9007
fix merge
yawkat Sep 28, 2022
a106f20
fix sse decoding
yawkat Sep 28, 2022
d18a4df
comments on PoolResizer
yawkat Sep 28, 2022
94441bf
move HttpLineBasedFrameDecoder removal logic
yawkat Sep 28, 2022
0431175
implement pool disable option
yawkat Sep 28, 2022
4df4d34
fix SslRefreshSpec
yawkat Sep 28, 2022
ce54ced
make test not use ChannelPipelineCustomizer
yawkat Sep 29, 2022
e76c2a9
handle sslConfiguration.enabled properly
yawkat Sep 29, 2022
0b61862
fix client tests that rely on pool internals
yawkat Sep 29, 2022
40b0fad
fix HttpResponseSpec
yawkat Sep 29, 2022
5f7d2bd
fix test
yawkat Sep 29, 2022
033d135
fix test
yawkat Sep 29, 2022
f7f1c08
fix BinaryWebSocketSpec
yawkat Sep 29, 2022
dce9aa7
fix LogbookNettyClientCustomizer
yawkat Sep 29, 2022
aa55b2d
fix Http2AccessLoggerSpec
yawkat Sep 29, 2022
1dbc9be
remove obsolete idle state handling
yawkat Sep 30, 2022
130b492
remove todo
yawkat Sep 30, 2022
8e4ac0d
move exchange/stream-specific handlers to DefaultHttpClient
yawkat Sep 30, 2022
122d65c
remove some raw types
yawkat Sep 30, 2022
1626acb
remove todo
yawkat Sep 30, 2022
9d9460b
fix compile error
yawkat Sep 30, 2022
e0b4ba7
prevent double release
yawkat Sep 30, 2022
45be5c0
remove terminateRequestChannel
yawkat Sep 30, 2022
4337ca4
implement pool handle leak detection
yawkat Sep 30, 2022
aeea702
fix some todos
yawkat Sep 30, 2022
b13ee30
spotless
yawkat Sep 30, 2022
4ed4948
checkstyle
yawkat Sep 30, 2022
e780c18
docs
yawkat Sep 30, 2022
966cd48
sonar
yawkat Sep 30, 2022
826586b
fix keepAliveOnServerError and enable it by default
yawkat Sep 30, 2022
4de283e
fix test
yawkat Sep 30, 2022
9ac7fb5
fix test
yawkat Sep 30, 2022
8fb7b24
fix *another* test
yawkat Sep 30, 2022
74bccc7
implement max-pending-acquires, remove unused config options
yawkat Oct 10, 2022
02209b1
docs
yawkat Oct 10, 2022
17aaad7
Merge branch '4.0.x' into request-channel-4x
yawkat Oct 10, 2022
14d679e
test for max-pending-acquires
yawkat Oct 11, 2022
ee06047
test for max-concurrent-http1-connections
yawkat Oct 11, 2022
cfd7054
Merge branch '4.0.x' into request-channel-4x
yawkat Oct 12, 2022
f40b38c
address feedback
yawkat Oct 17, 2022
af90519
fix remove order
yawkat Oct 17, 2022
e93e189
handle non-mutable http requests properly
yawkat Oct 17, 2022
213eb60
Merge branch '4.0.x' into request-channel-4x
yawkat Oct 17, 2022
68bc654
fix merge
yawkat Oct 17, 2022
93bd6bb
spotless
yawkat Oct 17, 2022
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
Original file line number Diff line number Diff line change
Expand Up @@ -36,8 +36,11 @@
import java.nio.charset.StandardCharsets;
import java.time.Duration;
import java.time.temporal.ChronoUnit;
import java.util.Arrays;
import java.util.Collections;
import java.util.List;
import java.util.Map;
import java.util.Objects;
import java.util.Optional;
import java.util.OptionalInt;
import java.util.concurrent.ThreadFactory;
Expand Down Expand Up @@ -145,7 +148,16 @@ public abstract class HttpClientConfiguration {

private String eventLoopGroup = "default";

private HttpVersion httpVersion = HttpVersion.HTTP_1_1;
@Deprecated
@Nullable
private HttpVersion httpVersion = null;

private HttpVersionSelection.PlaintextMode plaintextMode = HttpVersionSelection.PlaintextMode.HTTP_1;

private List<String> alpnModes = Arrays.asList(
HttpVersionSelection.ALPN_HTTP_2,
HttpVersionSelection.ALPN_HTTP_1
);

private LogLevel logLevel;

Expand Down Expand Up @@ -201,15 +213,23 @@ public HttpClientConfiguration(HttpClientConfiguration copy) {
/**
* The HTTP version to use. Defaults to {@link HttpVersion#HTTP_1_1}.
* @return The http version
* @deprecated There are now separate settings for HTTP and HTTPS connections. To configure
* HTTP connections (e.g. for h2c), use {@link #plaintextMode}. To configure ALPN, set
* {@link #alpnModes}.
*/
@Deprecated
public HttpVersion getHttpVersion() {
return httpVersion;
}

/**
* Sets the HTTP version to use. Defaults to {@link HttpVersion#HTTP_1_1}.
* @param httpVersion The http version
* @deprecated There are now separate settings for HTTP and HTTPS connections. To configure
* HTTP connections (e.g. for h2c), use {@link #plaintextMode}. To configure ALPN, set
* {@link #alpnModes}.
*/
@Deprecated
public void setHttpVersion(HttpVersion httpVersion) {
if (httpVersion != null) {
this.httpVersion = httpVersion;
Expand Down Expand Up @@ -637,6 +657,58 @@ public Proxy resolveProxy(boolean isSsl, String host, int port) {
}
}

/**
* The connection mode to use for <i>plaintext</i> (http as opposed to https) connections.
* <br>
* <b>Note: If {@link #httpVersion} is set, this setting is ignored!</b>
*
* @return The plaintext connection mode.
* @since 4.0.0
*/
@NonNull
public HttpVersionSelection.PlaintextMode getPlaintextMode() {
yawkat marked this conversation as resolved.
Show resolved Hide resolved
return plaintextMode;
}

/**
* The connection mode to use for <i>plaintext</i> (http as opposed to https) connections.
* <br>
* <b>Note: If {@link #httpVersion} is set, this setting is ignored!</b>
*
* @param plaintextMode The plaintext connection mode.
* @since 4.0.0
*/
public void setPlaintextMode(@NonNull HttpVersionSelection.PlaintextMode plaintextMode) {
this.plaintextMode = Objects.requireNonNull(plaintextMode, "plaintextMode");
}

/**
* The protocols to support for TLS ALPN. If HTTP 2 is included, this will also restrict the
* TLS cipher suites to those supported by the HTTP 2 standard.
* <br>
* <b>Note: If {@link #httpVersion} is set, this setting is ignored!</b>
*
* @return The supported ALPN protocols.
* @since 4.0.0
*/
@NonNull
public List<String> getAlpnModes() {
yawkat marked this conversation as resolved.
Show resolved Hide resolved
return alpnModes;
}

/**
* The protocols to support for TLS ALPN. If HTTP 2 is included, this will also restrict the
* TLS cipher suites to those supported by the HTTP 2 standard.
* <br>
* <b>Note: If {@link #httpVersion} is set, this setting is ignored!</b>
*
* @param alpnModes The supported ALPN protocols.
* @since 4.0.0
*/
public void setAlpnModes(@NonNull List<String> alpnModes) {
this.alpnModes = Objects.requireNonNull(alpnModes, "alpnModes");
}

/**
* Configuration for the HTTP client connnection pool.
*/
Expand All @@ -650,15 +722,13 @@ public static class ConnectionPoolConfiguration implements Toggleable {
* The default enable value.
*/
@SuppressWarnings("WeakerAccess")
public static final boolean DEFAULT_ENABLED = false;
public static final boolean DEFAULT_ENABLED = true;

/**
* The default max connections value.
*/
@SuppressWarnings("WeakerAccess")
public static final int DEFAULT_MAXCONNECTIONS = -1;
private int maxPendingConnections = 4;

private int maxConnections = DEFAULT_MAXCONNECTIONS;
private int maxConcurrentRequestsPerHttp2Connection = Integer.MAX_VALUE;
private int maxConcurrentHttp1Connections = Integer.MAX_VALUE;
private int maxConcurrentHttp2Connections = 1;

private int maxPendingAcquires = Integer.MAX_VALUE;

Expand All @@ -685,24 +755,6 @@ public void setEnabled(boolean enabled) {
this.enabled = enabled;
}

/**
* The maximum number of connections. Defaults to ({@value io.micronaut.http.client.HttpClientConfiguration.ConnectionPoolConfiguration#DEFAULT_MAXCONNECTIONS}); no maximum.
*
* @return The max connections
*/
public int getMaxConnections() {
return maxConnections;
}

/**
* Sets the maximum number of connections. Defaults to no maximum.
*
* @param maxConnections The count
*/
public void setMaxConnections(int maxConnections) {
this.maxConnections = maxConnections;
}

Comment on lines -688 to -705
Copy link
Contributor

Choose a reason for hiding this comment

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

can we deprecate instead of remove?

Copy link
Member Author

Choose a reason for hiding this comment

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

sure but why, since it's going into 4.0 anyway?

/**
* Maximum number of futures awaiting connection acquisition. Defaults to no maximum.
*
Expand Down Expand Up @@ -738,5 +790,90 @@ public Optional<Duration> getAcquireTimeout() {
public void setAcquireTimeout(@Nullable Duration acquireTimeout) {
this.acquireTimeout = acquireTimeout;
}

/**
* The maximum number of <i>pending</i> (new) connections before they are assigned to a
* pool.
*
* @return The maximum number of pending connections
* @since 4.0.0
*/
public int getMaxPendingConnections() {
yawkat marked this conversation as resolved.
Show resolved Hide resolved
return maxPendingConnections;
}

/**
* The maximum number of <i>pending</i> (new) connections before they are assigned to a
* pool.
*
* @param maxPendingConnections The maximum number of pending connections
* @since 4.0.0
*/
public void setMaxPendingConnections(int maxPendingConnections) {
yawkat marked this conversation as resolved.
Show resolved Hide resolved
this.maxPendingConnections = maxPendingConnections;
}

/**
* The maximum number of requests (streams) that can run concurrently on one HTTP2
* connection.
*
* @return The maximum concurrent request count
* @since 4.0.0
*/
public int getMaxConcurrentRequestsPerHttp2Connection() {
yawkat marked this conversation as resolved.
Show resolved Hide resolved
return maxConcurrentRequestsPerHttp2Connection;
}

/**
* The maximum number of requests (streams) that can run concurrently on one HTTP2
* connection.
*
* @param maxConcurrentRequestsPerHttp2Connection The maximum concurrent request count
* @since 4.0.0
*/
public void setMaxConcurrentRequestsPerHttp2Connection(int maxConcurrentRequestsPerHttp2Connection) {
yawkat marked this conversation as resolved.
Show resolved Hide resolved
this.maxConcurrentRequestsPerHttp2Connection = maxConcurrentRequestsPerHttp2Connection;
}

/**
* The maximum number of concurrent HTTP1 connections in the pool.
*
* @return The maximum concurrent connection count
* @since 4.0.0
*/
public int getMaxConcurrentHttp1Connections() {
yawkat marked this conversation as resolved.
Show resolved Hide resolved
return maxConcurrentHttp1Connections;
}

/**
* The maximum number of concurrent HTTP1 connections in the pool.
*
* @param maxConcurrentHttp1Connections The maximum concurrent connection count
* @since 4.0.0
*/
public void setMaxConcurrentHttp1Connections(int maxConcurrentHttp1Connections) {
yawkat marked this conversation as resolved.
Show resolved Hide resolved
this.maxConcurrentHttp1Connections = maxConcurrentHttp1Connections;
}

/**
* The maximum number of concurrent HTTP2 connections in the pool.
*
* @return The maximum concurrent connection count
* @since 4.0.0
*/
public int getMaxConcurrentHttp2Connections() {
yawkat marked this conversation as resolved.
Show resolved Hide resolved
return maxConcurrentHttp2Connections;
}

/**
* The maximum number of concurrent HTTP2 connections in the pool.
*
* @param maxConcurrentHttp2Connections The maximum concurrent connection count
* @since 4.0.0
*/
public void setMaxConcurrentHttp2Connections(int maxConcurrentHttp2Connections) {
yawkat marked this conversation as resolved.
Show resolved Hide resolved
this.maxConcurrentHttp2Connections = maxConcurrentHttp2Connections;
}
}

}
Original file line number Diff line number Diff line change
Expand Up @@ -47,9 +47,25 @@ public interface HttpClientRegistry<T extends HttpClient> {
* @param clientId The client ID
* @param path The path (Optional)
* @return The client
* @deprecated Use {@link #getClient(HttpVersionSelection, String, String)} instead
*/
@Deprecated
@NonNull
T getClient(HttpVersion httpVersion, @NonNull String clientId, @Nullable String path);
default T getClient(HttpVersion httpVersion, @NonNull String clientId, @Nullable String path) {
return getClient(HttpVersionSelection.forLegacyVersion(httpVersion), clientId, path);
}

/**
* Return the client for the client ID and path.
*
* @param httpVersion The HTTP version
* @param clientId The client ID
* @param path The path (Optional)
* @return The client
* @since 4.0.0
*/
@NonNull
T getClient(@NonNull HttpVersionSelection httpVersion, @NonNull String clientId, @Nullable String path);

/**
* Resolves a {@link HttpClient} for the given injection point.
Expand Down
Loading