1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28 package org.apache.hc.client5.http.impl.nio;
29
30 import java.io.IOException;
31 import java.net.SocketAddress;
32 import java.util.concurrent.atomic.AtomicBoolean;
33
34 import javax.net.ssl.SSLContext;
35 import javax.net.ssl.SSLSession;
36
37 import org.apache.hc.client5.http.nio.ManagedAsyncClientConnection;
38 import org.apache.hc.core5.http.EndpointDetails;
39 import org.apache.hc.core5.http.HttpConnection;
40 import org.apache.hc.core5.http.HttpVersion;
41 import org.apache.hc.core5.http.ProtocolVersion;
42 import org.apache.hc.core5.http.nio.command.ShutdownCommand;
43 import org.apache.hc.core5.io.CloseMode;
44 import org.apache.hc.core5.net.NamedEndpoint;
45 import org.apache.hc.core5.reactor.Command;
46 import org.apache.hc.core5.reactor.IOEventHandler;
47 import org.apache.hc.core5.reactor.IOSession;
48 import org.apache.hc.core5.reactor.ssl.SSLBufferMode;
49 import org.apache.hc.core5.reactor.ssl.SSLSessionInitializer;
50 import org.apache.hc.core5.reactor.ssl.SSLSessionVerifier;
51 import org.apache.hc.core5.reactor.ssl.TlsDetails;
52 import org.apache.hc.core5.reactor.ssl.TransportSecurityLayer;
53 import org.apache.hc.core5.util.Identifiable;
54 import org.apache.hc.core5.util.Timeout;
55 import org.slf4j.Logger;
56 import org.slf4j.LoggerFactory;
57
58 final class DefaultManagedAsyncClientConnection implements ManagedAsyncClientConnection, Identifiable {
59
60 private static final Logger LOG = LoggerFactory.getLogger(DefaultManagedAsyncClientConnection.class);
61
62 private final IOSession ioSession;
63 private final Timeout socketTimeout;
64 private final AtomicBoolean closed;
65
66 public DefaultManagedAsyncClientConnection(final IOSession ioSession) {
67 this.ioSession = ioSession;
68 this.socketTimeout = ioSession.getSocketTimeout();
69 this.closed = new AtomicBoolean();
70 }
71
72 @Override
73 public String getId() {
74 return ioSession.getId();
75 }
76
77 @Override
78 public void close(final CloseMode closeMode) {
79 if (this.closed.compareAndSet(false, true)) {
80 if (LOG.isDebugEnabled()) {
81 LOG.debug("{}: Shutdown connection {}", getId(), closeMode);
82 }
83 ioSession.close(closeMode);
84 }
85 }
86
87 @Override
88 public void close() throws IOException {
89 if (this.closed.compareAndSet(false, true)) {
90 if (LOG.isDebugEnabled()) {
91 LOG.debug("{}: Close connection", getId());
92 }
93 ioSession.enqueue(new ShutdownCommand(CloseMode.GRACEFUL), Command.Priority.IMMEDIATE);
94 }
95 }
96
97 @Override
98 public boolean isOpen() {
99 return ioSession.isOpen();
100 }
101
102 @Override
103 public void setSocketTimeout(final Timeout timeout) {
104 ioSession.setSocketTimeout(timeout);
105 }
106
107 @Override
108 public Timeout getSocketTimeout() {
109 return ioSession.getSocketTimeout();
110 }
111
112 @Override
113 public SocketAddress getRemoteAddress() {
114 return ioSession.getRemoteAddress();
115 }
116
117 @Override
118 public SocketAddress getLocalAddress() {
119 return ioSession.getLocalAddress();
120 }
121
122 @Override
123 public EndpointDetails getEndpointDetails() {
124 final IOEventHandler handler = ioSession.getHandler();
125 if (handler instanceof HttpConnection) {
126 return ((HttpConnection) handler).getEndpointDetails();
127 }
128 return null;
129 }
130
131 @Override
132 public ProtocolVersion getProtocolVersion() {
133 final IOEventHandler handler = ioSession.getHandler();
134 if (handler instanceof HttpConnection) {
135 return ((HttpConnection) handler).getProtocolVersion();
136 }
137 return HttpVersion.DEFAULT;
138 }
139
140 @Override
141 public void startTls(
142 final SSLContext sslContext,
143 final NamedEndpoint endpoint,
144 final SSLBufferMode sslBufferMode,
145 final SSLSessionInitializer initializer,
146 final SSLSessionVerifier verifier,
147 final Timeout handshakeTimeout) throws UnsupportedOperationException {
148 if (LOG.isDebugEnabled()) {
149 LOG.debug("{}: start TLS", getId());
150 }
151 if (ioSession instanceof TransportSecurityLayer) {
152 ((TransportSecurityLayer) ioSession).startTls(sslContext, endpoint, sslBufferMode, initializer, verifier,
153 handshakeTimeout);
154 } else {
155 throw new UnsupportedOperationException("TLS upgrade not supported");
156 }
157 }
158
159 @Override
160 public TlsDetails getTlsDetails() {
161 return ioSession instanceof TransportSecurityLayer ? ((TransportSecurityLayer) ioSession).getTlsDetails() : null;
162 }
163
164 @Override
165 public SSLSession getSSLSession() {
166 final TlsDetails tlsDetails = getTlsDetails();
167 return tlsDetails != null ? tlsDetails.getSSLSession() : null;
168 }
169
170 @Override
171 public void submitCommand(final Command command, final Command.Priority priority) {
172 if (LOG.isDebugEnabled()) {
173 LOG.debug("{}: {} with {} priority", getId(), command.getClass().getSimpleName(), priority);
174 }
175 ioSession.enqueue(command, Command.Priority.IMMEDIATE);
176 }
177
178 @Override
179 public void passivate() {
180 ioSession.setSocketTimeout(Timeout.ZERO_MILLISECONDS);
181 }
182
183 @Override
184 public void activate() {
185 ioSession.setSocketTimeout(socketTimeout);
186 }
187
188 }