Skip to content

Commit accf1f3

Browse files
committed
Make Socket options configurable, close AsyncHttpClient#1086
1 parent 2bccd7c commit accf1f3

File tree

5 files changed

+139
-1
lines changed

5 files changed

+139
-1
lines changed

client/src/main/java/org/asynchttpclient/AsyncHttpClientConfig.java

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -257,6 +257,16 @@ public interface AsyncHttpClientConfig {
257257

258258
boolean isValidateResponseHeaders();
259259

260+
boolean isTcpNoDelay();
261+
262+
boolean isSoReuseAddress();
263+
264+
int getSoLinger();
265+
266+
int getSoSndBuf();
267+
268+
int getSoRcvBuf();
269+
260270
boolean isUsePooledMemory();
261271

262272
interface AdditionalChannelInitializer {

client/src/main/java/org/asynchttpclient/DefaultAsyncHttpClientConfig.java

Lines changed: 90 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -119,6 +119,11 @@ public class DefaultAsyncHttpClientConfig implements AsyncHttpClientConfig {
119119
private final EventLoopGroup eventLoopGroup;
120120
private final boolean useNativeTransport;
121121
private final boolean usePooledMemory;
122+
private final boolean tcpNoDelay;
123+
private final boolean soReuseAddress;
124+
private final int soLinger;
125+
private final int soSndBuf;
126+
private final int soRcvBuf;
122127
private final Timer nettyTimer;
123128
private final ThreadFactory threadFactory;
124129
private final AdditionalChannelInitializer httpAdditionalChannelInitializer;
@@ -172,6 +177,13 @@ private DefaultAsyncHttpClientConfig(//
172177
List<ResponseFilter> responseFilters,//
173178
List<IOExceptionFilter> ioExceptionFilters,//
174179

180+
// tuning
181+
boolean tcpNoDelay,//
182+
boolean soReuseAddress,//
183+
int soLinger, //
184+
int soSndBuf, //
185+
int soRcvBuf, //
186+
175187
// internals
176188
String threadPoolName,//
177189
int httpClientCodecMaxInitialLineLength,//
@@ -236,6 +248,13 @@ private DefaultAsyncHttpClientConfig(//
236248
this.responseFilters = responseFilters;
237249
this.ioExceptionFilters = ioExceptionFilters;
238250

251+
// tuning
252+
this.tcpNoDelay = tcpNoDelay;
253+
this.soReuseAddress = soReuseAddress;
254+
this.soLinger = soLinger;
255+
this.soSndBuf = soSndBuf;
256+
this.soRcvBuf = soRcvBuf;
257+
239258
// internals
240259
this.threadPoolName = threadPoolName;
241260
this.httpClientCodecMaxInitialLineLength = httpClientCodecMaxInitialLineLength;
@@ -446,6 +465,32 @@ public List<IOExceptionFilter> getIoExceptionFilters() {
446465
return ioExceptionFilters;
447466
}
448467

468+
// tuning
469+
@Override
470+
public boolean isTcpNoDelay() {
471+
return tcpNoDelay;
472+
}
473+
474+
@Override
475+
public boolean isSoReuseAddress() {
476+
return soReuseAddress;
477+
}
478+
479+
@Override
480+
public int getSoLinger() {
481+
return soLinger;
482+
}
483+
484+
@Override
485+
public int getSoSndBuf() {
486+
return soSndBuf;
487+
}
488+
489+
@Override
490+
public int getSoRcvBuf() {
491+
return soRcvBuf;
492+
}
493+
449494
// internals
450495
@Override
451496
public String getThreadPoolName() {
@@ -580,6 +625,13 @@ public static class Builder {
580625
private final List<ResponseFilter> responseFilters = new LinkedList<>();
581626
private final List<IOExceptionFilter> ioExceptionFilters = new LinkedList<>();
582627

628+
// tuning
629+
private boolean tcpNoDelay = defaultTcpNoDelay();
630+
private boolean soReuseAddress = defaultSoReuseAddress();
631+
private int soLinger = defaultSoLinger();
632+
private int soSndBuf = defaultSoSndBuf();
633+
private int soRcvBuf = defaultSoRcvBuf();
634+
583635
// internals
584636
private String threadPoolName = defaultThreadPoolName();
585637
private int httpClientCodecMaxInitialLineLength = defaultHttpClientCodecMaxInitialLineLength();
@@ -646,6 +698,13 @@ public Builder(AsyncHttpClientConfig config) {
646698
responseFilters.addAll(config.getResponseFilters());
647699
ioExceptionFilters.addAll(config.getIoExceptionFilters());
648700

701+
// tuning
702+
tcpNoDelay = config.isTcpNoDelay();
703+
soReuseAddress = config.isSoReuseAddress();
704+
soLinger = config.getSoLinger();
705+
soSndBuf = config.getSoSndBuf();
706+
soRcvBuf = config.getSoRcvBuf();
707+
649708
// internals
650709
threadPoolName = config.getThreadPoolName();
651710
httpClientCodecMaxInitialLineLength = config.getHttpClientCodecMaxInitialLineLength();
@@ -890,6 +949,32 @@ public Builder removeIOExceptionFilter(IOExceptionFilter ioExceptionFilter) {
890949
return this;
891950
}
892951

952+
// tuning
953+
public Builder setTcpNoDelay(boolean tcpNoDelay) {
954+
this.tcpNoDelay = tcpNoDelay;
955+
return this;
956+
}
957+
958+
public Builder setSoReuseAddress(boolean soReuseAddress) {
959+
this.soReuseAddress = soReuseAddress;
960+
return this;
961+
}
962+
963+
public Builder setSoLinger(int soLinger) {
964+
this.soLinger = soLinger;
965+
return this;
966+
}
967+
968+
public Builder setSoSndBuf(int soSndBuf) {
969+
this.soSndBuf = soSndBuf;
970+
return this;
971+
}
972+
973+
public Builder setSoRcvBuf(int soRcvBuf) {
974+
this.soRcvBuf = soRcvBuf;
975+
return this;
976+
}
977+
893978
// internals
894979
public Builder setThreadPoolName(String threadPoolName) {
895980
this.threadPoolName = threadPoolName;
@@ -1024,6 +1109,11 @@ public DefaultAsyncHttpClientConfig build() {
10241109
requestFilters.isEmpty() ? Collections.emptyList() : Collections.unmodifiableList(requestFilters), //
10251110
responseFilters.isEmpty() ? Collections.emptyList() : Collections.unmodifiableList(responseFilters),//
10261111
ioExceptionFilters.isEmpty() ? Collections.emptyList() : Collections.unmodifiableList(ioExceptionFilters),//
1112+
tcpNoDelay, //
1113+
soReuseAddress, //
1114+
soLinger, //
1115+
soSndBuf, //
1116+
soRcvBuf, //
10271117
threadPoolName, //
10281118
httpClientCodecMaxInitialLineLength, //
10291119
httpClientCodecMaxHeaderSize, //

client/src/main/java/org/asynchttpclient/config/AsyncHttpClientConfigDefaults.java

Lines changed: 20 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -115,6 +115,26 @@ public static int defaultSslSessionTimeout() {
115115
return AsyncHttpClientConfigHelper.getAsyncHttpClientConfig().getInt(ASYNC_CLIENT_CONFIG_ROOT + "sslSessionTimeout");
116116
}
117117

118+
public static boolean defaultTcpNoDelay() {
119+
return AsyncHttpClientConfigHelper.getAsyncHttpClientConfig().getBoolean(ASYNC_CLIENT_CONFIG_ROOT + "tcpNoDelay");
120+
}
121+
122+
public static boolean defaultSoReuseAddress() {
123+
return AsyncHttpClientConfigHelper.getAsyncHttpClientConfig().getBoolean(ASYNC_CLIENT_CONFIG_ROOT + "soReuseAddress");
124+
}
125+
126+
public static int defaultSoLinger() {
127+
return AsyncHttpClientConfigHelper.getAsyncHttpClientConfig().getInt(ASYNC_CLIENT_CONFIG_ROOT + "soLinger");
128+
}
129+
130+
public static int defaultSoSndBuf() {
131+
return AsyncHttpClientConfigHelper.getAsyncHttpClientConfig().getInt(ASYNC_CLIENT_CONFIG_ROOT + "soSndBuf");
132+
}
133+
134+
public static int defaultSoRcvBuf() {
135+
return AsyncHttpClientConfigHelper.getAsyncHttpClientConfig().getInt(ASYNC_CLIENT_CONFIG_ROOT + "soRcvBuf");
136+
}
137+
118138
public static int defaultHttpClientCodecMaxInitialLineLength() {
119139
return AsyncHttpClientConfigHelper.getAsyncHttpClientConfig().getInt(ASYNC_CLIENT_CONFIG_ROOT + "httpClientCodecMaxInitialLineLength");
120140
}

client/src/main/java/org/asynchttpclient/netty/channel/ChannelManager.java

Lines changed: 14 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -197,13 +197,26 @@ private Bootstrap newBootstrap(Class<? extends Channel> socketChannelClass, Even
197197
Bootstrap bootstrap = new Bootstrap().channel(socketChannelClass).group(eventLoopGroup)//
198198
// default to PooledByteBufAllocator
199199
.option(ChannelOption.ALLOCATOR, config.isUsePooledMemory() ? PooledByteBufAllocator.DEFAULT : UnpooledByteBufAllocator.DEFAULT)//
200-
.option(ChannelOption.TCP_NODELAY, true)//
200+
.option(ChannelOption.TCP_NODELAY, config.isTcpNoDelay())//
201+
.option(ChannelOption.SO_REUSEADDR, config.isSoReuseAddress())//
201202
.option(ChannelOption.AUTO_CLOSE, false);
202203

203204
if (config.getConnectTimeout() > 0) {
204205
bootstrap.option(ChannelOption.CONNECT_TIMEOUT_MILLIS, config.getConnectTimeout());
205206
}
206207

208+
if (config.getSoLinger() >= 0) {
209+
bootstrap.option(ChannelOption.SO_LINGER, config.getSoLinger());
210+
}
211+
212+
if (config.getSoSndBuf() >= 0) {
213+
bootstrap.option(ChannelOption.SO_SNDBUF, config.getSoSndBuf());
214+
}
215+
216+
if (config.getSoRcvBuf() >= 0) {
217+
bootstrap.option(ChannelOption.SO_RCVBUF, config.getSoRcvBuf());
218+
}
219+
207220
for (Entry<ChannelOption<Object>, Object> entry : config.getChannelOptions().entrySet()) {
208221
bootstrap.option(entry.getKey(), entry.getValue());
209222
}

client/src/main/resources/ahc-default.properties

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -24,6 +24,11 @@ org.asynchttpclient.useOpenSsl=false
2424
org.asynchttpclient.acceptAnyCertificate=false
2525
org.asynchttpclient.sslSessionCacheSize=0
2626
org.asynchttpclient.sslSessionTimeout=0
27+
org.asynchttpclient.tcpNoDelay=true
28+
org.asynchttpclient.soReuseAddress=false
29+
org.asynchttpclient.soLinger=-1
30+
org.asynchttpclient.soSndBuf=-1
31+
org.asynchttpclient.soRcvBuf=-1
2732
org.asynchttpclient.httpClientCodecMaxInitialLineLength=4096
2833
org.asynchttpclient.httpClientCodecMaxHeaderSize=8192
2934
org.asynchttpclient.httpClientCodecMaxChunkSize=8192

0 commit comments

Comments
 (0)