use of java.nio.channels.SocketChannel in project jetty.project by eclipse.
the class ConnectHandlerTest method testCONNECTAndPOSTWithContext.
@Test
public void testCONNECTAndPOSTWithContext() throws Exception {
final String contextKey = "contextKey";
final String contextValue = "contextValue";
// Replace the default ProxyHandler with a subclass to test context information passing
disposeProxy();
proxy.setHandler(new ConnectHandler() {
@Override
protected boolean handleAuthentication(HttpServletRequest request, HttpServletResponse response, String address) {
request.setAttribute(contextKey, contextValue);
return super.handleAuthentication(request, response, address);
}
@Override
protected void connectToServer(HttpServletRequest request, String host, int port, Promise<SocketChannel> promise) {
Assert.assertEquals(contextValue, request.getAttribute(contextKey));
super.connectToServer(request, host, port, promise);
}
@Override
protected void prepareContext(HttpServletRequest request, ConcurrentMap<String, Object> context) {
// Transfer data from the HTTP request to the connection context
Assert.assertEquals(contextValue, request.getAttribute(contextKey));
context.put(contextKey, request.getAttribute(contextKey));
}
@Override
protected int read(EndPoint endPoint, ByteBuffer buffer, ConcurrentMap<String, Object> context) throws IOException {
Assert.assertEquals(contextValue, context.get(contextKey));
return super.read(endPoint, buffer, context);
}
@Override
protected void write(EndPoint endPoint, ByteBuffer buffer, Callback callback, ConcurrentMap<String, Object> context) {
Assert.assertEquals(contextValue, context.get(contextKey));
super.write(endPoint, buffer, callback, context);
}
});
proxy.start();
String hostPort = "localhost:" + serverConnector.getLocalPort();
String request = "" + "CONNECT " + hostPort + " HTTP/1.1\r\n" + "Host: " + hostPort + "\r\n" + "\r\n";
try (Socket socket = newSocket()) {
OutputStream output = socket.getOutputStream();
InputStream input = socket.getInputStream();
output.write(request.getBytes(StandardCharsets.UTF_8));
output.flush();
// Expect 200 OK from the CONNECT request
HttpTester.Response response = readResponse(input);
Assert.assertEquals(HttpStatus.OK_200, response.getStatus());
String body = "0123456789ABCDEF";
request = "" + "POST /echo HTTP/1.1\r\n" + "Host: " + hostPort + "\r\n" + "Content-Length: " + body.length() + "\r\n" + "\r\n" + body;
output.write(request.getBytes(StandardCharsets.UTF_8));
output.flush();
response = readResponse(input);
Assert.assertEquals(HttpStatus.OK_200, response.getStatus());
Assert.assertEquals("POST /echo\r\n" + body, response.getContent());
}
}
use of java.nio.channels.SocketChannel in project jetty.project by eclipse.
the class ConnectHandler method connectToServer.
protected void connectToServer(HttpServletRequest request, String host, int port, Promise<SocketChannel> promise) {
SocketChannel channel = null;
try {
channel = SocketChannel.open();
channel.socket().setTcpNoDelay(true);
channel.configureBlocking(false);
InetSocketAddress address = newConnectAddress(host, port);
channel.connect(address);
promise.succeeded(channel);
} catch (Throwable x) {
close(channel);
promise.failed(x);
}
}
use of java.nio.channels.SocketChannel in project jetty.project by eclipse.
the class HttpVersionCustomizerTest method testCustomizeHttpVersion.
@Test
public void testCustomizeHttpVersion() throws Exception {
Server server = new Server();
HttpConfiguration httpConfig = new HttpConfiguration();
httpConfig.addCustomizer((connector, config, request) -> request.setHttpVersion(HttpVersion.HTTP_1_1));
ServerConnector connector = new ServerConnector(server, new HttpConnectionFactory(httpConfig));
server.addConnector(connector);
server.setHandler(new AbstractHandler() {
@Override
public void handle(String target, Request baseRequest, HttpServletRequest request, HttpServletResponse response) throws IOException, ServletException {
baseRequest.setHandled(true);
response.setStatus(500);
Assert.assertEquals(HttpVersion.HTTP_1_1.asString(), request.getProtocol());
response.setStatus(200);
response.getWriter().println("OK");
}
});
server.start();
try {
try (SocketChannel socket = SocketChannel.open(new InetSocketAddress("localhost", connector.getLocalPort()))) {
HttpTester.Request request = HttpTester.newRequest();
request.setVersion(HttpVersion.HTTP_1_0);
socket.write(request.generate());
HttpTester.Response response = HttpTester.parseResponse(HttpTester.from(socket));
Assert.assertNotNull(response);
Assert.assertThat(response.getStatus(), Matchers.equalTo(HttpStatus.OK_200));
}
} finally {
server.stop();
}
}
use of java.nio.channels.SocketChannel in project jetty.project by eclipse.
the class PrefaceTest method testClientPrefaceReplySentAfterServerPreface.
@Test
public void testClientPrefaceReplySentAfterServerPreface() throws Exception {
start(new ServerSessionListener.Adapter() {
@Override
public Map<Integer, Integer> onPreface(Session session) {
Map<Integer, Integer> settings = new HashMap<>();
settings.put(SettingsFrame.MAX_CONCURRENT_STREAMS, 128);
return settings;
}
@Override
public void onPing(Session session, PingFrame frame) {
session.close(ErrorCode.NO_ERROR.code, null, Callback.NOOP);
}
});
ByteBufferPool byteBufferPool = client.getByteBufferPool();
try (SocketChannel socket = SocketChannel.open()) {
socket.connect(new InetSocketAddress("localhost", connector.getLocalPort()));
Generator generator = new Generator(byteBufferPool);
ByteBufferPool.Lease lease = new ByteBufferPool.Lease(byteBufferPool);
generator.control(lease, new PrefaceFrame());
Map<Integer, Integer> clientSettings = new HashMap<>();
clientSettings.put(SettingsFrame.ENABLE_PUSH, 0);
generator.control(lease, new SettingsFrame(clientSettings, false));
// The PING frame just to make sure the client stops reading.
generator.control(lease, new PingFrame(true));
List<ByteBuffer> buffers = lease.getByteBuffers();
socket.write(buffers.toArray(new ByteBuffer[buffers.size()]));
Queue<SettingsFrame> settings = new ArrayDeque<>();
Parser parser = new Parser(byteBufferPool, new Parser.Listener.Adapter() {
@Override
public void onSettings(SettingsFrame frame) {
settings.offer(frame);
}
}, 4096, 8192);
ByteBuffer buffer = byteBufferPool.acquire(1024, true);
while (true) {
BufferUtil.clearToFill(buffer);
int read = socket.read(buffer);
BufferUtil.flipToFlush(buffer, 0);
if (read < 0)
break;
parser.parse(buffer);
}
Assert.assertEquals(2, settings.size());
SettingsFrame frame1 = settings.poll();
Assert.assertFalse(frame1.isReply());
SettingsFrame frame2 = settings.poll();
Assert.assertTrue(frame2.isReply());
}
}
use of java.nio.channels.SocketChannel in project jetty.project by eclipse.
the class PrefaceTest method testOnPrefaceNotifiedForStandardUpgrade.
@Test
public void testOnPrefaceNotifiedForStandardUpgrade() throws Exception {
Integer maxConcurrentStreams = 128;
AtomicReference<CountDownLatch> serverPrefaceLatch = new AtomicReference<>(new CountDownLatch(1));
AtomicReference<CountDownLatch> serverSettingsLatch = new AtomicReference<>(new CountDownLatch(1));
HttpConfiguration config = new HttpConfiguration();
prepareServer(new HttpConnectionFactory(config), new HTTP2CServerConnectionFactory(config) {
@Override
protected ServerSessionListener newSessionListener(Connector connector, EndPoint endPoint) {
return new ServerSessionListener.Adapter() {
@Override
public Map<Integer, Integer> onPreface(Session session) {
Map<Integer, Integer> serverSettings = new HashMap<>();
serverSettings.put(SettingsFrame.MAX_CONCURRENT_STREAMS, maxConcurrentStreams);
serverPrefaceLatch.get().countDown();
return serverSettings;
}
@Override
public void onSettings(Session session, SettingsFrame frame) {
serverSettingsLatch.get().countDown();
}
@Override
public Stream.Listener onNewStream(Stream stream, HeadersFrame frame) {
MetaData.Response response = new MetaData.Response(HttpVersion.HTTP_2, HttpStatus.OK_200, new HttpFields());
stream.headers(new HeadersFrame(stream.getId(), response, null, true), Callback.NOOP);
return null;
}
};
}
});
server.start();
ByteBufferPool byteBufferPool = new MappedByteBufferPool();
try (SocketChannel socket = SocketChannel.open()) {
socket.connect(new InetSocketAddress("localhost", connector.getLocalPort()));
String upgradeRequest = "" + "GET /one HTTP/1.1\r\n" + "Host: localhost\r\n" + "Connection: Upgrade, HTTP2-Settings\r\n" + "Upgrade: h2c\r\n" + "HTTP2-Settings: \r\n" + "\r\n";
ByteBuffer upgradeBuffer = ByteBuffer.wrap(upgradeRequest.getBytes(StandardCharsets.ISO_8859_1));
socket.write(upgradeBuffer);
// Make sure onPreface() is called on server.
Assert.assertTrue(serverPrefaceLatch.get().await(5, TimeUnit.SECONDS));
Assert.assertTrue(serverSettingsLatch.get().await(5, TimeUnit.SECONDS));
// The 101 response is the reply to the client preface SETTINGS frame.
ByteBuffer buffer = byteBufferPool.acquire(1024, true);
http1: while (true) {
BufferUtil.clearToFill(buffer);
int read = socket.read(buffer);
BufferUtil.flipToFlush(buffer, 0);
if (read < 0)
Assert.fail();
int crlfs = 0;
while (buffer.hasRemaining()) {
byte b = buffer.get();
if (b == '\r' || b == '\n')
++crlfs;
else
crlfs = 0;
if (crlfs == 4)
break http1;
}
}
// Reset the latches on server.
serverPrefaceLatch.set(new CountDownLatch(1));
serverSettingsLatch.set(new CountDownLatch(1));
// After the 101, the client must send the connection preface.
Generator generator = new Generator(byteBufferPool);
ByteBufferPool.Lease lease = new ByteBufferPool.Lease(byteBufferPool);
generator.control(lease, new PrefaceFrame());
Map<Integer, Integer> clientSettings = new HashMap<>();
clientSettings.put(SettingsFrame.ENABLE_PUSH, 1);
generator.control(lease, new SettingsFrame(clientSettings, false));
List<ByteBuffer> buffers = lease.getByteBuffers();
socket.write(buffers.toArray(new ByteBuffer[buffers.size()]));
// However, we should not call onPreface() again.
Assert.assertFalse(serverPrefaceLatch.get().await(1, TimeUnit.SECONDS));
// Although we should notify of the SETTINGS frame.
Assert.assertTrue(serverSettingsLatch.get().await(5, TimeUnit.SECONDS));
CountDownLatch clientSettingsLatch = new CountDownLatch(1);
AtomicBoolean responded = new AtomicBoolean();
Parser parser = new Parser(byteBufferPool, new Parser.Listener.Adapter() {
@Override
public void onSettings(SettingsFrame frame) {
if (frame.isReply())
return;
Assert.assertEquals(maxConcurrentStreams, frame.getSettings().get(SettingsFrame.MAX_CONCURRENT_STREAMS));
clientSettingsLatch.countDown();
}
@Override
public void onHeaders(HeadersFrame frame) {
if (frame.isEndStream())
responded.set(true);
}
}, 4096, 8192);
// HTTP/2 parsing.
while (true) {
parser.parse(buffer);
if (responded.get())
break;
BufferUtil.clearToFill(buffer);
int read = socket.read(buffer);
BufferUtil.flipToFlush(buffer, 0);
if (read < 0)
Assert.fail();
}
Assert.assertTrue(clientSettingsLatch.await(5, TimeUnit.SECONDS));
}
}
Aggregations