/**
 * Copyright (c) 2010 RedEngine Ltd, http://www.redengine.co.nz. All rights reserved.
 *
 * This program is licensed to you under the Apache License Version 2.0,
 * and you may not use this file except in compliance with the Apache License Version 2.0.
 * You may obtain a copy of the Apache License Version 2.0 at http://www.apache.org/licenses/LICENSE-2.0.
 *
 * Unless required by applicable law or agreed to in writing,
 * software distributed under the Apache License Version 2.0 is distributed on an
 * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the Apache License Version 2.0 for the specific language governing permissions and limitations there under.
 */
package net.stickycode.deploy.tomcat;

import org.apache.catalina.Engine;
import org.apache.catalina.LifecycleException;
import org.apache.catalina.connector.Connector;
import org.apache.catalina.core.StandardContext;
import org.apache.catalina.core.StandardHost;
import org.apache.catalina.loader.WebappLoader;
import org.apache.catalina.startup.ContextConfig;
import org.apache.catalina.startup.Embedded;

public class TomcatDeployer {


  public class EmbeddedDeployer
      extends Embedded {
    public boolean isStarted() {
      return started;
    }
  }

  private EmbeddedDeployer container;
  private Engine engine;
  private StandardHost host;
  private StandardContext context;

  private final DeploymentConfiguration configuration;

  public TomcatDeployer(DeploymentConfiguration configuration) {
    super();
    this.configuration = configuration;
  }

  public void deploy() {
    createContainer();
    createEngine();
    createDefaultHost();
    createContextForWar();
    listenToHttpOnPort();

    try {
      container.start();
    }
    catch (LifecycleException e) {
      throw new FailedToStartDeploymentException(e);
    }

    if (!context.getAvailable())
      throw new FailedToStartDeploymentException();
  }

  private void listenToHttpOnPort() {
    Connector connector = container.createConnector(configuration.getBindAddress(), configuration.getPort(), "http");
    container.addConnector(connector);
  }

  private void createContextForWar() {
    StandardContext context = new StandardContext();
    context.setDocBase(configuration.getWar().getAbsolutePath());
    context.setPath(configuration.getContextPath());
    context.setLoader(new WebappLoader());
    context.setProcessTlds(false);
    context.setTldNamespaceAware(false);
    context.setAntiResourceLocking(false);

    ContextConfig listener = new ContextConfig();
    listener.setDefaultWebXml("META-INF/sticky/stripped-web.xml");
    context.addLifecycleListener(listener);

    host.addChild(context);
    this.context = context;
  }

  private void createDefaultHost() {
    host = new StandardHost();
    host.setName("sticky-host");
    host.setUnpackWARs(false);
    host.setName("sticky-host");
    engine.addChild(host);
    engine.setDefaultHost(host.getName());
  }

  private void createEngine() {
    engine = container.createEngine();
    engine.setName("sticky-" + System.currentTimeMillis());
    container.addEngine(engine);
  }

  public void stop() {
    try {
      container.stop();
    }
    catch (LifecycleException e) {
      throw new FailedToStopDeploymentException(e);
    }
  }

  private void createContainer() {
    container = new EmbeddedDeployer();
    container.setName("sticky-container");
    container.setUseNaming(true);
    container.setCatalinaHome(configuration.getWorkingDirectory().getAbsolutePath());
    container.setCatalinaBase(configuration.getWorkingDirectory().getAbsolutePath());
  }
}
@@ -17,17 +17,17 @@
  (c) 201
-0
+1
  RedEngi
@@ -752,16 +752,200 @@
 omcat;%0A%0A
+import java.io.BufferedReader;%0Aimport java.io.IOException;%0Aimport java.io.InputStreamReader;%0Aimport java.io.PrintWriter;%0Aimport java.net.Socket;%0Aimport java.net.UnknownHostException;%0A%0A
 import o
@@ -2134,16 +2134,813 @@
 ption();
+%0A%0A    verifyListening();%0A  %7D%0A%0A  private void verifyListening()%7B%0A    try %7B%0A      Socket s = new Socket(configuration.getBindAddress(), configuration.getPort());%0A      PrintWriter w = new PrintWriter(s.getOutputStream());%0A      w.print(%22OPTIONS * HTTP/1.1%5Cr%5CnHOST: web%5Cr%5Cn%5Cr%5Cn%22);%0A      w.flush();%0A      BufferedReader r = new BufferedReader(new InputStreamReader(s.getInputStream(), %22UTF-8%22));%0A      String pingResult = r.readLine();%0A      s.close();%0A      if (!%22HTTP/1.1 200 OK%22.equals(pingResult))%0A        throw new FailedToStartDeploymentException(%22Options test after start returned '%22 + pingResult + %22'%22);%0A%0A    %7D%0A    catch (UnknownHostException e) %7B%0A      throw new FailedToStartDeploymentException(e);%0A    %7D%0A    catch (IOException e) %7B%0A      throw new FailedToStartDeploymentException(e);%0A    %7D
 %0A  %7D%0A%0A  
@@ -3831,24 +3831,24 @@
 cky-host%22);%0A
+
     host.set
@@ -3870,41 +3870,8 @@
 e);%0A
-    host.setName(%22sticky-host%22);%0A
     

Test that a * options request return ok on start, its the most common connect test so is good validation that tomcat is running