Rework Jetty startup so connectors are only started once

Previously the server was started to make the ServletContext
available, then, to prevent requests from being handled before the
application context had been started, the connectors were stopped.
Once application context startup had completed, the connectors were
then started again. In addition to being somewhat inefficient, this
caused problems on FreeBSD where stopping the connector didn't free
up the port quickly enough for the subsequent start to then be able
to bind to it.

This commit updates the Jetty startup logic to be closer to the logic
that's used for Tomcat. Before the server is started, the configured
connectors are cached and then removed. The server is then started
without any connectors. Once application context startup has
completed, the connectors are reinstated and started.

Fixes #968
This commit is contained in:
Andy Wilkinson 2014-07-28 14:38:11 +01:00
parent 8c15b13fda
commit bd577f1515
1 changed files with 10 additions and 7 deletions

View File

@ -44,6 +44,8 @@ public class JettyEmbeddedServletContainer implements EmbeddedServletContainer {
private final boolean autoStart; private final boolean autoStart;
private Connector[] connectors;
/** /**
* Create a new {@link JettyEmbeddedServletContainer} instance. * Create a new {@link JettyEmbeddedServletContainer} instance.
* @param server the underlying Jetty server * @param server the underlying Jetty server
@ -65,14 +67,13 @@ public class JettyEmbeddedServletContainer implements EmbeddedServletContainer {
private synchronized void initialize() { private synchronized void initialize() {
try { try {
// Cache and clear the connectors to prevent requests being handled before
// the application context is ready
this.connectors = this.server.getConnectors();
this.server.setConnectors(null);
// Start the server so that the ServletContext is available
this.server.start(); this.server.start();
// Start the server so the ServletContext is available, but stop the
// connectors to prevent requests from being handled before the Spring context
// is ready:
Connector[] connectors = this.server.getConnectors();
for (Connector connector : connectors) {
connector.stop();
}
} }
catch (Exception ex) { catch (Exception ex) {
try { try {
@ -88,6 +89,8 @@ public class JettyEmbeddedServletContainer implements EmbeddedServletContainer {
@Override @Override
public void start() throws EmbeddedServletContainerException { public void start() throws EmbeddedServletContainerException {
this.server.setConnectors(this.connectors);
if (!this.autoStart) { if (!this.autoStart) {
return; return;
} }