Merge remote-tracking branch 'origin/master' into session-refactor
This commit is contained in:
commit
bf2a1fa29e
33
VERSION.txt
33
VERSION.txt
|
@ -1,4 +1,35 @@
|
||||||
jetty-9.3.3-SNAPSHOT
|
jetty-9.3.4-SNAPSHOT
|
||||||
|
|
||||||
|
jetty-9.3.3.v20150827 - 27 August 2015
|
||||||
|
+ 470311 Introduce a proxy-protocol module.
|
||||||
|
+ 471055 Restore legacy/experimental WebSocket extensions (deflate-frame)
|
||||||
|
+ 472411 PathResource.checkAliasPath() typo
|
||||||
|
+ 473321 Overriding SSL context KeyStoreType requires explicit override of
|
||||||
|
TrustStoreType
|
||||||
|
+ 474025 SslContextFactory does not work with JCEKS Keystore
|
||||||
|
+ 474068 Update WebSocket Extension for permessage-deflate draft-22
|
||||||
|
+ 474319 Reintroduce blocking connect().
|
||||||
|
+ 474321 Allow synchronous address resolution.
|
||||||
|
+ 474344 apache-jstl includes test dependencies
|
||||||
|
+ 474358 DefaultServlet bad Content-Type on compressed content
|
||||||
|
+ 474361 Handle JVM version extensions like -internal
|
||||||
|
+ 474453 Tiny buffers (under 7 bytes) fail to compress in permessage-deflate
|
||||||
|
+ 474454 Backport permessage-deflate from Jetty 9.3.x to 9.2.x
|
||||||
|
+ 474455 Enable permessage-deflate WebSocket extension
|
||||||
|
+ 474558 Debug log ServletContainerInitializer @HandlesTypes contents
|
||||||
|
+ 474617 AsyncListener.onError not called for errors
|
||||||
|
+ 474618 AsyncListener.onComplete not called when error occurs
|
||||||
|
+ 474634 AsyncListener.onError() handling.
|
||||||
|
+ 474685 GzipHandler configuration supports csv paths and mimetypes.
|
||||||
|
+ 474888 HttpClient JMX support.
|
||||||
|
+ 474936 WebSocketSessions are not always cleaned out from openSessions
|
||||||
|
+ 474961 Close input stream for classes in AnnotationParser after scanning
|
||||||
|
+ 475195 SNI matching fails when keystore does not contain wild certificates.
|
||||||
|
+ 475483 Starting Jetty with [exec] should use properties file.
|
||||||
|
+ 475546 ClosedChannelException when connecting to HTTPS over HTTP proxy with
|
||||||
|
CONNECT.
|
||||||
|
+ 475605 Add support for multi-homed destinations.
|
||||||
|
+ 475927 SecureRequestCustomizer fails to match host.
|
||||||
|
|
||||||
jetty-9.3.2.v20150730 - 30 July 2015
|
jetty-9.3.2.v20150730 - 30 July 2015
|
||||||
+ 470351 Fixed SNI matching of wildcard certificates
|
+ 470351 Fixed SNI matching of wildcard certificates
|
||||||
|
|
|
@ -2,7 +2,7 @@
|
||||||
<parent>
|
<parent>
|
||||||
<groupId>org.eclipse.jetty</groupId>
|
<groupId>org.eclipse.jetty</groupId>
|
||||||
<artifactId>jetty-project</artifactId>
|
<artifactId>jetty-project</artifactId>
|
||||||
<version>9.3.3-SNAPSHOT</version>
|
<version>9.3.4-SNAPSHOT</version>
|
||||||
<relativePath>../../pom.xml</relativePath>
|
<relativePath>../../pom.xml</relativePath>
|
||||||
</parent>
|
</parent>
|
||||||
<modelVersion>4.0.0</modelVersion>
|
<modelVersion>4.0.0</modelVersion>
|
||||||
|
|
|
@ -2,7 +2,7 @@
|
||||||
<parent>
|
<parent>
|
||||||
<groupId>org.eclipse.jetty</groupId>
|
<groupId>org.eclipse.jetty</groupId>
|
||||||
<artifactId>jetty-project</artifactId>
|
<artifactId>jetty-project</artifactId>
|
||||||
<version>9.3.3-SNAPSHOT</version>
|
<version>9.3.4-SNAPSHOT</version>
|
||||||
</parent>
|
</parent>
|
||||||
<modelVersion>4.0.0</modelVersion>
|
<modelVersion>4.0.0</modelVersion>
|
||||||
<artifactId>apache-jsp</artifactId>
|
<artifactId>apache-jsp</artifactId>
|
||||||
|
|
|
@ -2,7 +2,7 @@
|
||||||
<parent>
|
<parent>
|
||||||
<groupId>org.eclipse.jetty</groupId>
|
<groupId>org.eclipse.jetty</groupId>
|
||||||
<artifactId>jetty-project</artifactId>
|
<artifactId>jetty-project</artifactId>
|
||||||
<version>9.3.3-SNAPSHOT</version>
|
<version>9.3.4-SNAPSHOT</version>
|
||||||
</parent>
|
</parent>
|
||||||
<modelVersion>4.0.0</modelVersion>
|
<modelVersion>4.0.0</modelVersion>
|
||||||
<artifactId>apache-jstl</artifactId>
|
<artifactId>apache-jstl</artifactId>
|
||||||
|
|
|
@ -2,7 +2,7 @@
|
||||||
<parent>
|
<parent>
|
||||||
<groupId>org.eclipse.jetty</groupId>
|
<groupId>org.eclipse.jetty</groupId>
|
||||||
<artifactId>example-async-rest</artifactId>
|
<artifactId>example-async-rest</artifactId>
|
||||||
<version>9.3.3-SNAPSHOT</version>
|
<version>9.3.4-SNAPSHOT</version>
|
||||||
</parent>
|
</parent>
|
||||||
<modelVersion>4.0.0</modelVersion>
|
<modelVersion>4.0.0</modelVersion>
|
||||||
<groupId>org.eclipse.jetty.example-async-rest</groupId>
|
<groupId>org.eclipse.jetty.example-async-rest</groupId>
|
||||||
|
|
|
@ -2,7 +2,7 @@
|
||||||
<parent>
|
<parent>
|
||||||
<groupId>org.eclipse.jetty</groupId>
|
<groupId>org.eclipse.jetty</groupId>
|
||||||
<artifactId>example-async-rest</artifactId>
|
<artifactId>example-async-rest</artifactId>
|
||||||
<version>9.3.3-SNAPSHOT</version>
|
<version>9.3.4-SNAPSHOT</version>
|
||||||
</parent>
|
</parent>
|
||||||
<modelVersion>4.0.0</modelVersion>
|
<modelVersion>4.0.0</modelVersion>
|
||||||
<groupId>org.eclipse.jetty.example-async-rest</groupId>
|
<groupId>org.eclipse.jetty.example-async-rest</groupId>
|
||||||
|
|
|
@ -2,7 +2,7 @@
|
||||||
<parent>
|
<parent>
|
||||||
<groupId>org.eclipse.jetty.examples</groupId>
|
<groupId>org.eclipse.jetty.examples</groupId>
|
||||||
<artifactId>examples-parent</artifactId>
|
<artifactId>examples-parent</artifactId>
|
||||||
<version>9.3.3-SNAPSHOT</version>
|
<version>9.3.4-SNAPSHOT</version>
|
||||||
<relativePath>../pom.xml</relativePath>
|
<relativePath>../pom.xml</relativePath>
|
||||||
</parent>
|
</parent>
|
||||||
<modelVersion>4.0.0</modelVersion>
|
<modelVersion>4.0.0</modelVersion>
|
||||||
|
|
|
@ -2,7 +2,7 @@
|
||||||
<parent>
|
<parent>
|
||||||
<groupId>org.eclipse.jetty.examples</groupId>
|
<groupId>org.eclipse.jetty.examples</groupId>
|
||||||
<artifactId>examples-parent</artifactId>
|
<artifactId>examples-parent</artifactId>
|
||||||
<version>9.3.3-SNAPSHOT</version>
|
<version>9.3.4-SNAPSHOT</version>
|
||||||
<relativePath>../pom.xml</relativePath>
|
<relativePath>../pom.xml</relativePath>
|
||||||
</parent>
|
</parent>
|
||||||
<modelVersion>4.0.0</modelVersion>
|
<modelVersion>4.0.0</modelVersion>
|
||||||
|
|
|
@ -21,7 +21,7 @@
|
||||||
<parent>
|
<parent>
|
||||||
<groupId>org.eclipse.jetty</groupId>
|
<groupId>org.eclipse.jetty</groupId>
|
||||||
<artifactId>jetty-project</artifactId>
|
<artifactId>jetty-project</artifactId>
|
||||||
<version>9.3.3-SNAPSHOT</version>
|
<version>9.3.4-SNAPSHOT</version>
|
||||||
<relativePath>../pom.xml</relativePath>
|
<relativePath>../pom.xml</relativePath>
|
||||||
</parent>
|
</parent>
|
||||||
<groupId>org.eclipse.jetty.examples</groupId>
|
<groupId>org.eclipse.jetty.examples</groupId>
|
||||||
|
|
|
@ -2,7 +2,7 @@
|
||||||
<parent>
|
<parent>
|
||||||
<groupId>org.eclipse.jetty</groupId>
|
<groupId>org.eclipse.jetty</groupId>
|
||||||
<artifactId>jetty-alpn-parent</artifactId>
|
<artifactId>jetty-alpn-parent</artifactId>
|
||||||
<version>9.3.3-SNAPSHOT</version>
|
<version>9.3.4-SNAPSHOT</version>
|
||||||
</parent>
|
</parent>
|
||||||
<modelVersion>4.0.0</modelVersion>
|
<modelVersion>4.0.0</modelVersion>
|
||||||
<artifactId>jetty-alpn-client</artifactId>
|
<artifactId>jetty-alpn-client</artifactId>
|
||||||
|
|
|
@ -2,7 +2,7 @@
|
||||||
<parent>
|
<parent>
|
||||||
<groupId>org.eclipse.jetty</groupId>
|
<groupId>org.eclipse.jetty</groupId>
|
||||||
<artifactId>jetty-alpn-parent</artifactId>
|
<artifactId>jetty-alpn-parent</artifactId>
|
||||||
<version>9.3.3-SNAPSHOT</version>
|
<version>9.3.4-SNAPSHOT</version>
|
||||||
</parent>
|
</parent>
|
||||||
<modelVersion>4.0.0</modelVersion>
|
<modelVersion>4.0.0</modelVersion>
|
||||||
<artifactId>jetty-alpn-server</artifactId>
|
<artifactId>jetty-alpn-server</artifactId>
|
||||||
|
|
|
@ -2,7 +2,7 @@
|
||||||
<parent>
|
<parent>
|
||||||
<groupId>org.eclipse.jetty</groupId>
|
<groupId>org.eclipse.jetty</groupId>
|
||||||
<artifactId>jetty-project</artifactId>
|
<artifactId>jetty-project</artifactId>
|
||||||
<version>9.3.3-SNAPSHOT</version>
|
<version>9.3.4-SNAPSHOT</version>
|
||||||
</parent>
|
</parent>
|
||||||
<modelVersion>4.0.0</modelVersion>
|
<modelVersion>4.0.0</modelVersion>
|
||||||
<artifactId>jetty-alpn-parent</artifactId>
|
<artifactId>jetty-alpn-parent</artifactId>
|
||||||
|
|
|
@ -2,7 +2,7 @@
|
||||||
<parent>
|
<parent>
|
||||||
<groupId>org.eclipse.jetty</groupId>
|
<groupId>org.eclipse.jetty</groupId>
|
||||||
<artifactId>jetty-project</artifactId>
|
<artifactId>jetty-project</artifactId>
|
||||||
<version>9.3.3-SNAPSHOT</version>
|
<version>9.3.4-SNAPSHOT</version>
|
||||||
</parent>
|
</parent>
|
||||||
<modelVersion>4.0.0</modelVersion>
|
<modelVersion>4.0.0</modelVersion>
|
||||||
<artifactId>jetty-annotations</artifactId>
|
<artifactId>jetty-annotations</artifactId>
|
||||||
|
|
|
@ -2,7 +2,7 @@
|
||||||
<parent>
|
<parent>
|
||||||
<groupId>org.eclipse.jetty</groupId>
|
<groupId>org.eclipse.jetty</groupId>
|
||||||
<artifactId>jetty-project</artifactId>
|
<artifactId>jetty-project</artifactId>
|
||||||
<version>9.3.3-SNAPSHOT</version>
|
<version>9.3.4-SNAPSHOT</version>
|
||||||
</parent>
|
</parent>
|
||||||
<modelVersion>4.0.0</modelVersion>
|
<modelVersion>4.0.0</modelVersion>
|
||||||
<artifactId>jetty-ant</artifactId>
|
<artifactId>jetty-ant</artifactId>
|
||||||
|
|
|
@ -2,7 +2,7 @@
|
||||||
<parent>
|
<parent>
|
||||||
<groupId>org.eclipse.jetty.cdi</groupId>
|
<groupId>org.eclipse.jetty.cdi</groupId>
|
||||||
<artifactId>jetty-cdi-parent</artifactId>
|
<artifactId>jetty-cdi-parent</artifactId>
|
||||||
<version>9.3.3-SNAPSHOT</version>
|
<version>9.3.4-SNAPSHOT</version>
|
||||||
</parent>
|
</parent>
|
||||||
<modelVersion>4.0.0</modelVersion>
|
<modelVersion>4.0.0</modelVersion>
|
||||||
<artifactId>cdi-core</artifactId>
|
<artifactId>cdi-core</artifactId>
|
||||||
|
|
|
@ -2,7 +2,7 @@
|
||||||
<parent>
|
<parent>
|
||||||
<groupId>org.eclipse.jetty.cdi</groupId>
|
<groupId>org.eclipse.jetty.cdi</groupId>
|
||||||
<artifactId>jetty-cdi-parent</artifactId>
|
<artifactId>jetty-cdi-parent</artifactId>
|
||||||
<version>9.3.3-SNAPSHOT</version>
|
<version>9.3.4-SNAPSHOT</version>
|
||||||
</parent>
|
</parent>
|
||||||
<modelVersion>4.0.0</modelVersion>
|
<modelVersion>4.0.0</modelVersion>
|
||||||
<artifactId>cdi-full-servlet</artifactId>
|
<artifactId>cdi-full-servlet</artifactId>
|
||||||
|
|
|
@ -2,7 +2,7 @@
|
||||||
<parent>
|
<parent>
|
||||||
<groupId>org.eclipse.jetty.cdi</groupId>
|
<groupId>org.eclipse.jetty.cdi</groupId>
|
||||||
<artifactId>jetty-cdi-parent</artifactId>
|
<artifactId>jetty-cdi-parent</artifactId>
|
||||||
<version>9.3.3-SNAPSHOT</version>
|
<version>9.3.4-SNAPSHOT</version>
|
||||||
</parent>
|
</parent>
|
||||||
<modelVersion>4.0.0</modelVersion>
|
<modelVersion>4.0.0</modelVersion>
|
||||||
<artifactId>cdi-servlet</artifactId>
|
<artifactId>cdi-servlet</artifactId>
|
||||||
|
|
|
@ -2,7 +2,7 @@
|
||||||
<parent>
|
<parent>
|
||||||
<groupId>org.eclipse.jetty.cdi</groupId>
|
<groupId>org.eclipse.jetty.cdi</groupId>
|
||||||
<artifactId>jetty-cdi-parent</artifactId>
|
<artifactId>jetty-cdi-parent</artifactId>
|
||||||
<version>9.3.3-SNAPSHOT</version>
|
<version>9.3.4-SNAPSHOT</version>
|
||||||
</parent>
|
</parent>
|
||||||
<modelVersion>4.0.0</modelVersion>
|
<modelVersion>4.0.0</modelVersion>
|
||||||
<artifactId>cdi-websocket</artifactId>
|
<artifactId>cdi-websocket</artifactId>
|
||||||
|
|
|
@ -2,7 +2,7 @@
|
||||||
<parent>
|
<parent>
|
||||||
<groupId>org.eclipse.jetty</groupId>
|
<groupId>org.eclipse.jetty</groupId>
|
||||||
<artifactId>jetty-project</artifactId>
|
<artifactId>jetty-project</artifactId>
|
||||||
<version>9.3.3-SNAPSHOT</version>
|
<version>9.3.4-SNAPSHOT</version>
|
||||||
</parent>
|
</parent>
|
||||||
<modelVersion>4.0.0</modelVersion>
|
<modelVersion>4.0.0</modelVersion>
|
||||||
<groupId>org.eclipse.jetty.cdi</groupId>
|
<groupId>org.eclipse.jetty.cdi</groupId>
|
||||||
|
|
|
@ -20,7 +20,7 @@
|
||||||
<parent>
|
<parent>
|
||||||
<groupId>org.eclipse.jetty.cdi</groupId>
|
<groupId>org.eclipse.jetty.cdi</groupId>
|
||||||
<artifactId>jetty-cdi-parent</artifactId>
|
<artifactId>jetty-cdi-parent</artifactId>
|
||||||
<version>9.3.3-SNAPSHOT</version>
|
<version>9.3.4-SNAPSHOT</version>
|
||||||
</parent>
|
</parent>
|
||||||
<modelVersion>4.0.0</modelVersion>
|
<modelVersion>4.0.0</modelVersion>
|
||||||
<artifactId>test-cdi-webapp</artifactId>
|
<artifactId>test-cdi-webapp</artifactId>
|
||||||
|
|
|
@ -2,7 +2,7 @@
|
||||||
<parent>
|
<parent>
|
||||||
<groupId>org.eclipse.jetty</groupId>
|
<groupId>org.eclipse.jetty</groupId>
|
||||||
<artifactId>jetty-project</artifactId>
|
<artifactId>jetty-project</artifactId>
|
||||||
<version>9.3.3-SNAPSHOT</version>
|
<version>9.3.4-SNAPSHOT</version>
|
||||||
</parent>
|
</parent>
|
||||||
|
|
||||||
<modelVersion>4.0.0</modelVersion>
|
<modelVersion>4.0.0</modelVersion>
|
||||||
|
|
|
@ -21,9 +21,9 @@ package org.eclipse.jetty.client;
|
||||||
import java.io.Closeable;
|
import java.io.Closeable;
|
||||||
import java.io.IOException;
|
import java.io.IOException;
|
||||||
import java.util.ArrayList;
|
import java.util.ArrayList;
|
||||||
|
import java.util.Deque;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
import java.util.concurrent.BlockingDeque;
|
import java.util.Queue;
|
||||||
import java.util.concurrent.BlockingQueue;
|
|
||||||
import java.util.concurrent.LinkedBlockingDeque;
|
import java.util.concurrent.LinkedBlockingDeque;
|
||||||
import java.util.concurrent.atomic.AtomicInteger;
|
import java.util.concurrent.atomic.AtomicInteger;
|
||||||
import java.util.concurrent.locks.ReentrantLock;
|
import java.util.concurrent.locks.ReentrantLock;
|
||||||
|
@ -44,15 +44,15 @@ import org.eclipse.jetty.util.thread.Sweeper;
|
||||||
@ManagedObject("The connection pool")
|
@ManagedObject("The connection pool")
|
||||||
public class ConnectionPool implements Closeable, Dumpable, Sweeper.Sweepable
|
public class ConnectionPool implements Closeable, Dumpable, Sweeper.Sweepable
|
||||||
{
|
{
|
||||||
protected static final Logger LOG = Log.getLogger(ConnectionPool.class);
|
private static final Logger LOG = Log.getLogger(ConnectionPool.class);
|
||||||
|
|
||||||
private final AtomicInteger connectionCount = new AtomicInteger();
|
private final AtomicInteger connectionCount = new AtomicInteger();
|
||||||
private final ReentrantLock lock = new ReentrantLock();
|
private final ReentrantLock lock = new ReentrantLock();
|
||||||
private final Destination destination;
|
private final Destination destination;
|
||||||
private final int maxConnections;
|
private final int maxConnections;
|
||||||
private final Callback requester;
|
private final Callback requester;
|
||||||
private final BlockingDeque<Connection> idleConnections;
|
private final Deque<Connection> idleConnections;
|
||||||
private final BlockingQueue<Connection> activeConnections;
|
private final Queue<Connection> activeConnections;
|
||||||
|
|
||||||
public ConnectionPool(Destination destination, int maxConnections, Callback requester)
|
public ConnectionPool(Destination destination, int maxConnections, Callback requester)
|
||||||
{
|
{
|
||||||
|
@ -81,12 +81,12 @@ public class ConnectionPool implements Closeable, Dumpable, Sweeper.Sweepable
|
||||||
return activeConnections.size();
|
return activeConnections.size();
|
||||||
}
|
}
|
||||||
|
|
||||||
public BlockingQueue<Connection> getIdleConnections()
|
public Queue<Connection> getIdleConnections()
|
||||||
{
|
{
|
||||||
return idleConnections;
|
return idleConnections;
|
||||||
}
|
}
|
||||||
|
|
||||||
public BlockingQueue<Connection> getActiveConnections()
|
public Queue<Connection> getActiveConnections()
|
||||||
{
|
{
|
||||||
return activeConnections;
|
return activeConnections;
|
||||||
}
|
}
|
||||||
|
@ -129,7 +129,7 @@ public class ConnectionPool implements Closeable, Dumpable, Sweeper.Sweepable
|
||||||
|
|
||||||
idleCreated(connection);
|
idleCreated(connection);
|
||||||
|
|
||||||
requester.succeeded();
|
proceed();
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
|
@ -150,11 +150,15 @@ public class ConnectionPool implements Closeable, Dumpable, Sweeper.Sweepable
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
protected void proceed()
|
||||||
|
{
|
||||||
|
requester.succeeded();
|
||||||
|
}
|
||||||
|
|
||||||
protected void idleCreated(Connection connection)
|
protected void idleCreated(Connection connection)
|
||||||
{
|
{
|
||||||
boolean idle;
|
boolean idle;
|
||||||
final ReentrantLock lock = this.lock;
|
lock();
|
||||||
lock.lock();
|
|
||||||
try
|
try
|
||||||
{
|
{
|
||||||
// Use "cold" new connections as last.
|
// Use "cold" new connections as last.
|
||||||
|
@ -162,7 +166,7 @@ public class ConnectionPool implements Closeable, Dumpable, Sweeper.Sweepable
|
||||||
}
|
}
|
||||||
finally
|
finally
|
||||||
{
|
{
|
||||||
lock.unlock();
|
unlock();
|
||||||
}
|
}
|
||||||
|
|
||||||
idle(connection, idle);
|
idle(connection, idle);
|
||||||
|
@ -172,8 +176,7 @@ public class ConnectionPool implements Closeable, Dumpable, Sweeper.Sweepable
|
||||||
{
|
{
|
||||||
boolean acquired;
|
boolean acquired;
|
||||||
Connection connection;
|
Connection connection;
|
||||||
final ReentrantLock lock = this.lock;
|
lock();
|
||||||
lock.lock();
|
|
||||||
try
|
try
|
||||||
{
|
{
|
||||||
connection = idleConnections.pollFirst();
|
connection = idleConnections.pollFirst();
|
||||||
|
@ -183,7 +186,7 @@ public class ConnectionPool implements Closeable, Dumpable, Sweeper.Sweepable
|
||||||
}
|
}
|
||||||
finally
|
finally
|
||||||
{
|
{
|
||||||
lock.unlock();
|
unlock();
|
||||||
}
|
}
|
||||||
|
|
||||||
if (acquired)
|
if (acquired)
|
||||||
|
@ -209,24 +212,28 @@ public class ConnectionPool implements Closeable, Dumpable, Sweeper.Sweepable
|
||||||
public boolean release(Connection connection)
|
public boolean release(Connection connection)
|
||||||
{
|
{
|
||||||
boolean idle;
|
boolean idle;
|
||||||
final ReentrantLock lock = this.lock;
|
lock();
|
||||||
lock.lock();
|
|
||||||
try
|
try
|
||||||
{
|
{
|
||||||
if (!activeConnections.remove(connection))
|
if (!activeConnections.remove(connection))
|
||||||
return false;
|
return false;
|
||||||
// Make sure we use "hot" connections first.
|
// Make sure we use "hot" connections first.
|
||||||
idle = idleConnections.offerFirst(connection);
|
idle = offerIdle(connection);
|
||||||
}
|
}
|
||||||
finally
|
finally
|
||||||
{
|
{
|
||||||
lock.unlock();
|
unlock();
|
||||||
}
|
}
|
||||||
|
|
||||||
released(connection);
|
released(connection);
|
||||||
return idle(connection, idle);
|
return idle(connection, idle);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
protected boolean offerIdle(Connection connection)
|
||||||
|
{
|
||||||
|
return idleConnections.offerFirst(connection);
|
||||||
|
}
|
||||||
|
|
||||||
protected boolean idle(Connection connection, boolean idle)
|
protected boolean idle(Connection connection, boolean idle)
|
||||||
{
|
{
|
||||||
if (idle)
|
if (idle)
|
||||||
|
@ -249,11 +256,15 @@ public class ConnectionPool implements Closeable, Dumpable, Sweeper.Sweepable
|
||||||
}
|
}
|
||||||
|
|
||||||
public boolean remove(Connection connection)
|
public boolean remove(Connection connection)
|
||||||
|
{
|
||||||
|
return remove(connection, false);
|
||||||
|
}
|
||||||
|
|
||||||
|
protected boolean remove(Connection connection, boolean force)
|
||||||
{
|
{
|
||||||
boolean activeRemoved;
|
boolean activeRemoved;
|
||||||
boolean idleRemoved;
|
boolean idleRemoved;
|
||||||
final ReentrantLock lock = this.lock;
|
lock();
|
||||||
lock.lock();
|
|
||||||
try
|
try
|
||||||
{
|
{
|
||||||
activeRemoved = activeConnections.remove(connection);
|
activeRemoved = activeConnections.remove(connection);
|
||||||
|
@ -261,12 +272,12 @@ public class ConnectionPool implements Closeable, Dumpable, Sweeper.Sweepable
|
||||||
}
|
}
|
||||||
finally
|
finally
|
||||||
{
|
{
|
||||||
lock.unlock();
|
unlock();
|
||||||
}
|
}
|
||||||
|
|
||||||
if (activeRemoved)
|
if (activeRemoved)
|
||||||
released(connection);
|
released(connection);
|
||||||
boolean removed = activeRemoved || idleRemoved;
|
boolean removed = activeRemoved || idleRemoved || force;
|
||||||
if (removed)
|
if (removed)
|
||||||
{
|
{
|
||||||
int pooled = connectionCount.decrementAndGet();
|
int pooled = connectionCount.decrementAndGet();
|
||||||
|
@ -278,29 +289,27 @@ public class ConnectionPool implements Closeable, Dumpable, Sweeper.Sweepable
|
||||||
|
|
||||||
public boolean isActive(Connection connection)
|
public boolean isActive(Connection connection)
|
||||||
{
|
{
|
||||||
final ReentrantLock lock = this.lock;
|
lock();
|
||||||
lock.lock();
|
|
||||||
try
|
try
|
||||||
{
|
{
|
||||||
return activeConnections.contains(connection);
|
return activeConnections.contains(connection);
|
||||||
}
|
}
|
||||||
finally
|
finally
|
||||||
{
|
{
|
||||||
lock.unlock();
|
unlock();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public boolean isIdle(Connection connection)
|
public boolean isIdle(Connection connection)
|
||||||
{
|
{
|
||||||
final ReentrantLock lock = this.lock;
|
lock();
|
||||||
lock.lock();
|
|
||||||
try
|
try
|
||||||
{
|
{
|
||||||
return idleConnections.contains(connection);
|
return idleConnections.contains(connection);
|
||||||
}
|
}
|
||||||
finally
|
finally
|
||||||
{
|
{
|
||||||
lock.unlock();
|
unlock();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -313,8 +322,7 @@ public class ConnectionPool implements Closeable, Dumpable, Sweeper.Sweepable
|
||||||
{
|
{
|
||||||
List<Connection> idles = new ArrayList<>();
|
List<Connection> idles = new ArrayList<>();
|
||||||
List<Connection> actives = new ArrayList<>();
|
List<Connection> actives = new ArrayList<>();
|
||||||
final ReentrantLock lock = this.lock;
|
lock();
|
||||||
lock.lock();
|
|
||||||
try
|
try
|
||||||
{
|
{
|
||||||
idles.addAll(idleConnections);
|
idles.addAll(idleConnections);
|
||||||
|
@ -324,7 +332,7 @@ public class ConnectionPool implements Closeable, Dumpable, Sweeper.Sweepable
|
||||||
}
|
}
|
||||||
finally
|
finally
|
||||||
{
|
{
|
||||||
lock.unlock();
|
unlock();
|
||||||
}
|
}
|
||||||
|
|
||||||
connectionCount.set(0);
|
connectionCount.set(0);
|
||||||
|
@ -348,8 +356,7 @@ public class ConnectionPool implements Closeable, Dumpable, Sweeper.Sweepable
|
||||||
{
|
{
|
||||||
List<Connection> actives = new ArrayList<>();
|
List<Connection> actives = new ArrayList<>();
|
||||||
List<Connection> idles = new ArrayList<>();
|
List<Connection> idles = new ArrayList<>();
|
||||||
final ReentrantLock lock = this.lock;
|
lock();
|
||||||
lock.lock();
|
|
||||||
try
|
try
|
||||||
{
|
{
|
||||||
actives.addAll(activeConnections);
|
actives.addAll(activeConnections);
|
||||||
|
@ -357,7 +364,7 @@ public class ConnectionPool implements Closeable, Dumpable, Sweeper.Sweepable
|
||||||
}
|
}
|
||||||
finally
|
finally
|
||||||
{
|
{
|
||||||
lock.unlock();
|
unlock();
|
||||||
}
|
}
|
||||||
|
|
||||||
ContainerLifeCycle.dumpObject(out, this);
|
ContainerLifeCycle.dumpObject(out, this);
|
||||||
|
@ -368,8 +375,7 @@ public class ConnectionPool implements Closeable, Dumpable, Sweeper.Sweepable
|
||||||
public boolean sweep()
|
public boolean sweep()
|
||||||
{
|
{
|
||||||
List<Sweeper.Sweepable> toSweep = new ArrayList<>();
|
List<Sweeper.Sweepable> toSweep = new ArrayList<>();
|
||||||
final ReentrantLock lock = this.lock;
|
lock();
|
||||||
lock.lock();
|
|
||||||
try
|
try
|
||||||
{
|
{
|
||||||
for (Connection connection : getActiveConnections())
|
for (Connection connection : getActiveConnections())
|
||||||
|
@ -380,7 +386,7 @@ public class ConnectionPool implements Closeable, Dumpable, Sweeper.Sweepable
|
||||||
}
|
}
|
||||||
finally
|
finally
|
||||||
{
|
{
|
||||||
lock.unlock();
|
unlock();
|
||||||
}
|
}
|
||||||
|
|
||||||
for (Sweeper.Sweepable candidate : toSweep)
|
for (Sweeper.Sweepable candidate : toSweep)
|
||||||
|
@ -400,13 +406,22 @@ public class ConnectionPool implements Closeable, Dumpable, Sweeper.Sweepable
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
protected void lock()
|
||||||
|
{
|
||||||
|
lock.lock();
|
||||||
|
}
|
||||||
|
|
||||||
|
protected void unlock()
|
||||||
|
{
|
||||||
|
lock.unlock();
|
||||||
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public String toString()
|
public String toString()
|
||||||
{
|
{
|
||||||
int activeSize;
|
int activeSize;
|
||||||
int idleSize;
|
int idleSize;
|
||||||
final ReentrantLock lock = this.lock;
|
lock();
|
||||||
lock.lock();
|
|
||||||
try
|
try
|
||||||
{
|
{
|
||||||
activeSize = activeConnections.size();
|
activeSize = activeConnections.size();
|
||||||
|
@ -414,7 +429,7 @@ public class ConnectionPool implements Closeable, Dumpable, Sweeper.Sweepable
|
||||||
}
|
}
|
||||||
finally
|
finally
|
||||||
{
|
{
|
||||||
lock.unlock();
|
unlock();
|
||||||
}
|
}
|
||||||
|
|
||||||
return String.format("%s[c=%d/%d,a=%d,i=%d]",
|
return String.format("%s[c=%d/%d,a=%d,i=%d]",
|
||||||
|
|
|
@ -22,9 +22,13 @@ import org.eclipse.jetty.client.api.Connection;
|
||||||
import org.eclipse.jetty.client.api.Destination;
|
import org.eclipse.jetty.client.api.Destination;
|
||||||
import org.eclipse.jetty.util.Callback;
|
import org.eclipse.jetty.util.Callback;
|
||||||
import org.eclipse.jetty.util.LeakDetector;
|
import org.eclipse.jetty.util.LeakDetector;
|
||||||
|
import org.eclipse.jetty.util.log.Log;
|
||||||
|
import org.eclipse.jetty.util.log.Logger;
|
||||||
|
|
||||||
public class LeakTrackingConnectionPool extends ConnectionPool
|
public class LeakTrackingConnectionPool extends ConnectionPool
|
||||||
{
|
{
|
||||||
|
private static final Logger LOG = Log.getLogger(LeakTrackingConnectionPool.class);
|
||||||
|
|
||||||
private final LeakDetector<Connection> leakDetector = new LeakDetector<Connection>()
|
private final LeakDetector<Connection> leakDetector = new LeakDetector<Connection>()
|
||||||
{
|
{
|
||||||
@Override
|
@Override
|
||||||
|
|
|
@ -71,9 +71,7 @@ public abstract class PoolingHttpDestination<C extends Connection> extends HttpD
|
||||||
{
|
{
|
||||||
if (getHttpExchanges().isEmpty())
|
if (getHttpExchanges().isEmpty())
|
||||||
return;
|
return;
|
||||||
C connection = acquire();
|
process();
|
||||||
if (connection != null)
|
|
||||||
process(connection);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@SuppressWarnings("unchecked")
|
@SuppressWarnings("unchecked")
|
||||||
|
@ -82,6 +80,13 @@ public abstract class PoolingHttpDestination<C extends Connection> extends HttpD
|
||||||
return (C)connectionPool.acquire();
|
return (C)connectionPool.acquire();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private void process()
|
||||||
|
{
|
||||||
|
C connection = acquire();
|
||||||
|
if (connection != null)
|
||||||
|
process(connection);
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* <p>Processes a new connection making it idle or active depending on whether requests are waiting to be sent.</p>
|
* <p>Processes a new connection making it idle or active depending on whether requests are waiting to be sent.</p>
|
||||||
* <p>A new connection is created when a request needs to be executed; it is possible that the request that
|
* <p>A new connection is created when a request needs to be executed; it is possible that the request that
|
||||||
|
@ -137,18 +142,21 @@ public abstract class PoolingHttpDestination<C extends Connection> extends HttpD
|
||||||
@SuppressWarnings("unchecked")
|
@SuppressWarnings("unchecked")
|
||||||
C connection = (C)c;
|
C connection = (C)c;
|
||||||
if (LOG.isDebugEnabled())
|
if (LOG.isDebugEnabled())
|
||||||
LOG.debug("{} released", connection);
|
LOG.debug("Released {}", connection);
|
||||||
HttpClient client = getHttpClient();
|
HttpClient client = getHttpClient();
|
||||||
if (client.isRunning())
|
if (client.isRunning())
|
||||||
{
|
{
|
||||||
if (connectionPool.isActive(connection))
|
if (connectionPool.isActive(connection))
|
||||||
{
|
{
|
||||||
process(connection);
|
if (connectionPool.release(connection))
|
||||||
|
send();
|
||||||
|
else
|
||||||
|
connection.close();
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
if (LOG.isDebugEnabled())
|
if (LOG.isDebugEnabled())
|
||||||
LOG.debug("{} explicit", connection);
|
LOG.debug("Released explicit {}", connection);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
|
@ -184,9 +192,7 @@ public abstract class PoolingHttpDestination<C extends Connection> extends HttpD
|
||||||
// We need to execute queued requests even if this connection failed.
|
// We need to execute queued requests even if this connection failed.
|
||||||
// We may create a connection that is not needed, but it will eventually
|
// We may create a connection that is not needed, but it will eventually
|
||||||
// idle timeout, so no worries.
|
// idle timeout, so no worries.
|
||||||
C newConnection = acquire();
|
process();
|
||||||
if (newConnection != null)
|
|
||||||
process(newConnection);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -0,0 +1,209 @@
|
||||||
|
//
|
||||||
|
// ========================================================================
|
||||||
|
// Copyright (c) 1995-2015 Mort Bay Consulting Pty. Ltd.
|
||||||
|
// ------------------------------------------------------------------------
|
||||||
|
// All rights reserved. This program and the accompanying materials
|
||||||
|
// are made available under the terms of the Eclipse Public License v1.0
|
||||||
|
// and Apache License v2.0 which accompanies this distribution.
|
||||||
|
//
|
||||||
|
// The Eclipse Public License is available at
|
||||||
|
// http://www.eclipse.org/legal/epl-v10.html
|
||||||
|
//
|
||||||
|
// The Apache License v2.0 is available at
|
||||||
|
// http://www.opensource.org/licenses/apache2.0.php
|
||||||
|
//
|
||||||
|
// You may elect to redistribute this code under either of these licenses.
|
||||||
|
// ========================================================================
|
||||||
|
//
|
||||||
|
|
||||||
|
package org.eclipse.jetty.client;
|
||||||
|
|
||||||
|
import java.io.IOException;
|
||||||
|
import java.util.HashMap;
|
||||||
|
import java.util.Map;
|
||||||
|
import java.util.concurrent.TimeUnit;
|
||||||
|
import java.util.concurrent.atomic.AtomicBoolean;
|
||||||
|
|
||||||
|
import org.eclipse.jetty.client.api.Connection;
|
||||||
|
import org.eclipse.jetty.client.api.Destination;
|
||||||
|
import org.eclipse.jetty.util.Callback;
|
||||||
|
import org.eclipse.jetty.util.annotation.ManagedAttribute;
|
||||||
|
import org.eclipse.jetty.util.component.ContainerLifeCycle;
|
||||||
|
import org.eclipse.jetty.util.log.Log;
|
||||||
|
import org.eclipse.jetty.util.log.Logger;
|
||||||
|
import org.eclipse.jetty.util.thread.Scheduler;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* <p>A {@link ConnectionPool} that validates connections before
|
||||||
|
* making them available for use.</p>
|
||||||
|
* <p>Connections that have just been opened are not validated.
|
||||||
|
* Connections that are {@link #release(Connection) released} will
|
||||||
|
* be validated.</p>
|
||||||
|
* <p>Validation by reading from the EndPoint is not reliable,
|
||||||
|
* since the TCP FIN may arrive just after the validation read.</p>
|
||||||
|
* <p>This class validates connections by putting them in a
|
||||||
|
* "quarantine" for a configurable timeout, where they cannot
|
||||||
|
* be used to send requests. When the timeout expires, the
|
||||||
|
* quarantined connection is made idle and therefore available
|
||||||
|
* to send requests.</p>
|
||||||
|
* <p>The existing HttpClient mechanism to detect server closes
|
||||||
|
* will trigger and close quarantined connections, before they
|
||||||
|
* are made idle (and reusable) again.</p>
|
||||||
|
* <p>There still is a small chance that the timeout expires,
|
||||||
|
* the connection is made idle and available again, it is used
|
||||||
|
* to send a request exactly when the server decides to close.
|
||||||
|
* This case is however unavoidable and may be mitigated by
|
||||||
|
* tuning the idle timeout of the servers to be larger than
|
||||||
|
* that of the client.</p>
|
||||||
|
*/
|
||||||
|
public class ValidatingConnectionPool extends ConnectionPool
|
||||||
|
{
|
||||||
|
private static final Logger LOG = Log.getLogger(ValidatingConnectionPool.class);
|
||||||
|
|
||||||
|
private final Scheduler scheduler;
|
||||||
|
private final long timeout;
|
||||||
|
private final Map<Connection, Holder> quarantine;
|
||||||
|
|
||||||
|
public ValidatingConnectionPool(Destination destination, int maxConnections, Callback requester, Scheduler scheduler, long timeout)
|
||||||
|
{
|
||||||
|
super(destination, maxConnections, requester);
|
||||||
|
this.scheduler = scheduler;
|
||||||
|
this.timeout = timeout;
|
||||||
|
this.quarantine = new HashMap<>(maxConnections);
|
||||||
|
}
|
||||||
|
|
||||||
|
@ManagedAttribute(value = "The number of validating connections", readonly = true)
|
||||||
|
public int getValidatingConnectionCount()
|
||||||
|
{
|
||||||
|
return quarantine.size();
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public boolean release(Connection connection)
|
||||||
|
{
|
||||||
|
lock();
|
||||||
|
try
|
||||||
|
{
|
||||||
|
if (!getActiveConnections().remove(connection))
|
||||||
|
return false;
|
||||||
|
Holder holder = new Holder(connection);
|
||||||
|
holder.task = scheduler.schedule(holder, timeout, TimeUnit.MILLISECONDS);
|
||||||
|
quarantine.put(connection, holder);
|
||||||
|
if (LOG.isDebugEnabled())
|
||||||
|
LOG.debug("Validating for {}ms {}", timeout, connection);
|
||||||
|
}
|
||||||
|
finally
|
||||||
|
{
|
||||||
|
unlock();
|
||||||
|
}
|
||||||
|
|
||||||
|
released(connection);
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public boolean remove(Connection connection)
|
||||||
|
{
|
||||||
|
Holder holder;
|
||||||
|
lock();
|
||||||
|
try
|
||||||
|
{
|
||||||
|
holder = quarantine.remove(connection);
|
||||||
|
}
|
||||||
|
finally
|
||||||
|
{
|
||||||
|
unlock();
|
||||||
|
}
|
||||||
|
|
||||||
|
if (holder == null)
|
||||||
|
return super.remove(connection);
|
||||||
|
|
||||||
|
if (LOG.isDebugEnabled())
|
||||||
|
LOG.debug("Removed while validating {}", connection);
|
||||||
|
|
||||||
|
boolean cancelled = holder.cancel();
|
||||||
|
if (cancelled)
|
||||||
|
return remove(connection, true);
|
||||||
|
|
||||||
|
return super.remove(connection);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void dump(Appendable out, String indent) throws IOException
|
||||||
|
{
|
||||||
|
super.dump(out, indent);
|
||||||
|
ContainerLifeCycle.dump(out, indent, quarantine.values());
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public String toString()
|
||||||
|
{
|
||||||
|
int size;
|
||||||
|
lock();
|
||||||
|
try
|
||||||
|
{
|
||||||
|
size = quarantine.size();
|
||||||
|
}
|
||||||
|
finally
|
||||||
|
{
|
||||||
|
unlock();
|
||||||
|
}
|
||||||
|
return String.format("%s[v=%d]", super.toString(), size);
|
||||||
|
}
|
||||||
|
|
||||||
|
private class Holder implements Runnable
|
||||||
|
{
|
||||||
|
private final long timestamp = System.nanoTime();
|
||||||
|
private final AtomicBoolean latch = new AtomicBoolean();
|
||||||
|
private final Connection connection;
|
||||||
|
public Scheduler.Task task;
|
||||||
|
|
||||||
|
public Holder(Connection connection)
|
||||||
|
{
|
||||||
|
this.connection = connection;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void run()
|
||||||
|
{
|
||||||
|
if (latch.compareAndSet(false, true))
|
||||||
|
{
|
||||||
|
boolean idle;
|
||||||
|
lock();
|
||||||
|
try
|
||||||
|
{
|
||||||
|
quarantine.remove(connection);
|
||||||
|
idle = offerIdle(connection);
|
||||||
|
if (LOG.isDebugEnabled())
|
||||||
|
LOG.debug("Validated {}", connection);
|
||||||
|
}
|
||||||
|
finally
|
||||||
|
{
|
||||||
|
unlock();
|
||||||
|
}
|
||||||
|
|
||||||
|
if (idle(connection, idle))
|
||||||
|
proceed();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public boolean cancel()
|
||||||
|
{
|
||||||
|
if (latch.compareAndSet(false, true))
|
||||||
|
{
|
||||||
|
task.cancel();
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public String toString()
|
||||||
|
{
|
||||||
|
return String.format("%s[validationLeft=%dms]",
|
||||||
|
connection,
|
||||||
|
timeout - TimeUnit.NANOSECONDS.toMillis(System.nanoTime() - timestamp)
|
||||||
|
);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
|
@ -98,7 +98,7 @@ public class HttpConnectionOverHTTP extends AbstractConnection implements Connec
|
||||||
protected boolean onReadTimeout()
|
protected boolean onReadTimeout()
|
||||||
{
|
{
|
||||||
if (LOG.isDebugEnabled())
|
if (LOG.isDebugEnabled())
|
||||||
LOG.debug("{} idle timeout", this);
|
LOG.debug("Idle timeout {}", this);
|
||||||
close(new TimeoutException());
|
close(new TimeoutException());
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
@ -141,10 +141,10 @@ public class HttpConnectionOverHTTP extends AbstractConnection implements Connec
|
||||||
getHttpDestination().close(this);
|
getHttpDestination().close(this);
|
||||||
getEndPoint().shutdownOutput();
|
getEndPoint().shutdownOutput();
|
||||||
if (LOG.isDebugEnabled())
|
if (LOG.isDebugEnabled())
|
||||||
LOG.debug("{} oshut", this);
|
LOG.debug("Shutdown {}", this);
|
||||||
getEndPoint().close();
|
getEndPoint().close();
|
||||||
if (LOG.isDebugEnabled())
|
if (LOG.isDebugEnabled())
|
||||||
LOG.debug("{} closed", this);
|
LOG.debug("Closed {}", this);
|
||||||
|
|
||||||
abort(failure);
|
abort(failure);
|
||||||
}
|
}
|
||||||
|
@ -166,10 +166,8 @@ public class HttpConnectionOverHTTP extends AbstractConnection implements Connec
|
||||||
{
|
{
|
||||||
if (!closed.get())
|
if (!closed.get())
|
||||||
return false;
|
return false;
|
||||||
|
|
||||||
if (sweeps.incrementAndGet() < 4)
|
if (sweeps.incrementAndGet() < 4)
|
||||||
return false;
|
return false;
|
||||||
|
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -21,6 +21,7 @@ package org.eclipse.jetty.client;
|
||||||
import java.util.Arrays;
|
import java.util.Arrays;
|
||||||
import java.util.Collection;
|
import java.util.Collection;
|
||||||
|
|
||||||
|
import org.eclipse.jetty.client.http.HttpClientTransportOverHTTP;
|
||||||
import org.eclipse.jetty.http.HttpScheme;
|
import org.eclipse.jetty.http.HttpScheme;
|
||||||
import org.eclipse.jetty.server.Handler;
|
import org.eclipse.jetty.server.Handler;
|
||||||
import org.eclipse.jetty.server.NetworkConnector;
|
import org.eclipse.jetty.server.NetworkConnector;
|
||||||
|
@ -84,10 +85,15 @@ public abstract class AbstractHttpClientServerTest
|
||||||
}
|
}
|
||||||
|
|
||||||
protected void startClient() throws Exception
|
protected void startClient() throws Exception
|
||||||
|
{
|
||||||
|
startClient(new HttpClientTransportOverHTTP(1));
|
||||||
|
}
|
||||||
|
|
||||||
|
protected void startClient(HttpClientTransport transport) throws Exception
|
||||||
{
|
{
|
||||||
QueuedThreadPool clientThreads = new QueuedThreadPool();
|
QueuedThreadPool clientThreads = new QueuedThreadPool();
|
||||||
clientThreads.setName("client");
|
clientThreads.setName("client");
|
||||||
client = new HttpClient(sslContextFactory);
|
client = new HttpClient(transport, sslContextFactory);
|
||||||
client.setExecutor(clientThreads);
|
client.setExecutor(clientThreads);
|
||||||
client.start();
|
client.start();
|
||||||
}
|
}
|
||||||
|
|
|
@ -881,9 +881,16 @@ public class HttpClientTest extends AbstractHttpClientServerTest
|
||||||
@Test
|
@Test
|
||||||
public void testConnectHostWithMultipleAddresses() throws Exception
|
public void testConnectHostWithMultipleAddresses() throws Exception
|
||||||
{
|
{
|
||||||
// Likely that the DNS for google.com returns multiple addresses.
|
|
||||||
String host = "google.com";
|
String host = "google.com";
|
||||||
Assume.assumeTrue(InetAddress.getAllByName(host).length > 1);
|
try
|
||||||
|
{
|
||||||
|
// Likely that the DNS for google.com returns multiple addresses.
|
||||||
|
Assume.assumeTrue(InetAddress.getAllByName(host).length > 1);
|
||||||
|
}
|
||||||
|
catch (Throwable x)
|
||||||
|
{
|
||||||
|
Assume.assumeNoException(x);
|
||||||
|
}
|
||||||
|
|
||||||
startClient();
|
startClient();
|
||||||
client.setFollowRedirects(false); // Avoid redirects from 80 to 443.
|
client.setFollowRedirects(false); // Avoid redirects from 80 to 443.
|
||||||
|
|
|
@ -21,7 +21,7 @@ package org.eclipse.jetty.client;
|
||||||
import java.io.IOException;
|
import java.io.IOException;
|
||||||
import java.nio.ByteBuffer;
|
import java.nio.ByteBuffer;
|
||||||
import java.util.Arrays;
|
import java.util.Arrays;
|
||||||
import java.util.concurrent.BlockingQueue;
|
import java.util.Queue;
|
||||||
import java.util.concurrent.CountDownLatch;
|
import java.util.concurrent.CountDownLatch;
|
||||||
import java.util.concurrent.TimeUnit;
|
import java.util.concurrent.TimeUnit;
|
||||||
|
|
||||||
|
@ -71,10 +71,10 @@ public class HttpConnectionLifecycleTest extends AbstractHttpClientServerTest
|
||||||
HttpDestinationOverHTTP destination = (HttpDestinationOverHTTP)client.getDestination(scheme, host, port);
|
HttpDestinationOverHTTP destination = (HttpDestinationOverHTTP)client.getDestination(scheme, host, port);
|
||||||
ConnectionPool connectionPool = destination.getConnectionPool();
|
ConnectionPool connectionPool = destination.getConnectionPool();
|
||||||
|
|
||||||
final BlockingQueue<Connection> idleConnections = connectionPool.getIdleConnections();
|
final Queue<Connection> idleConnections = connectionPool.getIdleConnections();
|
||||||
Assert.assertEquals(0, idleConnections.size());
|
Assert.assertEquals(0, idleConnections.size());
|
||||||
|
|
||||||
final BlockingQueue<Connection> activeConnections = connectionPool.getActiveConnections();
|
final Queue<Connection> activeConnections = connectionPool.getActiveConnections();
|
||||||
Assert.assertEquals(0, activeConnections.size());
|
Assert.assertEquals(0, activeConnections.size());
|
||||||
|
|
||||||
final CountDownLatch headersLatch = new CountDownLatch(1);
|
final CountDownLatch headersLatch = new CountDownLatch(1);
|
||||||
|
@ -132,10 +132,10 @@ public class HttpConnectionLifecycleTest extends AbstractHttpClientServerTest
|
||||||
HttpDestinationOverHTTP destination = (HttpDestinationOverHTTP)client.getDestination(scheme, host, port);
|
HttpDestinationOverHTTP destination = (HttpDestinationOverHTTP)client.getDestination(scheme, host, port);
|
||||||
ConnectionPool connectionPool = destination.getConnectionPool();
|
ConnectionPool connectionPool = destination.getConnectionPool();
|
||||||
|
|
||||||
final BlockingQueue<Connection> idleConnections = connectionPool.getIdleConnections();
|
final Queue<Connection> idleConnections = connectionPool.getIdleConnections();
|
||||||
Assert.assertEquals(0, idleConnections.size());
|
Assert.assertEquals(0, idleConnections.size());
|
||||||
|
|
||||||
final BlockingQueue<Connection> activeConnections = connectionPool.getActiveConnections();
|
final Queue<Connection> activeConnections = connectionPool.getActiveConnections();
|
||||||
Assert.assertEquals(0, activeConnections.size());
|
Assert.assertEquals(0, activeConnections.size());
|
||||||
|
|
||||||
final CountDownLatch beginLatch = new CountDownLatch(1);
|
final CountDownLatch beginLatch = new CountDownLatch(1);
|
||||||
|
@ -183,10 +183,10 @@ public class HttpConnectionLifecycleTest extends AbstractHttpClientServerTest
|
||||||
HttpDestinationOverHTTP destination = (HttpDestinationOverHTTP)client.getDestination(scheme, host, port);
|
HttpDestinationOverHTTP destination = (HttpDestinationOverHTTP)client.getDestination(scheme, host, port);
|
||||||
ConnectionPool connectionPool = destination.getConnectionPool();
|
ConnectionPool connectionPool = destination.getConnectionPool();
|
||||||
|
|
||||||
final BlockingQueue<Connection> idleConnections = connectionPool.getIdleConnections();
|
final Queue<Connection> idleConnections = connectionPool.getIdleConnections();
|
||||||
Assert.assertEquals(0, idleConnections.size());
|
Assert.assertEquals(0, idleConnections.size());
|
||||||
|
|
||||||
final BlockingQueue<Connection> activeConnections = connectionPool.getActiveConnections();
|
final Queue<Connection> activeConnections = connectionPool.getActiveConnections();
|
||||||
Assert.assertEquals(0, activeConnections.size());
|
Assert.assertEquals(0, activeConnections.size());
|
||||||
|
|
||||||
final CountDownLatch successLatch = new CountDownLatch(3);
|
final CountDownLatch successLatch = new CountDownLatch(3);
|
||||||
|
@ -243,10 +243,10 @@ public class HttpConnectionLifecycleTest extends AbstractHttpClientServerTest
|
||||||
HttpDestinationOverHTTP destination = (HttpDestinationOverHTTP)client.getDestination(scheme, host, port);
|
HttpDestinationOverHTTP destination = (HttpDestinationOverHTTP)client.getDestination(scheme, host, port);
|
||||||
ConnectionPool connectionPool = destination.getConnectionPool();
|
ConnectionPool connectionPool = destination.getConnectionPool();
|
||||||
|
|
||||||
final BlockingQueue<Connection> idleConnections = connectionPool.getIdleConnections();
|
final Queue<Connection> idleConnections = connectionPool.getIdleConnections();
|
||||||
Assert.assertEquals(0, idleConnections.size());
|
Assert.assertEquals(0, idleConnections.size());
|
||||||
|
|
||||||
final BlockingQueue<Connection> activeConnections = connectionPool.getActiveConnections();
|
final Queue<Connection> activeConnections = connectionPool.getActiveConnections();
|
||||||
Assert.assertEquals(0, activeConnections.size());
|
Assert.assertEquals(0, activeConnections.size());
|
||||||
|
|
||||||
final long delay = 1000;
|
final long delay = 1000;
|
||||||
|
@ -316,10 +316,10 @@ public class HttpConnectionLifecycleTest extends AbstractHttpClientServerTest
|
||||||
HttpDestinationOverHTTP destination = (HttpDestinationOverHTTP)client.getDestination(scheme, host, port);
|
HttpDestinationOverHTTP destination = (HttpDestinationOverHTTP)client.getDestination(scheme, host, port);
|
||||||
ConnectionPool connectionPool = destination.getConnectionPool();
|
ConnectionPool connectionPool = destination.getConnectionPool();
|
||||||
|
|
||||||
final BlockingQueue<Connection> idleConnections = connectionPool.getIdleConnections();
|
final Queue<Connection> idleConnections = connectionPool.getIdleConnections();
|
||||||
Assert.assertEquals(0, idleConnections.size());
|
Assert.assertEquals(0, idleConnections.size());
|
||||||
|
|
||||||
final BlockingQueue<Connection> activeConnections = connectionPool.getActiveConnections();
|
final Queue<Connection> activeConnections = connectionPool.getActiveConnections();
|
||||||
Assert.assertEquals(0, activeConnections.size());
|
Assert.assertEquals(0, activeConnections.size());
|
||||||
|
|
||||||
server.stop();
|
server.stop();
|
||||||
|
@ -369,10 +369,10 @@ public class HttpConnectionLifecycleTest extends AbstractHttpClientServerTest
|
||||||
HttpDestinationOverHTTP destination = (HttpDestinationOverHTTP)client.getDestination(scheme, host, port);
|
HttpDestinationOverHTTP destination = (HttpDestinationOverHTTP)client.getDestination(scheme, host, port);
|
||||||
ConnectionPool connectionPool = destination.getConnectionPool();
|
ConnectionPool connectionPool = destination.getConnectionPool();
|
||||||
|
|
||||||
final BlockingQueue<Connection> idleConnections = connectionPool.getIdleConnections();
|
final Queue<Connection> idleConnections = connectionPool.getIdleConnections();
|
||||||
Assert.assertEquals(0, idleConnections.size());
|
Assert.assertEquals(0, idleConnections.size());
|
||||||
|
|
||||||
final BlockingQueue<Connection> activeConnections = connectionPool.getActiveConnections();
|
final Queue<Connection> activeConnections = connectionPool.getActiveConnections();
|
||||||
Assert.assertEquals(0, activeConnections.size());
|
Assert.assertEquals(0, activeConnections.size());
|
||||||
|
|
||||||
final CountDownLatch latch = new CountDownLatch(1);
|
final CountDownLatch latch = new CountDownLatch(1);
|
||||||
|
@ -419,10 +419,10 @@ public class HttpConnectionLifecycleTest extends AbstractHttpClientServerTest
|
||||||
HttpDestinationOverHTTP destination = (HttpDestinationOverHTTP)client.getDestination(scheme, host, port);
|
HttpDestinationOverHTTP destination = (HttpDestinationOverHTTP)client.getDestination(scheme, host, port);
|
||||||
ConnectionPool connectionPool = destination.getConnectionPool();
|
ConnectionPool connectionPool = destination.getConnectionPool();
|
||||||
|
|
||||||
final BlockingQueue<Connection> idleConnections = connectionPool.getIdleConnections();
|
final Queue<Connection> idleConnections = connectionPool.getIdleConnections();
|
||||||
Assert.assertEquals(0, idleConnections.size());
|
Assert.assertEquals(0, idleConnections.size());
|
||||||
|
|
||||||
final BlockingQueue<Connection> activeConnections = connectionPool.getActiveConnections();
|
final Queue<Connection> activeConnections = connectionPool.getActiveConnections();
|
||||||
Assert.assertEquals(0, activeConnections.size());
|
Assert.assertEquals(0, activeConnections.size());
|
||||||
|
|
||||||
Log.getLogger(HttpConnection.class).info("Expecting java.lang.IllegalStateException: HttpParser{s=CLOSED,...");
|
Log.getLogger(HttpConnection.class).info("Expecting java.lang.IllegalStateException: HttpParser{s=CLOSED,...");
|
||||||
|
@ -449,7 +449,7 @@ public class HttpConnectionLifecycleTest extends AbstractHttpClientServerTest
|
||||||
|
|
||||||
Assert.assertEquals(0, idleConnections.size());
|
Assert.assertEquals(0, idleConnections.size());
|
||||||
Assert.assertEquals(0, activeConnections.size());
|
Assert.assertEquals(0, activeConnections.size());
|
||||||
|
|
||||||
server.stop();
|
server.stop();
|
||||||
}
|
}
|
||||||
finally
|
finally
|
||||||
|
@ -469,10 +469,10 @@ public class HttpConnectionLifecycleTest extends AbstractHttpClientServerTest
|
||||||
HttpDestinationOverHTTP destination = (HttpDestinationOverHTTP)client.getDestination(scheme, host, port);
|
HttpDestinationOverHTTP destination = (HttpDestinationOverHTTP)client.getDestination(scheme, host, port);
|
||||||
ConnectionPool connectionPool = destination.getConnectionPool();
|
ConnectionPool connectionPool = destination.getConnectionPool();
|
||||||
|
|
||||||
final BlockingQueue<Connection> idleConnections = connectionPool.getIdleConnections();
|
final Queue<Connection> idleConnections = connectionPool.getIdleConnections();
|
||||||
Assert.assertEquals(0, idleConnections.size());
|
Assert.assertEquals(0, idleConnections.size());
|
||||||
|
|
||||||
final BlockingQueue<Connection> activeConnections = connectionPool.getActiveConnections();
|
final Queue<Connection> activeConnections = connectionPool.getActiveConnections();
|
||||||
Assert.assertEquals(0, activeConnections.size());
|
Assert.assertEquals(0, activeConnections.size());
|
||||||
|
|
||||||
ContentResponse response = client.newRequest(host, port)
|
ContentResponse response = client.newRequest(host, port)
|
||||||
|
@ -501,10 +501,10 @@ public class HttpConnectionLifecycleTest extends AbstractHttpClientServerTest
|
||||||
HttpDestinationOverHTTP destination = (HttpDestinationOverHTTP)client.getDestination(scheme, host, port);
|
HttpDestinationOverHTTP destination = (HttpDestinationOverHTTP)client.getDestination(scheme, host, port);
|
||||||
ConnectionPool connectionPool = destination.getConnectionPool();
|
ConnectionPool connectionPool = destination.getConnectionPool();
|
||||||
|
|
||||||
final BlockingQueue<Connection> idleConnections = connectionPool.getIdleConnections();
|
final Queue<Connection> idleConnections = connectionPool.getIdleConnections();
|
||||||
Assert.assertEquals(0, idleConnections.size());
|
Assert.assertEquals(0, idleConnections.size());
|
||||||
|
|
||||||
final BlockingQueue<Connection> activeConnections = connectionPool.getActiveConnections();
|
final Queue<Connection> activeConnections = connectionPool.getActiveConnections();
|
||||||
Assert.assertEquals(0, activeConnections.size());
|
Assert.assertEquals(0, activeConnections.size());
|
||||||
|
|
||||||
client.setStrictEventOrdering(false);
|
client.setStrictEventOrdering(false);
|
||||||
|
|
|
@ -0,0 +1,204 @@
|
||||||
|
//
|
||||||
|
// ========================================================================
|
||||||
|
// Copyright (c) 1995-2015 Mort Bay Consulting Pty. Ltd.
|
||||||
|
// ------------------------------------------------------------------------
|
||||||
|
// All rights reserved. This program and the accompanying materials
|
||||||
|
// are made available under the terms of the Eclipse Public License v1.0
|
||||||
|
// and Apache License v2.0 which accompanies this distribution.
|
||||||
|
//
|
||||||
|
// The Eclipse Public License is available at
|
||||||
|
// http://www.eclipse.org/legal/epl-v10.html
|
||||||
|
//
|
||||||
|
// The Apache License v2.0 is available at
|
||||||
|
// http://www.opensource.org/licenses/apache2.0.php
|
||||||
|
//
|
||||||
|
// You may elect to redistribute this code under either of these licenses.
|
||||||
|
// ========================================================================
|
||||||
|
//
|
||||||
|
|
||||||
|
package org.eclipse.jetty.client;
|
||||||
|
|
||||||
|
import java.io.IOException;
|
||||||
|
import java.util.concurrent.CountDownLatch;
|
||||||
|
import java.util.concurrent.TimeUnit;
|
||||||
|
|
||||||
|
import javax.servlet.ServletException;
|
||||||
|
import javax.servlet.http.HttpServletRequest;
|
||||||
|
import javax.servlet.http.HttpServletResponse;
|
||||||
|
|
||||||
|
import org.eclipse.jetty.client.api.ContentResponse;
|
||||||
|
import org.eclipse.jetty.client.api.Request;
|
||||||
|
import org.eclipse.jetty.client.http.HttpClientTransportOverHTTP;
|
||||||
|
import org.eclipse.jetty.client.http.HttpDestinationOverHTTP;
|
||||||
|
import org.eclipse.jetty.client.util.FutureResponseListener;
|
||||||
|
import org.eclipse.jetty.http.HttpHeader;
|
||||||
|
import org.eclipse.jetty.http.HttpHeaderValue;
|
||||||
|
import org.eclipse.jetty.http.HttpStatus;
|
||||||
|
import org.eclipse.jetty.server.Handler;
|
||||||
|
import org.eclipse.jetty.server.handler.AbstractHandler;
|
||||||
|
import org.eclipse.jetty.util.ssl.SslContextFactory;
|
||||||
|
import org.junit.Assert;
|
||||||
|
import org.junit.Test;
|
||||||
|
|
||||||
|
public class ValidatingConnectionPoolTest extends AbstractHttpClientServerTest
|
||||||
|
{
|
||||||
|
public ValidatingConnectionPoolTest(SslContextFactory sslContextFactory)
|
||||||
|
{
|
||||||
|
super(sslContextFactory);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
protected void startClient() throws Exception
|
||||||
|
{
|
||||||
|
startClient(new ValidatingHttpClientTransportOverHTTP(1000));
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void testRequestAfterValidation() throws Exception
|
||||||
|
{
|
||||||
|
start(new EmptyServerHandler());
|
||||||
|
|
||||||
|
client.setMaxConnectionsPerDestination(1);
|
||||||
|
|
||||||
|
ContentResponse response = client.newRequest("localhost", connector.getLocalPort())
|
||||||
|
.scheme(scheme)
|
||||||
|
.send();
|
||||||
|
Assert.assertEquals(200, response.getStatus());
|
||||||
|
|
||||||
|
// The second request should be sent after the validating timeout.
|
||||||
|
response = client.newRequest("localhost", connector.getLocalPort())
|
||||||
|
.scheme(scheme)
|
||||||
|
.send();
|
||||||
|
Assert.assertEquals(200, response.getStatus());
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void testServerClosesConnectionAfterRedirectWithoutConnectionCloseHeader() throws Exception
|
||||||
|
{
|
||||||
|
start(new AbstractHandler()
|
||||||
|
{
|
||||||
|
@Override
|
||||||
|
public void handle(String target, org.eclipse.jetty.server.Request baseRequest, HttpServletRequest request, HttpServletResponse response) throws IOException, ServletException
|
||||||
|
{
|
||||||
|
baseRequest.setHandled(true);
|
||||||
|
if (target.endsWith("/redirect"))
|
||||||
|
{
|
||||||
|
response.setStatus(HttpStatus.TEMPORARY_REDIRECT_307);
|
||||||
|
response.setContentLength(0);
|
||||||
|
response.setHeader(HttpHeader.LOCATION.asString(), scheme + "://localhost:" + connector.getLocalPort() + "/");
|
||||||
|
response.flushBuffer();
|
||||||
|
baseRequest.getHttpChannel().getEndPoint().shutdownOutput();
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
response.setStatus(HttpStatus.OK_200);
|
||||||
|
response.setContentLength(0);
|
||||||
|
response.setHeader(HttpHeader.CONNECTION.asString(), HttpHeaderValue.CLOSE.asString());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
ContentResponse response = client.newRequest("localhost", connector.getLocalPort())
|
||||||
|
.scheme(scheme)
|
||||||
|
.path("/redirect")
|
||||||
|
.send();
|
||||||
|
Assert.assertEquals(200, response.getStatus());
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void testServerClosesConnectionAfterResponseWithQueuedRequestWithMaxConnectionsWithConnectionCloseHeader() throws Exception
|
||||||
|
{
|
||||||
|
testServerClosesConnectionAfterResponseWithQueuedRequestWithMaxConnections(new AbstractHandler()
|
||||||
|
{
|
||||||
|
@Override
|
||||||
|
public void handle(String target, org.eclipse.jetty.server.Request baseRequest, HttpServletRequest request, HttpServletResponse response) throws IOException, ServletException
|
||||||
|
{
|
||||||
|
baseRequest.setHandled(true);
|
||||||
|
response.setStatus(HttpStatus.OK_200);
|
||||||
|
response.setContentLength(0);
|
||||||
|
response.setHeader(HttpHeader.CONNECTION.asString(), HttpHeaderValue.CLOSE.asString());
|
||||||
|
}
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void testServerClosesConnectionAfterResponseWithQueuedRequestWithMaxConnectionsWithoutConnectionCloseHeader() throws Exception
|
||||||
|
{
|
||||||
|
testServerClosesConnectionAfterResponseWithQueuedRequestWithMaxConnections(new AbstractHandler()
|
||||||
|
{
|
||||||
|
@Override
|
||||||
|
public void handle(String target, org.eclipse.jetty.server.Request baseRequest, HttpServletRequest request, HttpServletResponse response) throws IOException, ServletException
|
||||||
|
{
|
||||||
|
baseRequest.setHandled(true);
|
||||||
|
response.setStatus(HttpStatus.OK_200);
|
||||||
|
response.setContentLength(0);
|
||||||
|
response.flushBuffer();
|
||||||
|
baseRequest.getHttpChannel().getEndPoint().shutdownOutput();
|
||||||
|
}
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
private void testServerClosesConnectionAfterResponseWithQueuedRequestWithMaxConnections(Handler handler) throws Exception
|
||||||
|
{
|
||||||
|
start(handler);
|
||||||
|
client.setMaxConnectionsPerDestination(1);
|
||||||
|
|
||||||
|
final CountDownLatch latch = new CountDownLatch(1);
|
||||||
|
Request request1 = client.newRequest("localhost", connector.getLocalPort())
|
||||||
|
.scheme(scheme)
|
||||||
|
.path("/one")
|
||||||
|
.onRequestBegin(r ->
|
||||||
|
{
|
||||||
|
try
|
||||||
|
{
|
||||||
|
latch.await();
|
||||||
|
}
|
||||||
|
catch (InterruptedException x)
|
||||||
|
{
|
||||||
|
r.abort(x);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
FutureResponseListener listener1 = new FutureResponseListener(request1);
|
||||||
|
request1.send(listener1);
|
||||||
|
|
||||||
|
Request request2 = client.newRequest("localhost", connector.getLocalPort())
|
||||||
|
.scheme(scheme)
|
||||||
|
.path("/two");
|
||||||
|
FutureResponseListener listener2 = new FutureResponseListener(request2);
|
||||||
|
request2.send(listener2);
|
||||||
|
|
||||||
|
// Now we have one request about to be sent, and one queued.
|
||||||
|
|
||||||
|
latch.countDown();
|
||||||
|
|
||||||
|
ContentResponse response1 = listener1.get(5, TimeUnit.SECONDS);
|
||||||
|
Assert.assertEquals(200, response1.getStatus());
|
||||||
|
|
||||||
|
ContentResponse response2 = listener2.get(5, TimeUnit.SECONDS);
|
||||||
|
Assert.assertEquals(200, response2.getStatus());
|
||||||
|
}
|
||||||
|
|
||||||
|
private static class ValidatingHttpClientTransportOverHTTP extends HttpClientTransportOverHTTP
|
||||||
|
{
|
||||||
|
private final long timeout;
|
||||||
|
|
||||||
|
public ValidatingHttpClientTransportOverHTTP(long timeout)
|
||||||
|
{
|
||||||
|
super(1);
|
||||||
|
this.timeout = timeout;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public HttpDestination newHttpDestination(Origin origin)
|
||||||
|
{
|
||||||
|
return new HttpDestinationOverHTTP(getHttpClient(), origin)
|
||||||
|
{
|
||||||
|
@Override
|
||||||
|
protected ConnectionPool newConnectionPool(HttpClient client)
|
||||||
|
{
|
||||||
|
return new ValidatingConnectionPool(this, client.getMaxConnectionsPerDestination(), this, client.getScheduler(), timeout);
|
||||||
|
}
|
||||||
|
};
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
|
@ -18,6 +18,7 @@
|
||||||
|
|
||||||
package org.eclipse.jetty.client.http;
|
package org.eclipse.jetty.client.http;
|
||||||
|
|
||||||
|
import java.util.Queue;
|
||||||
import java.util.concurrent.CountDownLatch;
|
import java.util.concurrent.CountDownLatch;
|
||||||
import java.util.concurrent.RejectedExecutionException;
|
import java.util.concurrent.RejectedExecutionException;
|
||||||
import java.util.concurrent.TimeUnit;
|
import java.util.concurrent.TimeUnit;
|
||||||
|
@ -62,7 +63,7 @@ public class HttpDestinationOverHTTPTest extends AbstractHttpClientServerTest
|
||||||
if (connection == null)
|
if (connection == null)
|
||||||
{
|
{
|
||||||
// There are no queued requests, so the newly created connection will be idle
|
// There are no queued requests, so the newly created connection will be idle
|
||||||
connection = destination.getConnectionPool().getIdleConnections().poll(5, TimeUnit.SECONDS);
|
connection = timedPoll(destination.getConnectionPool().getIdleConnections(), 5, TimeUnit.SECONDS);
|
||||||
}
|
}
|
||||||
Assert.assertNotNull(connection);
|
Assert.assertNotNull(connection);
|
||||||
}
|
}
|
||||||
|
@ -133,9 +134,10 @@ public class HttpDestinationOverHTTPTest extends AbstractHttpClientServerTest
|
||||||
latch.countDown();
|
latch.countDown();
|
||||||
|
|
||||||
// There must be 2 idle connections.
|
// There must be 2 idle connections.
|
||||||
Connection connection = destination.getConnectionPool().getIdleConnections().poll(5, TimeUnit.SECONDS);
|
Queue<Connection> idleConnections = destination.getConnectionPool().getIdleConnections();
|
||||||
|
Connection connection = timedPoll(idleConnections, 5, TimeUnit.SECONDS);
|
||||||
Assert.assertNotNull(connection);
|
Assert.assertNotNull(connection);
|
||||||
connection = destination.getConnectionPool().getIdleConnections().poll(5, TimeUnit.SECONDS);
|
connection = timedPoll(idleConnections, 5, TimeUnit.SECONDS);
|
||||||
Assert.assertNotNull(connection);
|
Assert.assertNotNull(connection);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -272,4 +274,17 @@ public class HttpDestinationOverHTTPTest extends AbstractHttpClientServerTest
|
||||||
destinationAfter = client.getDestination(scheme, host, port);
|
destinationAfter = client.getDestination(scheme, host, port);
|
||||||
Assert.assertNotSame(destinationBefore, destinationAfter);
|
Assert.assertNotSame(destinationBefore, destinationAfter);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private Connection timedPoll(Queue<Connection> connections, long time, TimeUnit unit) throws InterruptedException
|
||||||
|
{
|
||||||
|
long start = System.nanoTime();
|
||||||
|
while (unit.toNanos(time) > System.nanoTime() - start)
|
||||||
|
{
|
||||||
|
Connection connection = connections.poll();
|
||||||
|
if (connection != null)
|
||||||
|
return connection;
|
||||||
|
TimeUnit.MILLISECONDS.sleep(5);
|
||||||
|
}
|
||||||
|
return connections.poll();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -2,7 +2,7 @@
|
||||||
<parent>
|
<parent>
|
||||||
<groupId>org.eclipse.jetty</groupId>
|
<groupId>org.eclipse.jetty</groupId>
|
||||||
<artifactId>jetty-project</artifactId>
|
<artifactId>jetty-project</artifactId>
|
||||||
<version>9.3.3-SNAPSHOT</version>
|
<version>9.3.4-SNAPSHOT</version>
|
||||||
</parent>
|
</parent>
|
||||||
<modelVersion>4.0.0</modelVersion>
|
<modelVersion>4.0.0</modelVersion>
|
||||||
<artifactId>jetty-continuation</artifactId>
|
<artifactId>jetty-continuation</artifactId>
|
||||||
|
|
|
@ -2,7 +2,7 @@
|
||||||
<parent>
|
<parent>
|
||||||
<groupId>org.eclipse.jetty</groupId>
|
<groupId>org.eclipse.jetty</groupId>
|
||||||
<artifactId>jetty-project</artifactId>
|
<artifactId>jetty-project</artifactId>
|
||||||
<version>9.3.3-SNAPSHOT</version>
|
<version>9.3.4-SNAPSHOT</version>
|
||||||
</parent>
|
</parent>
|
||||||
<modelVersion>4.0.0</modelVersion>
|
<modelVersion>4.0.0</modelVersion>
|
||||||
<artifactId>jetty-deploy</artifactId>
|
<artifactId>jetty-deploy</artifactId>
|
||||||
|
|
|
@ -3,7 +3,7 @@
|
||||||
<parent>
|
<parent>
|
||||||
<groupId>org.eclipse.jetty</groupId>
|
<groupId>org.eclipse.jetty</groupId>
|
||||||
<artifactId>jetty-project</artifactId>
|
<artifactId>jetty-project</artifactId>
|
||||||
<version>9.3.3-SNAPSHOT</version>
|
<version>9.3.4-SNAPSHOT</version>
|
||||||
</parent>
|
</parent>
|
||||||
<artifactId>jetty-distribution</artifactId>
|
<artifactId>jetty-distribution</artifactId>
|
||||||
<name>Jetty :: Distribution Assemblies</name>
|
<name>Jetty :: Distribution Assemblies</name>
|
||||||
|
|
|
@ -3,7 +3,7 @@
|
||||||
<parent>
|
<parent>
|
||||||
<groupId>org.eclipse.jetty.fcgi</groupId>
|
<groupId>org.eclipse.jetty.fcgi</groupId>
|
||||||
<artifactId>fcgi-parent</artifactId>
|
<artifactId>fcgi-parent</artifactId>
|
||||||
<version>9.3.3-SNAPSHOT</version>
|
<version>9.3.4-SNAPSHOT</version>
|
||||||
</parent>
|
</parent>
|
||||||
|
|
||||||
<modelVersion>4.0.0</modelVersion>
|
<modelVersion>4.0.0</modelVersion>
|
||||||
|
|
|
@ -3,7 +3,7 @@
|
||||||
<parent>
|
<parent>
|
||||||
<groupId>org.eclipse.jetty.fcgi</groupId>
|
<groupId>org.eclipse.jetty.fcgi</groupId>
|
||||||
<artifactId>fcgi-parent</artifactId>
|
<artifactId>fcgi-parent</artifactId>
|
||||||
<version>9.3.3-SNAPSHOT</version>
|
<version>9.3.4-SNAPSHOT</version>
|
||||||
</parent>
|
</parent>
|
||||||
|
|
||||||
<modelVersion>4.0.0</modelVersion>
|
<modelVersion>4.0.0</modelVersion>
|
||||||
|
|
|
@ -3,7 +3,7 @@
|
||||||
<parent>
|
<parent>
|
||||||
<groupId>org.eclipse.jetty</groupId>
|
<groupId>org.eclipse.jetty</groupId>
|
||||||
<artifactId>jetty-project</artifactId>
|
<artifactId>jetty-project</artifactId>
|
||||||
<version>9.3.3-SNAPSHOT</version>
|
<version>9.3.4-SNAPSHOT</version>
|
||||||
</parent>
|
</parent>
|
||||||
|
|
||||||
<modelVersion>4.0.0</modelVersion>
|
<modelVersion>4.0.0</modelVersion>
|
||||||
|
|
|
@ -2,7 +2,7 @@
|
||||||
<parent>
|
<parent>
|
||||||
<groupId>org.eclipse.jetty</groupId>
|
<groupId>org.eclipse.jetty</groupId>
|
||||||
<artifactId>jetty-project</artifactId>
|
<artifactId>jetty-project</artifactId>
|
||||||
<version>9.3.3-SNAPSHOT</version>
|
<version>9.3.4-SNAPSHOT</version>
|
||||||
</parent>
|
</parent>
|
||||||
<modelVersion>4.0.0</modelVersion>
|
<modelVersion>4.0.0</modelVersion>
|
||||||
<artifactId>jetty-http-spi</artifactId>
|
<artifactId>jetty-http-spi</artifactId>
|
||||||
|
|
|
@ -3,7 +3,7 @@
|
||||||
<parent>
|
<parent>
|
||||||
<artifactId>jetty-project</artifactId>
|
<artifactId>jetty-project</artifactId>
|
||||||
<groupId>org.eclipse.jetty</groupId>
|
<groupId>org.eclipse.jetty</groupId>
|
||||||
<version>9.3.3-SNAPSHOT</version>
|
<version>9.3.4-SNAPSHOT</version>
|
||||||
</parent>
|
</parent>
|
||||||
<modelVersion>4.0.0</modelVersion>
|
<modelVersion>4.0.0</modelVersion>
|
||||||
<artifactId>jetty-http</artifactId>
|
<artifactId>jetty-http</artifactId>
|
||||||
|
|
|
@ -86,6 +86,19 @@ public class HttpParserTest
|
||||||
assertEquals(HttpMethod.GET,HttpMethod.lookAheadGet(b));
|
assertEquals(HttpMethod.GET,HttpMethod.lookAheadGet(b));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void testLineParse_Mock_IP() throws Exception
|
||||||
|
{
|
||||||
|
ByteBuffer buffer= BufferUtil.toBuffer("POST /mock/127.0.0.1 HTTP/1.1\015\012" + "\015\012");
|
||||||
|
|
||||||
|
HttpParser.RequestHandler handler = new Handler();
|
||||||
|
HttpParser parser= new HttpParser(handler);
|
||||||
|
parseAll(parser,buffer);
|
||||||
|
assertEquals("POST", _methodOrVersion);
|
||||||
|
assertEquals("/mock/127.0.0.1", _uriOrStatus);
|
||||||
|
assertEquals("HTTP/1.1", _versionOrReason);
|
||||||
|
assertEquals(-1, _headers);
|
||||||
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
public void testLineParse0() throws Exception
|
public void testLineParse0() throws Exception
|
||||||
|
|
|
@ -3,7 +3,7 @@
|
||||||
<parent>
|
<parent>
|
||||||
<groupId>org.eclipse.jetty.http2</groupId>
|
<groupId>org.eclipse.jetty.http2</groupId>
|
||||||
<artifactId>http2-parent</artifactId>
|
<artifactId>http2-parent</artifactId>
|
||||||
<version>9.3.3-SNAPSHOT</version>
|
<version>9.3.4-SNAPSHOT</version>
|
||||||
</parent>
|
</parent>
|
||||||
|
|
||||||
<modelVersion>4.0.0</modelVersion>
|
<modelVersion>4.0.0</modelVersion>
|
||||||
|
|
|
@ -3,7 +3,7 @@
|
||||||
<parent>
|
<parent>
|
||||||
<groupId>org.eclipse.jetty.http2</groupId>
|
<groupId>org.eclipse.jetty.http2</groupId>
|
||||||
<artifactId>http2-parent</artifactId>
|
<artifactId>http2-parent</artifactId>
|
||||||
<version>9.3.3-SNAPSHOT</version>
|
<version>9.3.4-SNAPSHOT</version>
|
||||||
</parent>
|
</parent>
|
||||||
|
|
||||||
<modelVersion>4.0.0</modelVersion>
|
<modelVersion>4.0.0</modelVersion>
|
||||||
|
|
|
@ -3,7 +3,7 @@
|
||||||
<parent>
|
<parent>
|
||||||
<groupId>org.eclipse.jetty.http2</groupId>
|
<groupId>org.eclipse.jetty.http2</groupId>
|
||||||
<artifactId>http2-parent</artifactId>
|
<artifactId>http2-parent</artifactId>
|
||||||
<version>9.3.3-SNAPSHOT</version>
|
<version>9.3.4-SNAPSHOT</version>
|
||||||
</parent>
|
</parent>
|
||||||
|
|
||||||
<modelVersion>4.0.0</modelVersion>
|
<modelVersion>4.0.0</modelVersion>
|
||||||
|
|
|
@ -3,7 +3,7 @@
|
||||||
<parent>
|
<parent>
|
||||||
<groupId>org.eclipse.jetty.http2</groupId>
|
<groupId>org.eclipse.jetty.http2</groupId>
|
||||||
<artifactId>http2-parent</artifactId>
|
<artifactId>http2-parent</artifactId>
|
||||||
<version>9.3.3-SNAPSHOT</version>
|
<version>9.3.4-SNAPSHOT</version>
|
||||||
</parent>
|
</parent>
|
||||||
|
|
||||||
<modelVersion>4.0.0</modelVersion>
|
<modelVersion>4.0.0</modelVersion>
|
||||||
|
|
|
@ -3,7 +3,7 @@
|
||||||
<parent>
|
<parent>
|
||||||
<groupId>org.eclipse.jetty.http2</groupId>
|
<groupId>org.eclipse.jetty.http2</groupId>
|
||||||
<artifactId>http2-parent</artifactId>
|
<artifactId>http2-parent</artifactId>
|
||||||
<version>9.3.3-SNAPSHOT</version>
|
<version>9.3.4-SNAPSHOT</version>
|
||||||
</parent>
|
</parent>
|
||||||
|
|
||||||
<modelVersion>4.0.0</modelVersion>
|
<modelVersion>4.0.0</modelVersion>
|
||||||
|
|
|
@ -3,7 +3,7 @@
|
||||||
<parent>
|
<parent>
|
||||||
<groupId>org.eclipse.jetty.http2</groupId>
|
<groupId>org.eclipse.jetty.http2</groupId>
|
||||||
<artifactId>http2-parent</artifactId>
|
<artifactId>http2-parent</artifactId>
|
||||||
<version>9.3.3-SNAPSHOT</version>
|
<version>9.3.4-SNAPSHOT</version>
|
||||||
</parent>
|
</parent>
|
||||||
|
|
||||||
<modelVersion>4.0.0</modelVersion>
|
<modelVersion>4.0.0</modelVersion>
|
||||||
|
|
|
@ -3,7 +3,7 @@
|
||||||
<parent>
|
<parent>
|
||||||
<artifactId>jetty-project</artifactId>
|
<artifactId>jetty-project</artifactId>
|
||||||
<groupId>org.eclipse.jetty</groupId>
|
<groupId>org.eclipse.jetty</groupId>
|
||||||
<version>9.3.3-SNAPSHOT</version>
|
<version>9.3.4-SNAPSHOT</version>
|
||||||
</parent>
|
</parent>
|
||||||
|
|
||||||
<modelVersion>4.0.0</modelVersion>
|
<modelVersion>4.0.0</modelVersion>
|
||||||
|
|
|
@ -2,7 +2,7 @@
|
||||||
<parent>
|
<parent>
|
||||||
<groupId>org.eclipse.jetty</groupId>
|
<groupId>org.eclipse.jetty</groupId>
|
||||||
<artifactId>jetty-project</artifactId>
|
<artifactId>jetty-project</artifactId>
|
||||||
<version>9.3.3-SNAPSHOT</version>
|
<version>9.3.4-SNAPSHOT</version>
|
||||||
</parent>
|
</parent>
|
||||||
<modelVersion>4.0.0</modelVersion>
|
<modelVersion>4.0.0</modelVersion>
|
||||||
<artifactId>jetty-infinispan</artifactId>
|
<artifactId>jetty-infinispan</artifactId>
|
||||||
|
|
|
@ -2,7 +2,7 @@
|
||||||
<parent>
|
<parent>
|
||||||
<artifactId>jetty-project</artifactId>
|
<artifactId>jetty-project</artifactId>
|
||||||
<groupId>org.eclipse.jetty</groupId>
|
<groupId>org.eclipse.jetty</groupId>
|
||||||
<version>9.3.3-SNAPSHOT</version>
|
<version>9.3.4-SNAPSHOT</version>
|
||||||
</parent>
|
</parent>
|
||||||
<modelVersion>4.0.0</modelVersion>
|
<modelVersion>4.0.0</modelVersion>
|
||||||
<artifactId>jetty-io</artifactId>
|
<artifactId>jetty-io</artifactId>
|
||||||
|
|
|
@ -2,7 +2,7 @@
|
||||||
<parent>
|
<parent>
|
||||||
<groupId>org.eclipse.jetty</groupId>
|
<groupId>org.eclipse.jetty</groupId>
|
||||||
<artifactId>jetty-project</artifactId>
|
<artifactId>jetty-project</artifactId>
|
||||||
<version>9.3.3-SNAPSHOT</version>
|
<version>9.3.4-SNAPSHOT</version>
|
||||||
</parent>
|
</parent>
|
||||||
<modelVersion>4.0.0</modelVersion>
|
<modelVersion>4.0.0</modelVersion>
|
||||||
<artifactId>jetty-jaas</artifactId>
|
<artifactId>jetty-jaas</artifactId>
|
||||||
|
|
|
@ -2,7 +2,7 @@
|
||||||
<parent>
|
<parent>
|
||||||
<groupId>org.eclipse.jetty</groupId>
|
<groupId>org.eclipse.jetty</groupId>
|
||||||
<artifactId>jetty-project</artifactId>
|
<artifactId>jetty-project</artifactId>
|
||||||
<version>9.3.3-SNAPSHOT</version>
|
<version>9.3.4-SNAPSHOT</version>
|
||||||
</parent>
|
</parent>
|
||||||
<modelVersion>4.0.0</modelVersion>
|
<modelVersion>4.0.0</modelVersion>
|
||||||
<artifactId>jetty-jaspi</artifactId>
|
<artifactId>jetty-jaspi</artifactId>
|
||||||
|
|
|
@ -2,7 +2,7 @@
|
||||||
<parent>
|
<parent>
|
||||||
<groupId>org.eclipse.jetty</groupId>
|
<groupId>org.eclipse.jetty</groupId>
|
||||||
<artifactId>jetty-project</artifactId>
|
<artifactId>jetty-project</artifactId>
|
||||||
<version>9.3.3-SNAPSHOT</version>
|
<version>9.3.4-SNAPSHOT</version>
|
||||||
</parent>
|
</parent>
|
||||||
<modelVersion>4.0.0</modelVersion>
|
<modelVersion>4.0.0</modelVersion>
|
||||||
<artifactId>jetty-jmx</artifactId>
|
<artifactId>jetty-jmx</artifactId>
|
||||||
|
|
|
@ -2,7 +2,7 @@
|
||||||
<parent>
|
<parent>
|
||||||
<groupId>org.eclipse.jetty</groupId>
|
<groupId>org.eclipse.jetty</groupId>
|
||||||
<artifactId>jetty-project</artifactId>
|
<artifactId>jetty-project</artifactId>
|
||||||
<version>9.3.3-SNAPSHOT</version>
|
<version>9.3.4-SNAPSHOT</version>
|
||||||
</parent>
|
</parent>
|
||||||
<modelVersion>4.0.0</modelVersion>
|
<modelVersion>4.0.0</modelVersion>
|
||||||
<artifactId>jetty-jndi</artifactId>
|
<artifactId>jetty-jndi</artifactId>
|
||||||
|
|
|
@ -2,7 +2,7 @@
|
||||||
<parent>
|
<parent>
|
||||||
<groupId>org.eclipse.jetty</groupId>
|
<groupId>org.eclipse.jetty</groupId>
|
||||||
<artifactId>jetty-project</artifactId>
|
<artifactId>jetty-project</artifactId>
|
||||||
<version>9.3.3-SNAPSHOT</version>
|
<version>9.3.4-SNAPSHOT</version>
|
||||||
</parent>
|
</parent>
|
||||||
<modelVersion>4.0.0</modelVersion>
|
<modelVersion>4.0.0</modelVersion>
|
||||||
<artifactId>jetty-jspc-maven-plugin</artifactId>
|
<artifactId>jetty-jspc-maven-plugin</artifactId>
|
||||||
|
|
|
@ -2,7 +2,7 @@
|
||||||
<parent>
|
<parent>
|
||||||
<groupId>org.eclipse.jetty</groupId>
|
<groupId>org.eclipse.jetty</groupId>
|
||||||
<artifactId>jetty-project</artifactId>
|
<artifactId>jetty-project</artifactId>
|
||||||
<version>9.3.3-SNAPSHOT</version>
|
<version>9.3.4-SNAPSHOT</version>
|
||||||
</parent>
|
</parent>
|
||||||
<modelVersion>4.0.0</modelVersion>
|
<modelVersion>4.0.0</modelVersion>
|
||||||
<artifactId>jetty-maven-plugin</artifactId>
|
<artifactId>jetty-maven-plugin</artifactId>
|
||||||
|
|
|
@ -19,7 +19,7 @@
|
||||||
<parent>
|
<parent>
|
||||||
<groupId>org.eclipse.jetty</groupId>
|
<groupId>org.eclipse.jetty</groupId>
|
||||||
<artifactId>jetty-project</artifactId>
|
<artifactId>jetty-project</artifactId>
|
||||||
<version>9.3.3-SNAPSHOT</version>
|
<version>9.3.4-SNAPSHOT</version>
|
||||||
</parent>
|
</parent>
|
||||||
<modelVersion>4.0.0</modelVersion>
|
<modelVersion>4.0.0</modelVersion>
|
||||||
<artifactId>jetty-monitor</artifactId>
|
<artifactId>jetty-monitor</artifactId>
|
||||||
|
|
|
@ -2,7 +2,7 @@
|
||||||
<parent>
|
<parent>
|
||||||
<groupId>org.eclipse.jetty</groupId>
|
<groupId>org.eclipse.jetty</groupId>
|
||||||
<artifactId>jetty-project</artifactId>
|
<artifactId>jetty-project</artifactId>
|
||||||
<version>9.3.3-SNAPSHOT</version>
|
<version>9.3.4-SNAPSHOT</version>
|
||||||
</parent>
|
</parent>
|
||||||
<modelVersion>4.0.0</modelVersion>
|
<modelVersion>4.0.0</modelVersion>
|
||||||
<artifactId>jetty-nosql</artifactId>
|
<artifactId>jetty-nosql</artifactId>
|
||||||
|
|
|
@ -2,7 +2,7 @@
|
||||||
<parent>
|
<parent>
|
||||||
<groupId>org.eclipse.jetty.osgi</groupId>
|
<groupId>org.eclipse.jetty.osgi</groupId>
|
||||||
<artifactId>jetty-osgi-project</artifactId>
|
<artifactId>jetty-osgi-project</artifactId>
|
||||||
<version>9.3.3-SNAPSHOT</version>
|
<version>9.3.4-SNAPSHOT</version>
|
||||||
</parent>
|
</parent>
|
||||||
<modelVersion>4.0.0</modelVersion>
|
<modelVersion>4.0.0</modelVersion>
|
||||||
<artifactId>jetty-osgi-alpn</artifactId>
|
<artifactId>jetty-osgi-alpn</artifactId>
|
||||||
|
|
|
@ -2,7 +2,7 @@
|
||||||
<parent>
|
<parent>
|
||||||
<groupId>org.eclipse.jetty.osgi</groupId>
|
<groupId>org.eclipse.jetty.osgi</groupId>
|
||||||
<artifactId>jetty-osgi-project</artifactId>
|
<artifactId>jetty-osgi-project</artifactId>
|
||||||
<version>9.3.3-SNAPSHOT</version>
|
<version>9.3.4-SNAPSHOT</version>
|
||||||
</parent>
|
</parent>
|
||||||
<modelVersion>4.0.0</modelVersion>
|
<modelVersion>4.0.0</modelVersion>
|
||||||
<artifactId>jetty-osgi-boot-jsp</artifactId>
|
<artifactId>jetty-osgi-boot-jsp</artifactId>
|
||||||
|
|
|
@ -2,7 +2,7 @@
|
||||||
<parent>
|
<parent>
|
||||||
<groupId>org.eclipse.jetty.osgi</groupId>
|
<groupId>org.eclipse.jetty.osgi</groupId>
|
||||||
<artifactId>jetty-osgi-project</artifactId>
|
<artifactId>jetty-osgi-project</artifactId>
|
||||||
<version>9.3.3-SNAPSHOT</version>
|
<version>9.3.4-SNAPSHOT</version>
|
||||||
<relativePath>../pom.xml</relativePath>
|
<relativePath>../pom.xml</relativePath>
|
||||||
</parent>
|
</parent>
|
||||||
<modelVersion>4.0.0</modelVersion>
|
<modelVersion>4.0.0</modelVersion>
|
||||||
|
|
|
@ -2,7 +2,7 @@
|
||||||
<parent>
|
<parent>
|
||||||
<groupId>org.eclipse.jetty.osgi</groupId>
|
<groupId>org.eclipse.jetty.osgi</groupId>
|
||||||
<artifactId>jetty-osgi-project</artifactId>
|
<artifactId>jetty-osgi-project</artifactId>
|
||||||
<version>9.3.3-SNAPSHOT</version>
|
<version>9.3.4-SNAPSHOT</version>
|
||||||
</parent>
|
</parent>
|
||||||
<modelVersion>4.0.0</modelVersion>
|
<modelVersion>4.0.0</modelVersion>
|
||||||
<artifactId>jetty-osgi-boot</artifactId>
|
<artifactId>jetty-osgi-boot</artifactId>
|
||||||
|
|
|
@ -2,7 +2,7 @@
|
||||||
<parent>
|
<parent>
|
||||||
<groupId>org.eclipse.jetty.osgi</groupId>
|
<groupId>org.eclipse.jetty.osgi</groupId>
|
||||||
<artifactId>jetty-osgi-project</artifactId>
|
<artifactId>jetty-osgi-project</artifactId>
|
||||||
<version>9.3.3-SNAPSHOT</version>
|
<version>9.3.4-SNAPSHOT</version>
|
||||||
</parent>
|
</parent>
|
||||||
<modelVersion>4.0.0</modelVersion>
|
<modelVersion>4.0.0</modelVersion>
|
||||||
<artifactId>jetty-httpservice</artifactId>
|
<artifactId>jetty-httpservice</artifactId>
|
||||||
|
|
|
@ -3,7 +3,7 @@
|
||||||
<parent>
|
<parent>
|
||||||
<groupId>org.eclipse.jetty</groupId>
|
<groupId>org.eclipse.jetty</groupId>
|
||||||
<artifactId>jetty-project</artifactId>
|
<artifactId>jetty-project</artifactId>
|
||||||
<version>9.3.3-SNAPSHOT</version>
|
<version>9.3.4-SNAPSHOT</version>
|
||||||
</parent>
|
</parent>
|
||||||
<groupId>org.eclipse.jetty.osgi</groupId>
|
<groupId>org.eclipse.jetty.osgi</groupId>
|
||||||
<artifactId>jetty-osgi-project</artifactId>
|
<artifactId>jetty-osgi-project</artifactId>
|
||||||
|
|
|
@ -2,7 +2,7 @@
|
||||||
<parent>
|
<parent>
|
||||||
<groupId>org.eclipse.jetty.osgi</groupId>
|
<groupId>org.eclipse.jetty.osgi</groupId>
|
||||||
<artifactId>jetty-osgi-project</artifactId>
|
<artifactId>jetty-osgi-project</artifactId>
|
||||||
<version>9.3.3-SNAPSHOT</version>
|
<version>9.3.4-SNAPSHOT</version>
|
||||||
</parent>
|
</parent>
|
||||||
<modelVersion>4.0.0</modelVersion>
|
<modelVersion>4.0.0</modelVersion>
|
||||||
<artifactId>test-jetty-osgi-context</artifactId>
|
<artifactId>test-jetty-osgi-context</artifactId>
|
||||||
|
|
|
@ -2,7 +2,7 @@
|
||||||
<parent>
|
<parent>
|
||||||
<groupId>org.eclipse.jetty.osgi</groupId>
|
<groupId>org.eclipse.jetty.osgi</groupId>
|
||||||
<artifactId>jetty-osgi-project</artifactId>
|
<artifactId>jetty-osgi-project</artifactId>
|
||||||
<version>9.3.3-SNAPSHOT</version>
|
<version>9.3.4-SNAPSHOT</version>
|
||||||
<relativePath>../pom.xml</relativePath>
|
<relativePath>../pom.xml</relativePath>
|
||||||
</parent>
|
</parent>
|
||||||
<modelVersion>4.0.0</modelVersion>
|
<modelVersion>4.0.0</modelVersion>
|
||||||
|
|
|
@ -2,7 +2,7 @@
|
||||||
<parent>
|
<parent>
|
||||||
<groupId>org.eclipse.jetty.osgi</groupId>
|
<groupId>org.eclipse.jetty.osgi</groupId>
|
||||||
<artifactId>jetty-osgi-project</artifactId>
|
<artifactId>jetty-osgi-project</artifactId>
|
||||||
<version>9.3.3-SNAPSHOT</version>
|
<version>9.3.4-SNAPSHOT</version>
|
||||||
<relativePath>../pom.xml</relativePath>
|
<relativePath>../pom.xml</relativePath>
|
||||||
</parent>
|
</parent>
|
||||||
<modelVersion>4.0.0</modelVersion>
|
<modelVersion>4.0.0</modelVersion>
|
||||||
|
|
|
@ -2,7 +2,7 @@
|
||||||
<parent>
|
<parent>
|
||||||
<groupId>org.eclipse.jetty</groupId>
|
<groupId>org.eclipse.jetty</groupId>
|
||||||
<artifactId>jetty-project</artifactId>
|
<artifactId>jetty-project</artifactId>
|
||||||
<version>9.3.3-SNAPSHOT</version>
|
<version>9.3.4-SNAPSHOT</version>
|
||||||
</parent>
|
</parent>
|
||||||
<modelVersion>4.0.0</modelVersion>
|
<modelVersion>4.0.0</modelVersion>
|
||||||
<artifactId>jetty-plus</artifactId>
|
<artifactId>jetty-plus</artifactId>
|
||||||
|
|
|
@ -2,7 +2,7 @@
|
||||||
<parent>
|
<parent>
|
||||||
<groupId>org.eclipse.jetty</groupId>
|
<groupId>org.eclipse.jetty</groupId>
|
||||||
<artifactId>jetty-project</artifactId>
|
<artifactId>jetty-project</artifactId>
|
||||||
<version>9.3.3-SNAPSHOT</version>
|
<version>9.3.4-SNAPSHOT</version>
|
||||||
</parent>
|
</parent>
|
||||||
<modelVersion>4.0.0</modelVersion>
|
<modelVersion>4.0.0</modelVersion>
|
||||||
<artifactId>jetty-proxy</artifactId>
|
<artifactId>jetty-proxy</artifactId>
|
||||||
|
|
|
@ -2,7 +2,7 @@
|
||||||
<parent>
|
<parent>
|
||||||
<groupId>org.eclipse.jetty</groupId>
|
<groupId>org.eclipse.jetty</groupId>
|
||||||
<artifactId>jetty-project</artifactId>
|
<artifactId>jetty-project</artifactId>
|
||||||
<version>9.3.3-SNAPSHOT</version>
|
<version>9.3.4-SNAPSHOT</version>
|
||||||
</parent>
|
</parent>
|
||||||
<modelVersion>4.0.0</modelVersion>
|
<modelVersion>4.0.0</modelVersion>
|
||||||
<groupId>org.eclipse.jetty</groupId>
|
<groupId>org.eclipse.jetty</groupId>
|
||||||
|
|
|
@ -2,7 +2,7 @@
|
||||||
<parent>
|
<parent>
|
||||||
<groupId>org.eclipse.jetty</groupId>
|
<groupId>org.eclipse.jetty</groupId>
|
||||||
<artifactId>jetty-project</artifactId>
|
<artifactId>jetty-project</artifactId>
|
||||||
<version>9.3.3-SNAPSHOT</version>
|
<version>9.3.4-SNAPSHOT</version>
|
||||||
</parent>
|
</parent>
|
||||||
<modelVersion>4.0.0</modelVersion>
|
<modelVersion>4.0.0</modelVersion>
|
||||||
<artifactId>jetty-rewrite</artifactId>
|
<artifactId>jetty-rewrite</artifactId>
|
||||||
|
|
|
@ -2,7 +2,7 @@
|
||||||
<parent>
|
<parent>
|
||||||
<groupId>org.eclipse.jetty</groupId>
|
<groupId>org.eclipse.jetty</groupId>
|
||||||
<artifactId>jetty-project</artifactId>
|
<artifactId>jetty-project</artifactId>
|
||||||
<version>9.3.3-SNAPSHOT</version>
|
<version>9.3.4-SNAPSHOT</version>
|
||||||
</parent>
|
</parent>
|
||||||
<modelVersion>4.0.0</modelVersion>
|
<modelVersion>4.0.0</modelVersion>
|
||||||
<artifactId>jetty-runner</artifactId>
|
<artifactId>jetty-runner</artifactId>
|
||||||
|
|
|
@ -2,7 +2,7 @@
|
||||||
<parent>
|
<parent>
|
||||||
<groupId>org.eclipse.jetty</groupId>
|
<groupId>org.eclipse.jetty</groupId>
|
||||||
<artifactId>jetty-project</artifactId>
|
<artifactId>jetty-project</artifactId>
|
||||||
<version>9.3.3-SNAPSHOT</version>
|
<version>9.3.4-SNAPSHOT</version>
|
||||||
</parent>
|
</parent>
|
||||||
<modelVersion>4.0.0</modelVersion>
|
<modelVersion>4.0.0</modelVersion>
|
||||||
<artifactId>jetty-security</artifactId>
|
<artifactId>jetty-security</artifactId>
|
||||||
|
|
|
@ -2,7 +2,7 @@
|
||||||
<parent>
|
<parent>
|
||||||
<groupId>org.eclipse.jetty</groupId>
|
<groupId>org.eclipse.jetty</groupId>
|
||||||
<artifactId>jetty-project</artifactId>
|
<artifactId>jetty-project</artifactId>
|
||||||
<version>9.3.3-SNAPSHOT</version>
|
<version>9.3.4-SNAPSHOT</version>
|
||||||
</parent>
|
</parent>
|
||||||
<modelVersion>4.0.0</modelVersion>
|
<modelVersion>4.0.0</modelVersion>
|
||||||
<artifactId>jetty-server</artifactId>
|
<artifactId>jetty-server</artifactId>
|
||||||
|
|
|
@ -19,7 +19,6 @@
|
||||||
package org.eclipse.jetty.server;
|
package org.eclipse.jetty.server;
|
||||||
|
|
||||||
import java.security.cert.X509Certificate;
|
import java.security.cert.X509Certificate;
|
||||||
import java.util.List;
|
|
||||||
|
|
||||||
import javax.net.ssl.SSLContext;
|
import javax.net.ssl.SSLContext;
|
||||||
import javax.net.ssl.SSLEngine;
|
import javax.net.ssl.SSLEngine;
|
||||||
|
@ -79,23 +78,26 @@ public class SecureRequestCustomizer implements HttpConfiguration.Customizer
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* <p>Customizes the request attributes to be set for SSL requests.</p>
|
* <p>
|
||||||
* <p>The requirements of the Servlet specs are:</p>
|
* Customizes the request attributes to be set for SSL requests.
|
||||||
|
* </p>
|
||||||
|
* <p>
|
||||||
|
* The requirements of the Servlet specs are:
|
||||||
|
* </p>
|
||||||
* <ul>
|
* <ul>
|
||||||
* <li> an attribute named "javax.servlet.request.ssl_session_id" of type
|
* <li>an attribute named "javax.servlet.request.ssl_session_id" of type String (since Servlet Spec 3.0).</li>
|
||||||
* String (since Servlet Spec 3.0).</li>
|
* <li>an attribute named "javax.servlet.request.cipher_suite" of type String.</li>
|
||||||
* <li> an attribute named "javax.servlet.request.cipher_suite" of type
|
* <li>an attribute named "javax.servlet.request.key_size" of type Integer.</li>
|
||||||
* String.</li>
|
* <li>an attribute named "javax.servlet.request.X509Certificate" of type java.security.cert.X509Certificate[]. This
|
||||||
* <li> an attribute named "javax.servlet.request.key_size" of type Integer.</li>
|
* is an array of objects of type X509Certificate, the order of this array is defined as being in ascending order of
|
||||||
* <li> an attribute named "javax.servlet.request.X509Certificate" of type
|
* trust. The first certificate in the chain is the one set by the client, the next is the one used to authenticate
|
||||||
* java.security.cert.X509Certificate[]. This is an array of objects of type
|
* the first, and so on.</li>
|
||||||
* X509Certificate, the order of this array is defined as being in ascending
|
|
||||||
* order of trust. The first certificate in the chain is the one set by the
|
|
||||||
* client, the next is the one used to authenticate the first, and so on.
|
|
||||||
* </li>
|
|
||||||
* </ul>
|
* </ul>
|
||||||
*
|
*
|
||||||
* @param request HttpRequest to be customized.
|
* @param sslEngine
|
||||||
|
* the sslEngine to be customized.
|
||||||
|
* @param request
|
||||||
|
* HttpRequest to be customized.
|
||||||
*/
|
*/
|
||||||
public void customize(SSLEngine sslEngine, Request request)
|
public void customize(SSLEngine sslEngine, Request request)
|
||||||
{
|
{
|
||||||
|
@ -105,16 +107,14 @@ public class SecureRequestCustomizer implements HttpConfiguration.Customizer
|
||||||
if (_sniHostCheck)
|
if (_sniHostCheck)
|
||||||
{
|
{
|
||||||
String name = request.getServerName();
|
String name = request.getServerName();
|
||||||
@SuppressWarnings("unchecked")
|
|
||||||
X509 x509 = (X509)sslSession.getValue(SniX509ExtendedKeyManager.SNI_X509);
|
X509 x509 = (X509)sslSession.getValue(SniX509ExtendedKeyManager.SNI_X509);
|
||||||
|
|
||||||
if (x509!=null && !x509.matches(name))
|
if (x509!=null && !x509.matches(name))
|
||||||
{
|
{
|
||||||
LOG.warn("Host {} does not match SNI {}",name,x509);
|
LOG.warn("Host {} does not match SNI {}",name,x509);
|
||||||
throw new BadMessageException(400,"Host does not match SNI");
|
throw new BadMessageException(400,"Host does not match SNI");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
if (LOG.isDebugEnabled())
|
if (LOG.isDebugEnabled())
|
||||||
LOG.debug("Host {} matched SNI {}",name,x509);
|
LOG.debug("Host {} matched SNI {}",name,x509);
|
||||||
}
|
}
|
||||||
|
|
|
@ -3,7 +3,7 @@
|
||||||
<parent>
|
<parent>
|
||||||
<artifactId>jetty-project</artifactId>
|
<artifactId>jetty-project</artifactId>
|
||||||
<groupId>org.eclipse.jetty</groupId>
|
<groupId>org.eclipse.jetty</groupId>
|
||||||
<version>9.3.3-SNAPSHOT</version>
|
<version>9.3.4-SNAPSHOT</version>
|
||||||
</parent>
|
</parent>
|
||||||
<modelVersion>4.0.0</modelVersion>
|
<modelVersion>4.0.0</modelVersion>
|
||||||
<artifactId>jetty-servlet</artifactId>
|
<artifactId>jetty-servlet</artifactId>
|
||||||
|
|
|
@ -3,7 +3,7 @@
|
||||||
<parent>
|
<parent>
|
||||||
<artifactId>jetty-project</artifactId>
|
<artifactId>jetty-project</artifactId>
|
||||||
<groupId>org.eclipse.jetty</groupId>
|
<groupId>org.eclipse.jetty</groupId>
|
||||||
<version>9.3.3-SNAPSHOT</version>
|
<version>9.3.4-SNAPSHOT</version>
|
||||||
</parent>
|
</parent>
|
||||||
<modelVersion>4.0.0</modelVersion>
|
<modelVersion>4.0.0</modelVersion>
|
||||||
<artifactId>jetty-servlets</artifactId>
|
<artifactId>jetty-servlets</artifactId>
|
||||||
|
|
|
@ -2,7 +2,7 @@
|
||||||
<parent>
|
<parent>
|
||||||
<groupId>org.eclipse.jetty</groupId>
|
<groupId>org.eclipse.jetty</groupId>
|
||||||
<artifactId>jetty-project</artifactId>
|
<artifactId>jetty-project</artifactId>
|
||||||
<version>9.3.3-SNAPSHOT</version>
|
<version>9.3.4-SNAPSHOT</version>
|
||||||
</parent>
|
</parent>
|
||||||
<modelVersion>4.0.0</modelVersion>
|
<modelVersion>4.0.0</modelVersion>
|
||||||
<artifactId>jetty-spring</artifactId>
|
<artifactId>jetty-spring</artifactId>
|
||||||
|
|
|
@ -2,7 +2,7 @@
|
||||||
<parent>
|
<parent>
|
||||||
<groupId>org.eclipse.jetty</groupId>
|
<groupId>org.eclipse.jetty</groupId>
|
||||||
<artifactId>jetty-project</artifactId>
|
<artifactId>jetty-project</artifactId>
|
||||||
<version>9.3.3-SNAPSHOT</version>
|
<version>9.3.4-SNAPSHOT</version>
|
||||||
</parent>
|
</parent>
|
||||||
<modelVersion>4.0.0</modelVersion>
|
<modelVersion>4.0.0</modelVersion>
|
||||||
<artifactId>jetty-start</artifactId>
|
<artifactId>jetty-start</artifactId>
|
||||||
|
|
|
@ -2,7 +2,7 @@
|
||||||
<parent>
|
<parent>
|
||||||
<groupId>org.eclipse.jetty</groupId>
|
<groupId>org.eclipse.jetty</groupId>
|
||||||
<artifactId>jetty-project</artifactId>
|
<artifactId>jetty-project</artifactId>
|
||||||
<version>9.3.3-SNAPSHOT</version>
|
<version>9.3.4-SNAPSHOT</version>
|
||||||
</parent>
|
</parent>
|
||||||
<modelVersion>4.0.0</modelVersion>
|
<modelVersion>4.0.0</modelVersion>
|
||||||
<artifactId>jetty-util-ajax</artifactId>
|
<artifactId>jetty-util-ajax</artifactId>
|
||||||
|
|
|
@ -2,7 +2,7 @@
|
||||||
<parent>
|
<parent>
|
||||||
<groupId>org.eclipse.jetty</groupId>
|
<groupId>org.eclipse.jetty</groupId>
|
||||||
<artifactId>jetty-project</artifactId>
|
<artifactId>jetty-project</artifactId>
|
||||||
<version>9.3.3-SNAPSHOT</version>
|
<version>9.3.4-SNAPSHOT</version>
|
||||||
</parent>
|
</parent>
|
||||||
<modelVersion>4.0.0</modelVersion>
|
<modelVersion>4.0.0</modelVersion>
|
||||||
<artifactId>jetty-util</artifactId>
|
<artifactId>jetty-util</artifactId>
|
||||||
|
|
|
@ -299,7 +299,7 @@ public class SslContextFactory extends AbstractLifeCycle
|
||||||
{
|
{
|
||||||
return _aliasX509.get(alias);
|
return _aliasX509.get(alias);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Create the SSLContext object and start the lifecycle
|
* Create the SSLContext object and start the lifecycle
|
||||||
* @see org.eclipse.jetty.util.component.AbstractLifeCycle#doStart()
|
* @see org.eclipse.jetty.util.component.AbstractLifeCycle#doStart()
|
||||||
|
@ -359,7 +359,7 @@ public class SslContextFactory extends AbstractLifeCycle
|
||||||
}
|
}
|
||||||
X509 x509 = new X509(alias,x509C);
|
X509 x509 = new X509(alias,x509C);
|
||||||
_aliasX509.put(alias,x509);
|
_aliasX509.put(alias,x509);
|
||||||
|
|
||||||
if (_validateCerts)
|
if (_validateCerts)
|
||||||
{
|
{
|
||||||
CertificateValidator validator = new CertificateValidator(trustStore, crls);
|
CertificateValidator validator = new CertificateValidator(trustStore, crls);
|
||||||
|
@ -371,7 +371,7 @@ public class SslContextFactory extends AbstractLifeCycle
|
||||||
}
|
}
|
||||||
|
|
||||||
LOG.info("x509={} for {}",x509,this);
|
LOG.info("x509={} for {}",x509,this);
|
||||||
|
|
||||||
for (String h:x509.getHosts())
|
for (String h:x509.getHosts())
|
||||||
_certHosts.put(h,x509);
|
_certHosts.put(h,x509);
|
||||||
for (String w:x509.getWilds())
|
for (String w:x509.getWilds())
|
||||||
|
@ -405,7 +405,7 @@ public class SslContextFactory extends AbstractLifeCycle
|
||||||
LOG.debug("Selected Ciphers {} of {}",Arrays.asList(_selectedCipherSuites),Arrays.asList(sslEngine.getSupportedCipherSuites()));
|
LOG.debug("Selected Ciphers {} of {}",Arrays.asList(_selectedCipherSuites),Arrays.asList(sslEngine.getSupportedCipherSuites()));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
protected void doStop() throws Exception
|
protected void doStop() throws Exception
|
||||||
{
|
{
|
||||||
|
@ -1710,15 +1710,15 @@ public class SslContextFactory extends AbstractLifeCycle
|
||||||
{
|
{
|
||||||
String host = _host = ((SNIHostName)serverName).getAsciiName();
|
String host = _host = ((SNIHostName)serverName).getAsciiName();
|
||||||
host=StringUtil.asciiToLowerCase(host);
|
host=StringUtil.asciiToLowerCase(host);
|
||||||
|
|
||||||
// Try an exact match
|
// Try an exact match
|
||||||
_x509 = _certHosts.get(host);
|
_x509 = _certHosts.get(host);
|
||||||
|
|
||||||
// Else try an exact wild match
|
// Else try an exact wild match
|
||||||
if (_x509==null)
|
if (_x509==null)
|
||||||
{
|
{
|
||||||
_x509 = _certWilds.get(host);
|
_x509 = _certWilds.get(host);
|
||||||
|
|
||||||
// Else try an 1 deep wild match
|
// Else try an 1 deep wild match
|
||||||
if (_x509==null)
|
if (_x509==null)
|
||||||
{
|
{
|
||||||
|
@ -1733,10 +1733,12 @@ public class SslContextFactory extends AbstractLifeCycle
|
||||||
|
|
||||||
if (LOG.isDebugEnabled())
|
if (LOG.isDebugEnabled())
|
||||||
LOG.debug("SNI matched {}->{}",host,_x509);
|
LOG.debug("SNI matched {}->{}",host,_x509);
|
||||||
|
|
||||||
}
|
}
|
||||||
else if (LOG.isDebugEnabled())
|
else
|
||||||
LOG.debug("SNI no match for {}", serverName);
|
{
|
||||||
|
if (LOG.isDebugEnabled())
|
||||||
|
LOG.debug("SNI no match for {}", serverName);
|
||||||
|
}
|
||||||
|
|
||||||
// Return true and allow the KeyManager to accept or reject when choosing a certificate.
|
// Return true and allow the KeyManager to accept or reject when choosing a certificate.
|
||||||
// If we don't have a SNI host, or didn't see any certificate aliases,
|
// If we don't have a SNI host, or didn't see any certificate aliases,
|
||||||
|
|
|
@ -32,14 +32,13 @@ import javax.naming.ldap.Rdn;
|
||||||
import javax.security.auth.x500.X500Principal;
|
import javax.security.auth.x500.X500Principal;
|
||||||
|
|
||||||
import org.eclipse.jetty.util.StringUtil;
|
import org.eclipse.jetty.util.StringUtil;
|
||||||
import org.eclipse.jetty.util.TypeUtil;
|
|
||||||
import org.eclipse.jetty.util.log.Log;
|
import org.eclipse.jetty.util.log.Log;
|
||||||
import org.eclipse.jetty.util.log.Logger;
|
import org.eclipse.jetty.util.log.Logger;
|
||||||
|
|
||||||
public class X509
|
public class X509
|
||||||
{
|
{
|
||||||
static final Logger LOG = Log.getLogger(X509.class);
|
private static final Logger LOG = Log.getLogger(X509.class);
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* @see {@link X509Certificate#getKeyUsage()}
|
* @see {@link X509Certificate#getKeyUsage()}
|
||||||
*/
|
*/
|
||||||
|
@ -51,26 +50,22 @@ public class X509
|
||||||
*/
|
*/
|
||||||
private static final int SUBJECT_ALTERNATIVE_NAMES__DNS_NAME=2;
|
private static final int SUBJECT_ALTERNATIVE_NAMES__DNS_NAME=2;
|
||||||
|
|
||||||
|
|
||||||
public static boolean isCertSign(X509Certificate x509)
|
public static boolean isCertSign(X509Certificate x509)
|
||||||
{
|
{
|
||||||
boolean[] key_usage=x509.getKeyUsage();
|
boolean[] key_usage=x509.getKeyUsage();
|
||||||
return key_usage!=null && key_usage[KEY_USAGE__KEY_CERT_SIGN];
|
return key_usage!=null && key_usage[KEY_USAGE__KEY_CERT_SIGN];
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
private final X509Certificate _x509;
|
private final X509Certificate _x509;
|
||||||
private final String _alias;
|
private final String _alias;
|
||||||
private final List<String> _hosts=new ArrayList<>();
|
private final List<String> _hosts=new ArrayList<>();
|
||||||
private final List<String> _wilds=new ArrayList<>();
|
private final List<String> _wilds=new ArrayList<>();
|
||||||
|
|
||||||
|
|
||||||
public X509(String alias,X509Certificate x509) throws CertificateParsingException, InvalidNameException
|
public X509(String alias,X509Certificate x509) throws CertificateParsingException, InvalidNameException
|
||||||
{
|
{
|
||||||
_alias=alias;
|
_alias=alias;
|
||||||
_x509 = x509;
|
_x509 = x509;
|
||||||
|
|
||||||
|
|
||||||
// Look for alternative name extensions
|
// Look for alternative name extensions
|
||||||
boolean named=false;
|
boolean named=false;
|
||||||
Collection<List<?>> altNames = x509.getSubjectAlternativeNames();
|
Collection<List<?>> altNames = x509.getSubjectAlternativeNames();
|
||||||
|
@ -82,7 +77,7 @@ public class X509
|
||||||
{
|
{
|
||||||
String cn = list.get(1).toString();
|
String cn = list.get(1).toString();
|
||||||
if (LOG.isDebugEnabled())
|
if (LOG.isDebugEnabled())
|
||||||
LOG.debug("Certificate SAN alias={} cn={} in {}",alias,cn,this);
|
LOG.debug("Certificate SAN alias={} CN={} in {}",alias,cn,this);
|
||||||
if (cn!=null)
|
if (cn!=null)
|
||||||
{
|
{
|
||||||
named=true;
|
named=true;
|
||||||
|
@ -92,28 +87,27 @@ public class X509
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// If no names found, look up the cn from the subject
|
// If no names found, look up the CN from the subject
|
||||||
if (!named)
|
if (!named)
|
||||||
{
|
{
|
||||||
LdapName name=new LdapName(x509.getSubjectX500Principal().getName(X500Principal.RFC2253));
|
LdapName name=new LdapName(x509.getSubjectX500Principal().getName(X500Principal.RFC2253));
|
||||||
for (Rdn rdn : name.getRdns())
|
for (Rdn rdn : name.getRdns())
|
||||||
{
|
{
|
||||||
if (rdn.getType().equalsIgnoreCase("cn"))
|
if (rdn.getType().equalsIgnoreCase("CN"))
|
||||||
{
|
{
|
||||||
String cn = rdn.getValue().toString();
|
String cn = rdn.getValue().toString();
|
||||||
if (LOG.isDebugEnabled())
|
if (LOG.isDebugEnabled())
|
||||||
LOG.debug("Certificate cn alias={} cn={} in {}",alias,cn,this);
|
LOG.debug("Certificate CN alias={} CN={} in {}",alias,cn,this);
|
||||||
if (cn!=null && cn.contains(".") && !cn.contains(" "))
|
if (cn!=null && cn.contains(".") && !cn.contains(" "))
|
||||||
addName(cn);
|
addName(cn);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
protected void addName(String cn)
|
protected void addName(String cn)
|
||||||
{
|
{
|
||||||
cn=StringUtil.asciiToLowerCase(cn);
|
cn=StringUtil.asciiToLowerCase(cn);
|
||||||
cn.toLowerCase();
|
|
||||||
if (cn.startsWith("*."))
|
if (cn.startsWith("*."))
|
||||||
_wilds.add(cn.substring(2));
|
_wilds.add(cn.substring(2));
|
||||||
else
|
else
|
||||||
|
@ -124,17 +118,17 @@ public class X509
|
||||||
{
|
{
|
||||||
return _alias;
|
return _alias;
|
||||||
}
|
}
|
||||||
|
|
||||||
public X509Certificate getCertificate()
|
public X509Certificate getCertificate()
|
||||||
{
|
{
|
||||||
return _x509;
|
return _x509;
|
||||||
}
|
}
|
||||||
|
|
||||||
public Set<String> getHosts()
|
public Set<String> getHosts()
|
||||||
{
|
{
|
||||||
return new HashSet<>(_hosts);
|
return new HashSet<>(_hosts);
|
||||||
}
|
}
|
||||||
|
|
||||||
public Set<String> getWilds()
|
public Set<String> getWilds()
|
||||||
{
|
{
|
||||||
return new HashSet<>(_wilds);
|
return new HashSet<>(_wilds);
|
||||||
|
@ -156,7 +150,6 @@ public class X509
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public String toString()
|
public String toString()
|
||||||
{
|
{
|
||||||
|
|
|
@ -2,7 +2,7 @@
|
||||||
<parent>
|
<parent>
|
||||||
<groupId>org.eclipse.jetty</groupId>
|
<groupId>org.eclipse.jetty</groupId>
|
||||||
<artifactId>jetty-project</artifactId>
|
<artifactId>jetty-project</artifactId>
|
||||||
<version>9.3.3-SNAPSHOT</version>
|
<version>9.3.4-SNAPSHOT</version>
|
||||||
</parent>
|
</parent>
|
||||||
<modelVersion>4.0.0</modelVersion>
|
<modelVersion>4.0.0</modelVersion>
|
||||||
<artifactId>jetty-webapp</artifactId>
|
<artifactId>jetty-webapp</artifactId>
|
||||||
|
|
|
@ -470,7 +470,10 @@ public class WebAppClassLoader extends URLClassLoader
|
||||||
c= _parent.loadClass(name);
|
c= _parent.loadClass(name);
|
||||||
|
|
||||||
if (c == null && ex!=null)
|
if (c == null && ex!=null)
|
||||||
|
{
|
||||||
|
LOG.debug("not found {} from {}",name,this,ex);
|
||||||
throw ex;
|
throw ex;
|
||||||
|
}
|
||||||
|
|
||||||
if (resolve)
|
if (resolve)
|
||||||
resolveClass(c);
|
resolveClass(c);
|
||||||
|
|
|
@ -3,7 +3,7 @@
|
||||||
<parent>
|
<parent>
|
||||||
<groupId>org.eclipse.jetty.websocket</groupId>
|
<groupId>org.eclipse.jetty.websocket</groupId>
|
||||||
<artifactId>websocket-parent</artifactId>
|
<artifactId>websocket-parent</artifactId>
|
||||||
<version>9.3.3-SNAPSHOT</version>
|
<version>9.3.4-SNAPSHOT</version>
|
||||||
</parent>
|
</parent>
|
||||||
|
|
||||||
<modelVersion>4.0.0</modelVersion>
|
<modelVersion>4.0.0</modelVersion>
|
||||||
|
|
|
@ -3,7 +3,7 @@
|
||||||
<parent>
|
<parent>
|
||||||
<groupId>org.eclipse.jetty.websocket</groupId>
|
<groupId>org.eclipse.jetty.websocket</groupId>
|
||||||
<artifactId>websocket-parent</artifactId>
|
<artifactId>websocket-parent</artifactId>
|
||||||
<version>9.3.3-SNAPSHOT</version>
|
<version>9.3.4-SNAPSHOT</version>
|
||||||
</parent>
|
</parent>
|
||||||
|
|
||||||
<modelVersion>4.0.0</modelVersion>
|
<modelVersion>4.0.0</modelVersion>
|
||||||
|
|
|
@ -3,7 +3,7 @@
|
||||||
<parent>
|
<parent>
|
||||||
<artifactId>jetty-project</artifactId>
|
<artifactId>jetty-project</artifactId>
|
||||||
<groupId>org.eclipse.jetty</groupId>
|
<groupId>org.eclipse.jetty</groupId>
|
||||||
<version>9.3.3-SNAPSHOT</version>
|
<version>9.3.4-SNAPSHOT</version>
|
||||||
</parent>
|
</parent>
|
||||||
|
|
||||||
<modelVersion>4.0.0</modelVersion>
|
<modelVersion>4.0.0</modelVersion>
|
||||||
|
|
|
@ -3,7 +3,7 @@
|
||||||
<parent>
|
<parent>
|
||||||
<groupId>org.eclipse.jetty.websocket</groupId>
|
<groupId>org.eclipse.jetty.websocket</groupId>
|
||||||
<artifactId>websocket-parent</artifactId>
|
<artifactId>websocket-parent</artifactId>
|
||||||
<version>9.3.3-SNAPSHOT</version>
|
<version>9.3.4-SNAPSHOT</version>
|
||||||
</parent>
|
</parent>
|
||||||
|
|
||||||
<modelVersion>4.0.0</modelVersion>
|
<modelVersion>4.0.0</modelVersion>
|
||||||
|
|
|
@ -18,33 +18,38 @@
|
||||||
|
|
||||||
package org.eclipse.jetty.websocket.api;
|
package org.eclipse.jetty.websocket.api;
|
||||||
|
|
||||||
|
import java.nio.charset.StandardCharsets;
|
||||||
|
|
||||||
public class CloseStatus
|
public class CloseStatus
|
||||||
{
|
{
|
||||||
private static final int MAX_CONTROL_PAYLOAD = 125;
|
private static final int MAX_CONTROL_PAYLOAD = 125;
|
||||||
private static final int MAX_REASON_PHRASE = MAX_CONTROL_PAYLOAD - 2;
|
public static final int MAX_REASON_PHRASE = MAX_CONTROL_PAYLOAD - 2;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Convenience method for trimming a long reason phrase at the maximum reason phrase length.
|
* Convenience method for trimming a long reason phrase at the maximum reason phrase length of 123 UTF-8 bytes (per WebSocket spec).
|
||||||
*
|
*
|
||||||
* @param reason
|
* @param reason
|
||||||
* the proposed reason phrase
|
* the proposed reason phrase
|
||||||
* @return the reason phrase (trimmed if needed)
|
* @return the reason phrase (trimmed if needed)
|
||||||
|
* @deprecated use of this method is strongly discouraged, as it creates too many new objects that are just thrown away to accomplish its goals.
|
||||||
*/
|
*/
|
||||||
|
@Deprecated
|
||||||
public static String trimMaxReasonLength(String reason)
|
public static String trimMaxReasonLength(String reason)
|
||||||
{
|
{
|
||||||
if (reason == null)
|
if (reason == null)
|
||||||
{
|
{
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
byte[] reasonBytes = reason.getBytes(StandardCharsets.UTF_8);
|
||||||
|
if (reasonBytes.length > MAX_REASON_PHRASE)
|
||||||
|
{
|
||||||
|
byte[] trimmed = new byte[MAX_REASON_PHRASE];
|
||||||
|
System.arraycopy(reasonBytes,0,trimmed,0,MAX_REASON_PHRASE);
|
||||||
|
return new String(trimmed,StandardCharsets.UTF_8);
|
||||||
|
}
|
||||||
|
|
||||||
if (reason.length() > MAX_REASON_PHRASE)
|
return reason;
|
||||||
{
|
|
||||||
return reason.substring(0,MAX_REASON_PHRASE);
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
return reason;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
private int code;
|
private int code;
|
||||||
|
|
|
@ -152,6 +152,15 @@ public interface RemoteEndpoint
|
||||||
*/
|
*/
|
||||||
BatchMode getBatchMode();
|
BatchMode getBatchMode();
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Set the batch mode with which messages are sent.
|
||||||
|
*
|
||||||
|
* @param mode
|
||||||
|
* the batch mode to use
|
||||||
|
* @see #flush()
|
||||||
|
*/
|
||||||
|
void setBatchMode(BatchMode mode);
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Flushes messages that may have been batched by the implementation.
|
* Flushes messages that may have been batched by the implementation.
|
||||||
*
|
*
|
||||||
|
|
|
@ -24,6 +24,8 @@ import java.lang.annotation.Retention;
|
||||||
import java.lang.annotation.RetentionPolicy;
|
import java.lang.annotation.RetentionPolicy;
|
||||||
import java.lang.annotation.Target;
|
import java.lang.annotation.Target;
|
||||||
|
|
||||||
|
import org.eclipse.jetty.websocket.api.BatchMode;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Tags a POJO as being a WebSocket class.
|
* Tags a POJO as being a WebSocket class.
|
||||||
*/
|
*/
|
||||||
|
@ -40,4 +42,6 @@ public @interface WebSocket
|
||||||
int maxIdleTime() default -2;
|
int maxIdleTime() default -2;
|
||||||
|
|
||||||
int maxTextMessageSize() default -2;
|
int maxTextMessageSize() default -2;
|
||||||
|
|
||||||
|
BatchMode batchMode() default BatchMode.AUTO;
|
||||||
}
|
}
|
||||||
|
|
|
@ -3,7 +3,7 @@
|
||||||
<parent>
|
<parent>
|
||||||
<groupId>org.eclipse.jetty.websocket</groupId>
|
<groupId>org.eclipse.jetty.websocket</groupId>
|
||||||
<artifactId>websocket-parent</artifactId>
|
<artifactId>websocket-parent</artifactId>
|
||||||
<version>9.3.3-SNAPSHOT</version>
|
<version>9.3.4-SNAPSHOT</version>
|
||||||
</parent>
|
</parent>
|
||||||
|
|
||||||
<modelVersion>4.0.0</modelVersion>
|
<modelVersion>4.0.0</modelVersion>
|
||||||
|
|
|
@ -3,7 +3,7 @@
|
||||||
<parent>
|
<parent>
|
||||||
<groupId>org.eclipse.jetty.websocket</groupId>
|
<groupId>org.eclipse.jetty.websocket</groupId>
|
||||||
<artifactId>websocket-parent</artifactId>
|
<artifactId>websocket-parent</artifactId>
|
||||||
<version>9.3.3-SNAPSHOT</version>
|
<version>9.3.4-SNAPSHOT</version>
|
||||||
</parent>
|
</parent>
|
||||||
|
|
||||||
<modelVersion>4.0.0</modelVersion>
|
<modelVersion>4.0.0</modelVersion>
|
||||||
|
|
|
@ -19,14 +19,13 @@
|
||||||
package org.eclipse.jetty.websocket.common;
|
package org.eclipse.jetty.websocket.common;
|
||||||
|
|
||||||
import java.nio.ByteBuffer;
|
import java.nio.ByteBuffer;
|
||||||
|
import java.nio.charset.StandardCharsets;
|
||||||
|
|
||||||
import org.eclipse.jetty.util.BufferUtil;
|
import org.eclipse.jetty.util.BufferUtil;
|
||||||
import org.eclipse.jetty.util.StringUtil;
|
|
||||||
import org.eclipse.jetty.util.Utf8Appendable.NotUtf8Exception;
|
|
||||||
import org.eclipse.jetty.util.Utf8StringBuilder;
|
import org.eclipse.jetty.util.Utf8StringBuilder;
|
||||||
import org.eclipse.jetty.util.log.Log;
|
import org.eclipse.jetty.util.Utf8Appendable.NotUtf8Exception;
|
||||||
import org.eclipse.jetty.util.log.Logger;
|
|
||||||
import org.eclipse.jetty.websocket.api.BadPayloadException;
|
import org.eclipse.jetty.websocket.api.BadPayloadException;
|
||||||
|
import org.eclipse.jetty.websocket.api.CloseStatus;
|
||||||
import org.eclipse.jetty.websocket.api.ProtocolException;
|
import org.eclipse.jetty.websocket.api.ProtocolException;
|
||||||
import org.eclipse.jetty.websocket.api.StatusCode;
|
import org.eclipse.jetty.websocket.api.StatusCode;
|
||||||
import org.eclipse.jetty.websocket.api.extensions.Frame;
|
import org.eclipse.jetty.websocket.api.extensions.Frame;
|
||||||
|
@ -34,19 +33,23 @@ import org.eclipse.jetty.websocket.common.frames.CloseFrame;
|
||||||
|
|
||||||
public class CloseInfo
|
public class CloseInfo
|
||||||
{
|
{
|
||||||
private static final Logger LOG = Log.getLogger(CloseInfo.class);
|
|
||||||
private int statusCode;
|
private int statusCode;
|
||||||
private String reason;
|
private byte[] reasonBytes;
|
||||||
|
|
||||||
public CloseInfo()
|
public CloseInfo()
|
||||||
{
|
{
|
||||||
this(StatusCode.NO_CODE,null);
|
this(StatusCode.NO_CODE,null);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Parse the Close Frame payload.
|
||||||
|
*
|
||||||
|
* @param payload the raw close frame payload.
|
||||||
|
* @param validate true if payload should be validated per WebSocket spec.
|
||||||
|
*/
|
||||||
public CloseInfo(ByteBuffer payload, boolean validate)
|
public CloseInfo(ByteBuffer payload, boolean validate)
|
||||||
{
|
{
|
||||||
this.statusCode = StatusCode.NO_CODE;
|
this.statusCode = StatusCode.NO_CODE;
|
||||||
this.reason = null;
|
|
||||||
|
|
||||||
if ((payload == null) || (payload.remaining() == 0))
|
if ((payload == null) || (payload.remaining() == 0))
|
||||||
{
|
{
|
||||||
|
@ -77,34 +80,24 @@ public class CloseInfo
|
||||||
|
|
||||||
if (data.remaining() > 0)
|
if (data.remaining() > 0)
|
||||||
{
|
{
|
||||||
// Reason
|
// Reason (trimmed to max reason size)
|
||||||
try
|
int len = Math.min(data.remaining(), CloseStatus.MAX_REASON_PHRASE);
|
||||||
|
reasonBytes = new byte[len];
|
||||||
|
data.get(reasonBytes,0,len);
|
||||||
|
|
||||||
|
// Spec Requirement : throw BadPayloadException on invalid UTF8
|
||||||
|
if(validate)
|
||||||
{
|
{
|
||||||
Utf8StringBuilder utf = new Utf8StringBuilder();
|
try
|
||||||
utf.append(data);
|
{
|
||||||
reason = utf.toString();
|
Utf8StringBuilder utf = new Utf8StringBuilder();
|
||||||
}
|
// if this throws, we know we have bad UTF8
|
||||||
catch (NotUtf8Exception e)
|
utf.append(reasonBytes,0,reasonBytes.length);
|
||||||
{
|
}
|
||||||
if (validate)
|
catch (NotUtf8Exception e)
|
||||||
{
|
{
|
||||||
throw new BadPayloadException("Invalid Close Reason",e);
|
throw new BadPayloadException("Invalid Close Reason",e);
|
||||||
}
|
}
|
||||||
else
|
|
||||||
{
|
|
||||||
LOG.warn(e);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
catch (RuntimeException e)
|
|
||||||
{
|
|
||||||
if (validate)
|
|
||||||
{
|
|
||||||
throw new ProtocolException("Invalid Close Reason",e);
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
LOG.warn(e);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -125,10 +118,28 @@ public class CloseInfo
|
||||||
this(statusCode,null);
|
this(statusCode,null);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Create a CloseInfo, trimming the reason to {@link CloseStatus#MAX_REASON_PHRASE} UTF-8 bytes if needed.
|
||||||
|
*
|
||||||
|
* @param statusCode the status code
|
||||||
|
* @param reason the raw reason code
|
||||||
|
*/
|
||||||
public CloseInfo(int statusCode, String reason)
|
public CloseInfo(int statusCode, String reason)
|
||||||
{
|
{
|
||||||
this.statusCode = statusCode;
|
this.statusCode = statusCode;
|
||||||
this.reason = reason;
|
if (reason != null)
|
||||||
|
{
|
||||||
|
byte[] utf8Bytes = reason.getBytes(StandardCharsets.UTF_8);
|
||||||
|
if (utf8Bytes.length > CloseStatus.MAX_REASON_PHRASE)
|
||||||
|
{
|
||||||
|
this.reasonBytes = new byte[CloseStatus.MAX_REASON_PHRASE];
|
||||||
|
System.arraycopy(utf8Bytes,0,this.reasonBytes,0,CloseStatus.MAX_REASON_PHRASE);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
this.reasonBytes = utf8Bytes;
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private ByteBuffer asByteBuffer()
|
private ByteBuffer asByteBuffer()
|
||||||
|
@ -140,11 +151,10 @@ public class CloseInfo
|
||||||
}
|
}
|
||||||
|
|
||||||
int len = 2; // status code
|
int len = 2; // status code
|
||||||
byte utf[] = null;
|
boolean hasReason = (this.reasonBytes != null) && (this.reasonBytes.length > 0);
|
||||||
if (StringUtil.isNotBlank(reason))
|
if (hasReason)
|
||||||
{
|
{
|
||||||
utf = StringUtil.getUtf8Bytes(reason);
|
len += this.reasonBytes.length;
|
||||||
len += utf.length;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
ByteBuffer buf = BufferUtil.allocate(len);
|
ByteBuffer buf = BufferUtil.allocate(len);
|
||||||
|
@ -152,9 +162,9 @@ public class CloseInfo
|
||||||
buf.put((byte)((statusCode >>> 8) & 0xFF));
|
buf.put((byte)((statusCode >>> 8) & 0xFF));
|
||||||
buf.put((byte)((statusCode >>> 0) & 0xFF));
|
buf.put((byte)((statusCode >>> 0) & 0xFF));
|
||||||
|
|
||||||
if (utf != null)
|
if (hasReason)
|
||||||
{
|
{
|
||||||
buf.put(utf,0,utf.length);
|
buf.put(this.reasonBytes,0,this.reasonBytes.length);
|
||||||
}
|
}
|
||||||
BufferUtil.flipToFlush(buf,0);
|
BufferUtil.flipToFlush(buf,0);
|
||||||
|
|
||||||
|
@ -178,7 +188,11 @@ public class CloseInfo
|
||||||
|
|
||||||
public String getReason()
|
public String getReason()
|
||||||
{
|
{
|
||||||
return reason;
|
if (this.reasonBytes == null)
|
||||||
|
{
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
return new String(this.reasonBytes,StandardCharsets.UTF_8);
|
||||||
}
|
}
|
||||||
|
|
||||||
public int getStatusCode()
|
public int getStatusCode()
|
||||||
|
@ -199,6 +213,6 @@ public class CloseInfo
|
||||||
@Override
|
@Override
|
||||||
public String toString()
|
public String toString()
|
||||||
{
|
{
|
||||||
return String.format("CloseInfo[code=%d,reason=%s]",statusCode,reason);
|
return String.format("CloseInfo[code=%d,reason=%s]",statusCode,getReason());
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -436,9 +436,7 @@ public class WebSocketRemoteEndpoint implements RemoteEndpoint
|
||||||
return batchMode;
|
return batchMode;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Only the JSR needs to have this method exposed.
|
@Override
|
||||||
// In the Jetty implementation the batching is set
|
|
||||||
// at the moment of opening the session.
|
|
||||||
public void setBatchMode(BatchMode batchMode)
|
public void setBatchMode(BatchMode batchMode)
|
||||||
{
|
{
|
||||||
this.batchMode = batchMode;
|
this.batchMode = batchMode;
|
||||||
|
|
|
@ -98,7 +98,7 @@ public class WebSocketSession extends ContainerLifeCycle implements Session, Web
|
||||||
@Override
|
@Override
|
||||||
public void close()
|
public void close()
|
||||||
{
|
{
|
||||||
this.close(StatusCode.NORMAL,null);
|
connection.close();
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
|
|
|
@ -25,6 +25,7 @@ import org.eclipse.jetty.util.BufferUtil;
|
||||||
import org.eclipse.jetty.util.Utf8Appendable.NotUtf8Exception;
|
import org.eclipse.jetty.util.Utf8Appendable.NotUtf8Exception;
|
||||||
import org.eclipse.jetty.util.log.Log;
|
import org.eclipse.jetty.util.log.Log;
|
||||||
import org.eclipse.jetty.util.log.Logger;
|
import org.eclipse.jetty.util.log.Logger;
|
||||||
|
import org.eclipse.jetty.websocket.api.BatchMode;
|
||||||
import org.eclipse.jetty.websocket.api.CloseException;
|
import org.eclipse.jetty.websocket.api.CloseException;
|
||||||
import org.eclipse.jetty.websocket.api.StatusCode;
|
import org.eclipse.jetty.websocket.api.StatusCode;
|
||||||
import org.eclipse.jetty.websocket.api.WebSocketPolicy;
|
import org.eclipse.jetty.websocket.api.WebSocketPolicy;
|
||||||
|
@ -208,6 +209,12 @@ public abstract class AbstractEventDriver implements IncomingFrames, EventDriver
|
||||||
{
|
{
|
||||||
/* TODO: provide annotation in future */
|
/* TODO: provide annotation in future */
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public BatchMode getBatchMode()
|
||||||
|
{
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void openSession(WebSocketSession session)
|
public void openSession(WebSocketSession session)
|
||||||
|
|
|
@ -23,6 +23,7 @@ import java.io.InputStream;
|
||||||
import java.io.Reader;
|
import java.io.Reader;
|
||||||
import java.nio.ByteBuffer;
|
import java.nio.ByteBuffer;
|
||||||
|
|
||||||
|
import org.eclipse.jetty.websocket.api.BatchMode;
|
||||||
import org.eclipse.jetty.websocket.api.WebSocketPolicy;
|
import org.eclipse.jetty.websocket.api.WebSocketPolicy;
|
||||||
import org.eclipse.jetty.websocket.api.extensions.Frame;
|
import org.eclipse.jetty.websocket.api.extensions.Frame;
|
||||||
import org.eclipse.jetty.websocket.api.extensions.IncomingFrames;
|
import org.eclipse.jetty.websocket.api.extensions.IncomingFrames;
|
||||||
|
@ -34,6 +35,8 @@ public interface EventDriver extends IncomingFrames
|
||||||
public WebSocketPolicy getPolicy();
|
public WebSocketPolicy getPolicy();
|
||||||
|
|
||||||
public WebSocketSession getSession();
|
public WebSocketSession getSession();
|
||||||
|
|
||||||
|
public BatchMode getBatchMode();
|
||||||
|
|
||||||
public void onBinaryFrame(ByteBuffer buffer, boolean fin) throws IOException;
|
public void onBinaryFrame(ByteBuffer buffer, boolean fin) throws IOException;
|
||||||
|
|
||||||
|
|
|
@ -23,6 +23,7 @@ import java.io.InputStream;
|
||||||
import java.io.Reader;
|
import java.io.Reader;
|
||||||
import java.nio.ByteBuffer;
|
import java.nio.ByteBuffer;
|
||||||
|
|
||||||
|
import org.eclipse.jetty.websocket.api.BatchMode;
|
||||||
import org.eclipse.jetty.websocket.api.WebSocketPolicy;
|
import org.eclipse.jetty.websocket.api.WebSocketPolicy;
|
||||||
import org.eclipse.jetty.websocket.api.annotations.WebSocket;
|
import org.eclipse.jetty.websocket.api.annotations.WebSocket;
|
||||||
import org.eclipse.jetty.websocket.api.extensions.Frame;
|
import org.eclipse.jetty.websocket.api.extensions.Frame;
|
||||||
|
@ -40,6 +41,7 @@ public class JettyAnnotatedEventDriver extends AbstractEventDriver
|
||||||
{
|
{
|
||||||
private final JettyAnnotatedMetadata events;
|
private final JettyAnnotatedMetadata events;
|
||||||
private boolean hasCloseBeenCalled = false;
|
private boolean hasCloseBeenCalled = false;
|
||||||
|
private BatchMode batchMode;
|
||||||
|
|
||||||
public JettyAnnotatedEventDriver(WebSocketPolicy policy, Object websocket, JettyAnnotatedMetadata events)
|
public JettyAnnotatedEventDriver(WebSocketPolicy policy, Object websocket, JettyAnnotatedMetadata events)
|
||||||
{
|
{
|
||||||
|
@ -64,6 +66,13 @@ public class JettyAnnotatedEventDriver extends AbstractEventDriver
|
||||||
{
|
{
|
||||||
this.policy.setIdleTimeout(anno.maxIdleTime());
|
this.policy.setIdleTimeout(anno.maxIdleTime());
|
||||||
}
|
}
|
||||||
|
this.batchMode = anno.batchMode();
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public BatchMode getBatchMode()
|
||||||
|
{
|
||||||
|
return this.batchMode;
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
|
|
|
@ -244,10 +244,14 @@ public abstract class AbstractWebSocketConnection extends AbstractConnection imp
|
||||||
return super.getExecutor();
|
return super.getExecutor();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Close without a close code or reason
|
||||||
|
*/
|
||||||
@Override
|
@Override
|
||||||
public void close()
|
public void close()
|
||||||
{
|
{
|
||||||
close(StatusCode.NORMAL,null);
|
CloseInfo close = new CloseInfo();
|
||||||
|
this.outgoingFrame(close.asFrame(),new OnCloseLocalCallback(close),BatchMode.OFF);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
|
Some files were not shown because too many files have changed in this diff Show More
Loading…
Reference in New Issue