View Javadoc

1   /*
2    * ====================================================================
3    * Licensed to the Apache Software Foundation (ASF) under one
4    * or more contributor license agreements.  See the NOTICE file
5    * distributed with this work for additional information
6    * regarding copyright ownership.  The ASF licenses this file
7    * to you under the Apache License, Version 2.0 (the
8    * "License"); you may not use this file except in compliance
9    * with the License.  You may obtain a copy of the License at
10   *
11   *   http://www.apache.org/licenses/LICENSE-2.0
12   *
13   * Unless required by applicable law or agreed to in writing,
14   * software distributed under the License is distributed on an
15   * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
16   * KIND, either express or implied.  See the License for the
17   * specific language governing permissions and limitations
18   * under the License.
19   * ====================================================================
20   *
21   * This software consists of voluntary contributions made by many
22   * individuals on behalf of the Apache Software Foundation.  For more
23   * information on the Apache Software Foundation, please see
24   * <http://www.apache.org/>.
25   *
26   */
27  
28  package org.apache.http.impl.nio.reactor;
29  
30  import java.net.SocketOptions;
31  import java.nio.channels.SelectionKey;
32  
33  import org.apache.http.annotation.NotThreadSafe;
34  import org.apache.http.util.Args;
35  
36  /**
37   * I/O reactor configuration parameters.
38   *
39   * @since 4.2
40   */
41  @NotThreadSafe
42  public final class IOReactorConfig implements Cloneable {
43  
44      private static final int AVAIL_PROCS = Runtime.getRuntime().availableProcessors();
45  
46      public static final IOReactorConfig DEFAULT = new Builder().build();
47  
48      // TODO: make final
49      private long selectInterval;
50      private long shutdownGracePeriod;
51      private boolean interestOpQueued;
52      private int ioThreadCount;
53      private int soTimeout;
54      private boolean soReuseAddress;
55      private int soLinger;
56      private boolean soKeepAlive;
57      private boolean tcpNoDelay;
58      private int connectTimeout;
59      private int sndBufSize;
60      private int rcvBufSize;
61  
62      @Deprecated
63      public IOReactorConfig() {
64          super();
65          this.selectInterval = 1000;
66          this.shutdownGracePeriod = 500;
67          this.interestOpQueued = false;
68          this.ioThreadCount = AVAIL_PROCS;
69          this.soTimeout = 0;
70          this.soReuseAddress = false;
71          this.soLinger = -1;
72          this.soKeepAlive = false;
73          this.tcpNoDelay = true;
74          this.connectTimeout = 0;
75          this.sndBufSize = 0;
76          this.rcvBufSize = 0;
77      }
78  
79      IOReactorConfig(
80              final long selectInterval,
81              final long shutdownGracePeriod,
82              final boolean interestOpQueued,
83              final int ioThreadCount,
84              final int soTimeout,
85              final boolean soReuseAddress,
86              final int soLinger,
87              final boolean soKeepAlive,
88              final boolean tcpNoDelay,
89              final int connectTimeout,
90              final int sndBufSize,
91              final int rcvBufSize) {
92          super();
93          this.selectInterval = selectInterval;
94          this.shutdownGracePeriod = shutdownGracePeriod;
95          this.interestOpQueued = interestOpQueued;
96          this.ioThreadCount = ioThreadCount;
97          this.soTimeout = soTimeout;
98          this.soReuseAddress = soReuseAddress;
99          this.soLinger = soLinger;
100         this.soKeepAlive = soKeepAlive;
101         this.tcpNoDelay = tcpNoDelay;
102         this.connectTimeout = connectTimeout;
103         this.sndBufSize = sndBufSize;
104         this.rcvBufSize = rcvBufSize;
105     }
106 
107     /**
108      * Determines time interval in milliseconds at which the I/O reactor wakes up to check for
109      * timed out sessions and session requests.
110      * <p/>
111      * Default: <code>1000</code> milliseconds.
112      */
113     public long getSelectInterval() {
114         return this.selectInterval;
115     }
116 
117     /**
118      * @deprecated (4.3) use {@link Builder#setSelectInterval(long)}
119      */
120     @Deprecated
121     public void setSelectInterval(final long selectInterval) {
122         Args.positive(selectInterval, "Select internal");
123         this.selectInterval = selectInterval;
124     }
125 
126     /**
127      * Determines grace period in milliseconds the I/O reactors are expected to block waiting
128      * for individual worker threads to terminate cleanly.
129      * <p/>
130      * Default: <code>500</code> milliseconds.
131      */
132     public long getShutdownGracePeriod() {
133         return this.shutdownGracePeriod;
134     }
135 
136     /**
137      * @deprecated (4.3) use {@link Builder#setShutdownGracePeriod(long)}
138      */
139     @Deprecated
140     public void setShutdownGracePeriod(final long gracePeriod) {
141         Args.positive(gracePeriod, "Shutdown grace period");
142         this.shutdownGracePeriod = gracePeriod;
143     }
144 
145     /**
146      * Determines whether or not I/O interest operations are to be queued and executed
147      * asynchronously by the I/O reactor thread or to be applied to the underlying
148      * {@link SelectionKey} immediately.
149      * <p/>
150      * Default: <code>false</code>
151      *
152      * @see SelectionKey
153      * @see SelectionKey#interestOps()
154      * @see SelectionKey#interestOps(int)
155      */
156     public boolean isInterestOpQueued() {
157         return this.interestOpQueued;
158     }
159 
160     /**
161      * @deprecated (4.3) use {@link Builder#setInterestOpQueued(boolean)}
162      */
163     @Deprecated
164     public void setInterestOpQueued(final boolean interestOpQueued) {
165         this.interestOpQueued = interestOpQueued;
166     }
167 
168     /**
169      * Determines the number of I/O dispatch threads to be used by the I/O reactor.
170      * <p/>
171      * Default: <code>2</code>
172      */
173     public int getIoThreadCount() {
174         return this.ioThreadCount;
175     }
176 
177     /**
178      * @deprecated (4.3) use {@link Builder#setIoThreadCount(int)}
179      */
180     @Deprecated
181     public void setIoThreadCount(final int ioThreadCount) {
182         Args.positive(ioThreadCount, "I/O thread count");
183         this.ioThreadCount = ioThreadCount;
184     }
185 
186     /**
187      * Determines the default socket timeout value for non-blocking I/O operations.
188      * <p/>
189      * Default: <code>0</code> (no timeout)
190      *
191      * @see SocketOptions#SO_TIMEOUT
192      */
193     public int getSoTimeout() {
194         return soTimeout;
195     }
196 
197     /**
198      * @deprecated (4.3) use {@link Builder#setSoTimeout(int)}
199      */
200     @Deprecated
201     public void setSoTimeout(final int soTimeout) {
202         this.soTimeout = soTimeout;
203     }
204 
205     /**
206      * Determines the default value of the {@link SocketOptions#SO_REUSEADDR} parameter
207      * for newly created sockets.
208      * <p/>
209      * Default: <code>false</code>
210      *
211      * @see SocketOptions#SO_REUSEADDR
212      */
213     public boolean isSoReuseAddress() {
214         return soReuseAddress;
215     }
216 
217     /**
218      * @deprecated (4.3) use {@link Builder#setSoReuseAddress(boolean)}
219      */
220     @Deprecated
221     public void setSoReuseAddress(final boolean soReuseAddress) {
222         this.soReuseAddress = soReuseAddress;
223     }
224 
225     /**
226      * Determines the default value of the {@link SocketOptions#SO_LINGER} parameter
227      * for newly created sockets.
228      * <p/>
229      * Default: <code>-1</code>
230      *
231      * @see SocketOptions#SO_LINGER
232      */
233     public int getSoLinger() {
234         return soLinger;
235     }
236 
237     /**
238      * @deprecated (4.3) use {@link Builder#setSoLinger(int)}
239      */
240     @Deprecated
241     public void setSoLinger(final int soLinger) {
242         this.soLinger = soLinger;
243     }
244 
245     /**
246      * Determines the default value of the {@link SocketOptions#SO_KEEPALIVE} parameter
247      * for newly created sockets.
248      * <p/>
249      * Default: <code>-1</code>
250      *
251      * @see SocketOptions#SO_KEEPALIVE
252      */
253     public boolean isSoKeepalive() {
254         return this.soKeepAlive;
255     }
256 
257     /**
258      * @deprecated (4.3) use {@link Builder#setSoKeepAlive(boolean)}
259      */
260     @Deprecated
261     public void setSoKeepalive(final boolean soKeepAlive) {
262         this.soKeepAlive = soKeepAlive;
263     }
264 
265     /**
266      * Determines the default value of the {@link SocketOptions#TCP_NODELAY} parameter
267      * for newly created sockets.
268      * <p/>
269      * Default: <code>false</code>
270      *
271      * @see SocketOptions#TCP_NODELAY
272      */
273     public boolean isTcpNoDelay() {
274         return tcpNoDelay;
275     }
276 
277     /**
278      * @deprecated (4.3) use {@link Builder#setTcpNoDelay(boolean)}
279      */
280     @Deprecated
281     public void setTcpNoDelay(final boolean tcpNoDelay) {
282         this.tcpNoDelay = tcpNoDelay;
283     }
284 
285     /**
286      * Determines the default connect timeout value for non-blocking connection requests.
287      * <p/>
288      * Default: <code>0</code> (no timeout)
289      */
290     public int getConnectTimeout() {
291         return connectTimeout;
292     }
293 
294     /**
295      * @deprecated (4.3) use {@link Builder#setConnectTimeout(int)}
296      */
297     @Deprecated
298     public void setConnectTimeout(final int connectTimeout) {
299         this.connectTimeout = connectTimeout;
300     }
301 
302     /**
303      * Determines the default value of the {@link SocketOptions#SO_SNDBUF} parameter
304      * for newly created sockets.
305      * <p/>
306      * Default: <code>0</code> (system default)
307      *
308      * @see SocketOptions#SO_SNDBUF
309      */
310     public int getSndBufSize() {
311         return sndBufSize;
312     }
313 
314     /**
315      * @deprecated (4.3) use {@link Builder#setSndBufSize(int)}
316      */
317     @Deprecated
318     public void setSndBufSize(final int sndBufSize) {
319         this.sndBufSize = sndBufSize;
320     }
321 
322     /**
323      * Determines the default value of the {@link SocketOptions#SO_RCVBUF} parameter
324      * for newly created sockets.
325      * <p/>
326      * Default: <code>0</code> (system default)
327      *
328      * @see SocketOptions#SO_RCVBUF
329      */
330     public int getRcvBufSize() {
331         return rcvBufSize;
332     }
333 
334     /**
335      * @deprecated (4.3) use {@link Builder#setRcvBufSize(int)}
336      */
337     @Deprecated
338     public void setRcvBufSize(final int rcvBufSize) {
339         this.rcvBufSize = rcvBufSize;
340     }
341 
342     @Override
343     protected IOReactorConfig clone() throws CloneNotSupportedException {
344         return (IOReactorConfig) super.clone();
345     }
346 
347     public static Builder custom() {
348         return new Builder();
349     }
350 
351     public static Builder copy(final IOReactorConfig config) {
352         Args.notNull(config, "I/O reactor config");
353         return new Builder()
354             .setSelectInterval(config.getSelectInterval())
355             .setShutdownGracePeriod(config.getShutdownGracePeriod())
356             .setInterestOpQueued(config.isInterestOpQueued())
357             .setIoThreadCount(config.getIoThreadCount())
358             .setSoTimeout(config.getSoTimeout())
359             .setSoReuseAddress(config.isSoReuseAddress())
360             .setSoLinger(config.getSoLinger())
361             .setSoKeepAlive(config.isSoKeepalive())
362             .setTcpNoDelay(config.isTcpNoDelay())
363             .setConnectTimeout(config.getConnectTimeout());
364     }
365 
366     public static class Builder {
367 
368         private long selectInterval;
369         private long shutdownGracePeriod;
370         private boolean interestOpQueued;
371         private int ioThreadCount;
372         private int soTimeout;
373         private boolean soReuseAddress;
374         private int soLinger;
375         private boolean soKeepAlive;
376         private boolean tcpNoDelay;
377         private int connectTimeout;
378         private int sndBufSize;
379         private int rcvBufSize;
380 
381         Builder() {
382             this.selectInterval = 1000;
383             this.shutdownGracePeriod = 500;
384             this.interestOpQueued = false;
385             this.ioThreadCount = AVAIL_PROCS;
386             this.soTimeout = 0;
387             this.soReuseAddress = false;
388             this.soLinger = -1;
389             this.soKeepAlive = false;
390             this.tcpNoDelay = true;
391             this.connectTimeout = 0;
392             this.sndBufSize = 0;
393             this.rcvBufSize = 0;
394         }
395 
396         public Builder setSelectInterval(final long selectInterval) {
397             this.selectInterval = selectInterval;
398             return this;
399         }
400 
401         public Builder setShutdownGracePeriod(final long shutdownGracePeriod) {
402             this.shutdownGracePeriod = shutdownGracePeriod;
403             return this;
404         }
405 
406         public Builder setInterestOpQueued(final boolean interestOpQueued) {
407             this.interestOpQueued = interestOpQueued;
408             return this;
409         }
410 
411         public Builder setIoThreadCount(final int ioThreadCount) {
412             this.ioThreadCount = ioThreadCount;
413             return this;
414         }
415 
416         public Builder setSoTimeout(final int soTimeout) {
417             this.soTimeout = soTimeout;
418             return this;
419         }
420 
421         public Builder setSoReuseAddress(final boolean soReuseAddress) {
422             this.soReuseAddress = soReuseAddress;
423             return this;
424         }
425 
426         public Builder setSoLinger(final int soLinger) {
427             this.soLinger = soLinger;
428             return this;
429         }
430 
431         public Builder setSoKeepAlive(final boolean soKeepAlive) {
432             this.soKeepAlive = soKeepAlive;
433             return this;
434         }
435 
436         public Builder setTcpNoDelay(final boolean tcpNoDelay) {
437             this.tcpNoDelay = tcpNoDelay;
438             return this;
439         }
440 
441         public Builder setConnectTimeout(final int connectTimeout) {
442             this.connectTimeout = connectTimeout;
443             return this;
444         }
445 
446         public Builder setSndBufSize(final int sndBufSize) {
447             this.sndBufSize = sndBufSize;
448             return this;
449         }
450 
451         public Builder setRcvBufSize(final int rcvBufSize) {
452             this.rcvBufSize = rcvBufSize;
453             return this;
454         }
455 
456         public IOReactorConfig build() {
457             return new IOReactorConfig(
458                     selectInterval, shutdownGracePeriod, interestOpQueued, ioThreadCount,
459                     soTimeout, soReuseAddress, soLinger, soKeepAlive, tcpNoDelay,
460                     connectTimeout, sndBufSize, rcvBufSize);
461         }
462 
463     }
464 
465     @Override
466     public String toString() {
467         final StringBuilder builder = new StringBuilder();
468         builder.append("[selectInterval=").append(this.selectInterval)
469                 .append(", shutdownGracePeriod=").append(this.shutdownGracePeriod)
470                 .append(", interestOpQueued=").append(this.interestOpQueued)
471                 .append(", ioThreadCount=").append(this.ioThreadCount)
472                 .append(", soTimeout=").append(this.soTimeout)
473                 .append(", soReuseAddress=").append(this.soReuseAddress)
474                 .append(", soLinger=").append(this.soLinger)
475                 .append(", soKeepAlive=").append(this.soKeepAlive)
476                 .append(", tcpNoDelay=").append(this.tcpNoDelay)
477                 .append(", connectTimeout=").append(this.connectTimeout)
478                 .append(", sndBufSize=").append(this.sndBufSize)
479                 .append(", rcvBufSize=").append(this.rcvBufSize)
480                 .append("]");
481         return builder.toString();
482     }
483 
484 }