< prev index next >
1 /*
2 * Copyright (c) 2015, 2016, Oracle and/or its affiliates. All rights reserved.
3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
4 *
5 * This code is free software; you can redistribute it and/or modify it
6 * under the terms of the GNU General Public License version 2 only, as
7 * published by the Free Software Foundation. Oracle designates this
8 * particular file as subject to the "Classpath" exception as provided
9 * by Oracle in the LICENSE file that accompanied this code.
10 *
11 * This code is distributed in the hope that it will be useful, but WITHOUT
12 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
13 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
14 * version 2 for more details (a copy is included in the LICENSE file that
15 * accompanied this code).
16 *
17 * You should have received a copy of the GNU General Public License version
18 * 2 along with this work; if not, write to the Free Software Foundation,
19 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
20 *
21 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
22 * or visit www.oracle.com if you need additional information or have any
23 * questions.
24 */
25 package java.net.http;
26
27 import java.io.IOException;
28 import java.net.InetSocketAddress;
29 import java.nio.ByteBuffer;
30 import java.nio.channels.SocketChannel;
31 import java.security.AccessControlContext;
32 import java.util.concurrent.CompletableFuture;
33
34 /**
35 * A plain text socket tunnel through a proxy. Uses "CONNECT" but does not
36 * encrypt. Used by WebSockets. Subclassed in SSLTunnelConnection for encryption.
37 */
38 class PlainTunnelingConnection extends HttpConnection {
39
40 final PlainHttpConnection delegate;
41 protected final InetSocketAddress proxyAddr;
42 private volatile boolean connected;
43 private final AccessControlContext acc;
44
45 @Override
46 public CompletableFuture<Void> connectAsync() {
47 return delegate.connectAsync()
48 .thenCompose((Void v) -> {
49 HttpRequestImpl req = new HttpRequestImpl(client, "CONNECT", address);
50 Exchange connectExchange = new Exchange(req, acc);
51 return connectExchange
52 .responseAsyncImpl(delegate)
53 .thenCompose((HttpResponse r) -> {
54 CompletableFuture<Void> cf = new CompletableFuture<>();
55 if (r.statusCode() != 200) {
56 cf.completeExceptionally(new IOException("Tunnel failed"));
57 } else {
58 connected = true;
59 cf.complete(null);
60 }
61 return cf;
62 });
63 });
64 }
65
66 @Override
67 public void connect() throws IOException, InterruptedException {
68 delegate.connect();
69 HttpRequestImpl req = new HttpRequestImpl(client, "CONNECT", address);
70 Exchange connectExchange = new Exchange(req, acc);
71 HttpResponse r = connectExchange.responseImpl(delegate);
72 if (r.statusCode() != 200) {
73 throw new IOException("Tunnel failed");
74 }
75 connected = true;
76 }
77
78 @Override
79 boolean connected() {
80 return connected;
81 }
82
83 protected PlainTunnelingConnection(InetSocketAddress addr,
84 InetSocketAddress proxy,
85 HttpClientImpl client,
86 AccessControlContext acc) {
87 super(addr, client);
88 this.proxyAddr = proxy;
89 this.acc = acc;
90 delegate = new PlainHttpConnection(proxy, client);
91 }
92
93 @Override
94 SocketChannel channel() {
95 return delegate.channel();
96 }
97
98 @Override
99 ConnectionPool.CacheKey cacheKey() {
100 return new ConnectionPool.CacheKey(null, proxyAddr);
101 }
102
103 @Override
104 long write(ByteBuffer[] buffers, int start, int number) throws IOException {
105 return delegate.write(buffers, start, number);
106 }
107
108 @Override
109 long write(ByteBuffer buffer) throws IOException {
110 return delegate.write(buffer);
111 }
112
113 @Override
114 public void close() {
115 delegate.close();
116 connected = false;
117 }
118
119 @Override
120 protected ByteBuffer readImpl(int length) throws IOException {
121 return delegate.readImpl(length);
122 }
123
124 @Override
125 CompletableFuture<Void> whenReceivingResponse() {
126 return delegate.whenReceivingResponse();
127 }
128
129 @Override
130 protected int readImpl(ByteBuffer buffer) throws IOException {
131 return delegate.readImpl(buffer);
132 }
133
134 @Override
135 boolean isSecure() {
136 return false;
137 }
138
139 @Override
140 boolean isProxied() {
141 return true;
142 }
143 }
< prev index next >