ProcessStarter.java :  » Content-Management-System » webman » com » teamkonzept » webman » Java Open Source

Java Open Source » Content Management System » webman 
webman » com » teamkonzept » webman » ProcessStarter.java
package com.teamkonzept.webman;

import java.io.*;
import java.net.*;

import com.teamkonzept.lib.*;
import com.teamkonzept.web.TKEvent;
import com.teamkonzept.web.TKHttpInterface;
import org.apache.log4j.Category;

/**
 * Starts an external java process.
 * <p>
 * To use the ProcessStarter create an instance of the class, then call "start".
 * All output of the running process to stdout and stderr can be redirected
 * to some PrintWriters specified in the constructor.
 * @author $Author: gregor $
 * @version $Revision: 1.16 $
 */
public class ProcessStarter 
{

  /** Logging Category */
  private  static Category cat = Category.getInstance(ProcessStarter.class.getName());

    /** Setze SocketTimeout deswegen so hoch (30 min), weil der Stager (d.h. SiteTransmitter) 
   u.U. ber einen laaangen Zeitraum nichts an den ProcessStarter sendet (nmlich beim bertragen der Site)
   Bricht dann der ProcessStarter whrend dessen die Verbindung ab, wird der Socket also nicht mehr ausgelesen,
   so schreibt der SiteTransmitter, wenn er die Site fertig bertragen hat, seine Ausgaben trotzdem weiter in den Socket
   -> Buffer is irgendwann voll -> SiteTransmitter kann nich mehr schreiben -> SiteTransmitter hngt, wird nich mehr fertig
   Da dieses Timeout ziemlich hoch ist, sollte versucht werden, es davon abhngig zu setzen, ob nun der Generator oder der
   Stager gestartet wird*/
  private final static int SOCKET_TIME_OUT = 1800000;

    /** ... */
    private PrintWriter out;
    private PrintWriter err;

    /**
     * a tag used to identified a keep alive log message send from the
     * generator
     **/
    public final static String KEEP_ALIVE_TAG = "-- keep alive --";

    /**
    Constructor.
    @param out a PrintWriter to which stdout messages of the process are redirected.
    @param err a PrintWriter to which stderr messages of the process are redirected.
    */
    public ProcessStarter (PrintWriter out, PrintWriter err)
    {
        this.out = out;
        this.err = err;
    }

    /**
    Starts the process. The default classpath will be the the classpath as given
    by System.getProperty("java.class.path") of the parent process.
    @param startClassname the name of the java class to start (should
        contain a main-method)
    @param arguments the (optional) argument string given to the proces
    @param addClasspath some additional classpath strings added to the default
        classpath. The string should start with a classpath separator.
    */
    public boolean start(String startClassname, String arguments, String addClasspath)
    {
        Runtime rt = Runtime.getRuntime();
    Process proc = null;
    ServerSocket server = null;
    try 
    {
      // Serversocket starten - welcher Port ???
      server = new ServerSocket(0);
      int port = server.getLocalPort();
        String startCmd = genStartCmd(startClassname, arguments + " port=" +port, addClasspath);
        ProcessStarter.cat.debug(startCmd);
        proc = rt.exec(startCmd);
      Socket socket = server.accept();
      //Kommentar zum SocketTimeout s.o.
        socket.setSoTimeout(SOCKET_TIME_OUT);
      InputStream in = socket.getInputStream();
      BufferedReader reader = new BufferedReader(new InputStreamReader(in));
      String line;
      while ((line = reader.readLine()) != null) 
      {
                if (!line.endsWith(KEEP_ALIVE_TAG)) {
                    out.println(line);
                    out.flush();
                }

          /*
            try {
            Thread.sleep(100);
          } catch (InterruptedException e) {
            out.println(e.toString());
          }
          */
          }
          /*
          reader = new BufferedReader(new InputStreamReader(proc.getErrorStream()));
      while ((line = reader.readLine()) != null) {
          err.println(line);
          err.flush();
       }
       */
      }
      catch (Exception e) 
      {
          ProcessStarter.cat.error("Processstarter.start", e);
      }
    finally 
    {
      try
      {
        server.close();
      }
      catch (Exception e)
      {
        ProcessStarter.cat.warn("Processstarter.start.finally", e);
      }
    }
    try {
      if (proc != null)
        proc.waitFor();
    }
    catch (InterruptedException e) 
    {
        ProcessStarter.cat.warn("Processstarter.start.waitfor", e);
    }

    int exitValue = proc.exitValue();

    proc.destroy();

    return exitValue == 0;
    }


    /**
  Determines the path to the webman classes.
    The returned string is of the form:
    "docRoot/WEB-INF/classes;docRoot/WEB-INF/classes/webman.zip"
  ("WEB-INF/classes" accords with the Java Servlet 2.2 recommendation.)
  @param docRoot the absolute path to the document root of the web application
  */
  // TODO: put this method in a a web application interface class?
  public static String getWMClasspath(String docRoot)
  {
      String pathSeparator = System.getProperty("path.separator");
      String servletDir = pathSeparator + docRoot + File.separator +
          "WEB-INF" + File.separator + "classes";
      // there should be a WEB-INF/lib dir with some jar files...
      String addPath = "";
      String libDir = docRoot + "WEB-INF" + File.separator + "lib";
      File d = new File(libDir);
      libDir = pathSeparator + libDir + File.separator;
      if ( d.isDirectory() )
      {
      String[] list = d.list();
      for ( int i = 0; i < list.length; i++ )
          if ( list[i].endsWith(".jar")
        || list[i].endsWith(".zip") )
        addPath += libDir + list[i];
      }
      // hier Spezial fuer Tomcat 4.0 und servlet.jar
      String privateDir = docRoot + "WEB-INF" + File.separator + "lib" + File.separator + "webman-only";
      libDir = pathSeparator + privateDir + File.separator;
      d = new File(privateDir);
      if ( d.isDirectory() )
      {
      String[] list = d.list();
      for ( int i = 0; i < list.length; i++ )
          if ( list[i].endsWith(".jar")
        || list[i].endsWith(".zip") )
        addPath += libDir + list[i];
      }
      return servletDir + addPath;
  }

  /**
    Generates the start string which can be passed to the Runtime.exec() method.
    @see ProcessStarter.start()
    @return the generated string
    */
    protected String genStartCmd(String startClassname, String arguments,
                                String addClasspath)
    {
        String javaHome = System.getProperty("java.home");
    String javaProg = javaHome + File.separator + "bin" + File.separator + "java";
    String javaClasspath = System.getProperty("java.class.path") + addClasspath;
    
    // Memory Einstellungen fr den Start !
    String memory = getMemoryProps();
        String cmd = javaProg + memory + " -classpath " + javaClasspath + " " + startClassname + " " + arguments;

        String os = System.getProperty("os.name");
        if (os.equalsIgnoreCase("Windows NT"))
        {
            cmd = "cmd.exe /c " + cmd;
      }
        ProcessStarter.cat.debug(cmd);
      return cmd;
    }

    private String getMemoryProps()
    {
        try
        {
            PropertyManager man = PropertyManager.getPropertyManager("MEMORY_EXTERNAL");
            String initial = man.getValue("INITIAL_HEAP", null);
            String max = man.getValue("MAX_HEAP", null);
            String back = " ";
            if (initial != null)
                back += "-Xms" + initial +  " ";
            if (max != null)
                back += "-Xmx" + max + " ";
            return back;
        }
        catch (Exception e)
        {
          ProcessStarter.cat.info("getMemoryProps(): exception caught");
        }
        return "";
    }
    
    /**
  Determine if the host operating system is a Microsoft OS
  
  private static boolean isMSOS()
    {
        // TODO: Abfrage vollstaendig machen...
      String os = System.getProperty("os.name");
      if (os.equalsIgnoreCase("Windows NT") ||
          os.equalsIgnoreCase("Windows 95") ||
          os.equalsIgnoreCase("Windows 98")) {
          return true;
        }
        else {
            return false;
        }
    }*/

}
java2s.com  | Contact Us | Privacy Policy
Copyright 2009 - 12 Demo Source and Support. All rights reserved.
All other trademarks are property of their respective owners.