tomcat-dev mailing list archives

Site index · List index
Message view « Date » · « Thread »
Top « Date » · « Thread »
From gl...@apache.org
Subject cvs commit: jakarta-tomcat-4.0/webapps/tomcat-docs/config host.xml
Date Fri, 10 Jan 2003 15:52:19 GMT
glenn       2003/01/10 07:52:19

  Modified:    .        RELEASE-NOTES-4.1.txt build.properties.sample
               catalina build.xml
               catalina/src/share/org/apache/catalina Deployer.java
               catalina/src/share/org/apache/catalina/core
                        LocalStrings.properties StandardHost.java
                        StandardHostDeployer.java
               catalina/src/share/org/apache/catalina/servlets
                        HTMLManagerServlet.java LocalStrings.properties
                        LocalStrings_fr.properties
                        LocalStrings_ja.properties ManagerServlet.java
               catalina/src/share/org/apache/catalina/startup
                        HostConfig.java LocalStrings.properties
                        LocalStrings_fr.properties
                        LocalStrings_ja.properties
               webapps/manager build.xml
               webapps/manager/WEB-INF web.xml
               webapps/tomcat-docs index.xml manager-howto.xml project.xml
               webapps/tomcat-docs/config host.xml
  Added:       catalina/src/share/org/apache/catalina/startup
                        ExpandWar.java
               webapps/tomcat-docs html-manager-howto.xml
  Log:
  Bug fixes and minor improvements to the manager and html manager web
  applications.  These patches fix as many of the 11 bugs I found for
  the manager in bugzilla that I could reproduce.
  
  manager web application
  -----------------------
  
  Bug #5551 - Enhancement, added /serverinfo command to list Tomcat, OS, and JVM properties
  Bug #7826 - Bug fix, make sure content type is set correctly for locale
  Bug #8969 - Bug fix, manager remove was not removing the webapp directory/war in the appBase
  Bug #13893 - Bug fix, manager remove was not removing the web application work directory
  
  How /deploy and /undeploy work was not changed
  
  /install war parameter will now accept a directory name or war file name without
  a URL or path.  It will look for that directory or war file in the Host appBase directory.
  This makes it easier to install web application directories and war files located in
  the Host appBase.
  
  /install will no longer allow installing web application directories or war files which
  are not located in the Host appBase if deployXML=false. This is for security when
  virtual hosting customers.
  
  /install will now unarchive a WAR if the war is located in the Host appBase and
  unpackWARs=true for the Host. To do this I had to factor out the code in
  startup/HostConfig.java which expands war files out into a seperate class.
  
  /install no longer requires a context path, if no context path is entered it
  will use the name of the web application directory or war file without the
  ".war" extension as the context path name.
  
  /install verifies that the context path name is the same as the web application
  directory name or war file name without the ".war" extension if the directory
  or war is located in the Host appbase and either autoDeploy=true or liveDeploy=true.
  This change is so that the mananger works consistent with how autoDeploy and liveDeploy
  work when Tomcat is restarted.
  
  /remove will now remove the web application directory and/or war file if
  the web application directory and/or war is located in the Host appBase and
  either autoDeploy=true or liveDeploy=true. This change is so that the mananger
  works consistent with how autoDeploy and liveDeploy work when Tomcat is restarted.
  
  /remove will now remove the web application temporary work directory
  
  Manager How-To docs
  -------------------
  
  Bug #5629 - Doc bug fix, documented that a reload does not reload the web.xml
  
  There was no documentation for installing a Context configuration .xml file,
  added documentation for this and reorganized the install docs.
  
  Removed documentation for using an http URL for installing a war.
  Support for this was removed a while ago.
  
  Updated the documenation for changes to the manager.
  
  html manager web application
  ----------------------------
  
  Bug #13205 - Bug fix, HTML Manager threw NPE if XML Config field was empty
  Bug #7826 - Bug fix, make sure content type is set correctly for locale
  
  Wrote new html-manager-howto.xml documentation.
  
  Added documentation to the web application, both the manager-howto.html
  and the html-manager-howto.html docs. (With no tomcat-docs left nav menu)
  
  Added the tomcat-docs header and footer to the application.
  
  Added the ability to upload and install a war file.  This adds a
  dependency on Jakarta commons-fileupload.  We will need to ask
  commons to work on a release of commons-fileupload.
  
  Added support for URL rewriting so that manager can be used if someone
  has cookies disabled.
  
  Revision  Changes    Path
  1.44      +10 -1     jakarta-tomcat-4.0/RELEASE-NOTES-4.1.txt
  
  Index: RELEASE-NOTES-4.1.txt
  ===================================================================
  RCS file: /home/cvs/jakarta-tomcat-4.0/RELEASE-NOTES-4.1.txt,v
  retrieving revision 1.43
  retrieving revision 1.44
  diff -u -r1.43 -r1.44
  --- RELEASE-NOTES-4.1.txt	31 Dec 2002 14:12:05 -0000	1.43
  +++ RELEASE-NOTES-4.1.txt	10 Jan 2003 15:52:17 -0000	1.44
  @@ -212,6 +212,11 @@
   [4.1.17] Default configuration:
            Connector performance tweaks.
   
  +[4.1.19] Manager and HTML Manager web applications
  +         Fix bugs 5551, 7826, 8969, 13983, 5629, and 13205
  +         Updated documentation and added some minor new features.
  +         See the Manager App HOW-TO and HTML Manager App HOW-TO
  +         documentation for more information.
   
   ------------------
   Catalina Bug Fixes:
  @@ -1060,6 +1065,10 @@
   freed by stopping Tomcat and then restarting it.
   
   The JSP command line compiler (JSPC) can also be used to precompile the JSPs.
  +
  +You can prevent this by setting the JspServlet init parameter fork to true
  +in conf/web.xml. This tells jasper to invoke java compiles of JSP pages
  +as an external process.
   
   
   -------------------------------
  
  
  
  1.55      +6 -1      jakarta-tomcat-4.0/build.properties.sample
  
  Index: build.properties.sample
  ===================================================================
  RCS file: /home/cvs/jakarta-tomcat-4.0/build.properties.sample,v
  retrieving revision 1.54
  retrieving revision 1.55
  diff -u -r1.54 -r1.55
  --- build.properties.sample	12 Nov 2002 16:34:57 -0000	1.54
  +++ build.properties.sample	10 Jan 2003 15:52:17 -0000	1.55
  @@ -162,6 +162,11 @@
   commons-pool.jar=${commons-pool.lib}/commons-pool.jar
   commons-pool.loc=http://jakarta.apache.org/builds/jakarta-commons/release/commons-pool/v1.0.1/commons-pool-1.0.1.tar.gz
   
  +# ----- Commons FileUpload, nightly build -----
  +commons-fileupload.home=${base.path}/commons-fileupload
  +commons-fileupload.lib=${commons-fileupload.home}
  +commons-fileupload.jar=${commons-fileupload.lib}/commons-fileupload-1.0-dev.jar
  +#commons-fileupload.loc=http://jakarta.apache.org/builds/jakarta-commons/nightly/commons-fileupload/commons-fileupload-20030106.zip
   
   # ----- JavaService, version 1.2.0 or later -----
   javaservice.home=${base.path}/javaservice
  
  
  
  1.131     +13 -1     jakarta-tomcat-4.0/catalina/build.xml
  
  Index: build.xml
  ===================================================================
  RCS file: /home/cvs/jakarta-tomcat-4.0/catalina/build.xml,v
  retrieving revision 1.130
  retrieving revision 1.131
  diff -u -r1.130 -r1.131
  --- build.xml	21 Sep 2002 16:21:49 -0000	1.130
  +++ build.xml	10 Jan 2003 15:52:18 -0000	1.131
  @@ -54,6 +54,7 @@
       <pathelement location="${commons-daemon.jar}"/>
       <pathelement location="${commons-dbcp.jar}"/>
       <pathelement location="${commons-digester.jar}"/>
  +    <pathelement location="${commons-fileupload.jar}"/>
       <pathelement location="${commons-logging.jar}"/>
       <pathelement location="${commons-modeler.jar}"/>
       <pathelement location="${commons-pool.jar}"/>
  @@ -87,6 +88,7 @@
       <pathelement location="${commons-daemon.jar}"/>
       <pathelement location="${commons-dbcp.jar}"/>
       <pathelement location="${commons-digester.jar}"/>
  +    <pathelement location="${commons-fileupload.jar}"/>
       <pathelement location="${commons-logging.jar}"/>
       <pathelement location="${commons-modeler.jar}"/>
       <pathelement location="${commons-pool.jar}"/>
  @@ -153,6 +155,9 @@
       <available property="digester.present"
        classname="org.apache.commons.digester.Digester"
        classpath="${commons-digester.jar}"/>
  +    <available property="fileupload.present"
  +     classname="org.apache.commons.fileupload.FileUpload"
  +     classpath="${commons-fileupload.jar}"/>
       <available property="logging.present"
        classname="org.apache.commons.logging.Log"
        classpath="${commons-logging.jar}"/>
  @@ -227,6 +232,7 @@
       <!-- JAR files availability flags -->
       <available property="daemon.jar.present" file="${commons-daemon.jar}" />
       <available property="dbcp.jar.present" file="${commons-dbcp.jar}" />
  +    <available property="fileupload.jar.present" file="${commons-fileupload.jar}" />
       <available property="jaas.jar.present" file="${jaas.jar}" />
       <condition property="javamail.jar.present">
         <and>
  @@ -584,6 +590,7 @@
       <echo message="--- Optional Libraries ---" />
       <echo message="daemon.present=${daemon.present}" />
       <echo message="dbcp.present=${dbcp.present}" />
  +    <echo message="fileupload.present=${fileupload.present}" />
       <echo message="jaas.present=${jaas.present}" />
       <echo message="javamail.present=${javamail.present}" />
       <echo message="jmx.present=${jmx.present}" />
  @@ -605,6 +612,7 @@
       <echo message="--- Optional JARs ---" />
       <echo message="daemon.jar.present=${daemon.jar.present}" />
       <echo message="dbcp.jar.present=${dbcp.jar.present}" />
  +    <echo message="fileupload.jar.present=${fileupload.jar.present}" />
       <echo message="jaas.jar.present=${jaas.jar.present}" />
       <echo message="javamail.jar.present=${javamail.jar.present}" />
       <echo message="jdbc20ext.jar.present=${jdbc20ext.jar.present}" />
  @@ -680,6 +688,10 @@
     <target name="copy-dbcp.jar" if="copy.dbcp.jar">
       <copy todir="${catalina.build}/common/lib" file="${commons-dbcp.jar}"/>
     </target>
  +  <target name="copy-fileupload.jar" if="fileupload.jar.present">
  +    <copy todir="${catalina.build}/server/lib"
  +          file="${commons-fileupload.jar}"/>
  +  </target>
     <target name="copy-jaas.jar" if="copy.jaas.jar">
       <copy todir="${catalina.build}/server/lib" file="${jaas.jar}"/>
     </target>
  @@ -733,7 +745,7 @@
   
   
     <!-- =================== BUILD: Copy Static Files ======================= -->
  -  <target name="build-static" depends="flags,flags.display,build-prepare,copy-activation.jar,copy-daemon.jar,copy-dbcp.jar,copy-jaas.jar,copy-jdbc20ext.jar,copy-jmx.jar,copy-jndi.jar,copy-jsse.jar,copy-jta.jar,copy-ldap.jar,copy-modeler.jar,copy-pool.jar,copy-tyrex.jar,copy-xerces.jar,copy-xerces2.jars">
  +  <target name="build-static" depends="flags,flags.display,build-prepare,copy-activation.jar,copy-daemon.jar,copy-dbcp.jar,copy-fileupload.jar,copy-jaas.jar,copy-jdbc20ext.jar,copy-jmx.jar,copy-jndi.jar,copy-jsse.jar,copy-jta.jar,copy-ldap.jar,copy-modeler.jar,copy-pool.jar,copy-tyrex.jar,copy-xerces.jar,copy-xerces2.jars">
   
       <!-- Executable Commands -->
       <copy todir="${catalina.build}/bin">
  
  
  
  1.7       +25 -4     jakarta-tomcat-4.0/catalina/src/share/org/apache/catalina/Deployer.java
  
  Index: Deployer.java
  ===================================================================
  RCS file: /home/cvs/jakarta-tomcat-4.0/catalina/src/share/org/apache/catalina/Deployer.java,v
  retrieving revision 1.6
  retrieving revision 1.7
  diff -u -r1.6 -r1.7
  --- Deployer.java	9 Apr 2002 23:48:21 -0000	1.6
  +++ Deployer.java	10 Jan 2003 15:52:18 -0000	1.7
  @@ -209,6 +209,27 @@
   
   
       /**
  +     * Remove an existing web application, attached to the specified context
  +     * path.  If this application is successfully removed, a
  +     * ContainerEvent of type <code>REMOVE_EVENT</code> will be sent to all
  +     * registered listeners, with the removed <code>Context</code> as
  +     * an argument. Deletes the web application war file and/or directory
  +     * if they exist in the Host's appBase.
  +     *
  +     * @param contextPath The context path of the application to be removed
  +     * @param undeploy boolean flag to remove web application from server
  +     *
  +     * @exception IllegalArgumentException if the specified context path
  +     *  is malformed (it must be "" or start with a slash)
  +     * @exception IllegalArgumentException if the specified context path does
  +     *  not identify a currently installed web application
  +     * @exception IOException if an input/output error occurs during
  +     *  removal
  +     */
  +    public void remove(String contextPath, boolean undeploy) throws IOException;
  +
  +
  +    /**
        * Start an existing web application, attached to the specified context
        * path.  Only starts a web application if it is not running.
        *
  
  
  
  1.48      +2 -0      jakarta-tomcat-4.0/catalina/src/share/org/apache/catalina/core/LocalStrings.properties
  
  Index: LocalStrings.properties
  ===================================================================
  RCS file: /home/cvs/jakarta-tomcat-4.0/catalina/src/share/org/apache/catalina/core/LocalStrings.properties,v
  retrieving revision 1.47
  retrieving revision 1.48
  diff -u -r1.47 -r1.48
  --- LocalStrings.properties	5 Nov 2002 11:36:16 -0000	1.47
  +++ LocalStrings.properties	10 Jan 2003 15:52:18 -0000	1.48
  @@ -94,6 +94,7 @@
   standardHost.appBase=Application base directory {0} does not exist
   standardHost.configRequired=URL to configuration file is required
   standardHost.configNotAllowed=Use of configuration file is not allowed
  +standardHost.installBase=Only web applications in the Host web application directory can be installed
   standardHost.installing=Installing web application at context path {0} from URL {1}
   standardHost.installingWAR=Installing web application from URL {0}
   standardHost.installError=Error deploying application at context path {0}
  @@ -106,6 +107,7 @@
   standardHost.notStarted=Host has not yet been started
   standardHost.nullName=Host name is required
   standardHost.pathFormat=Invalid context path: {0}
  +standardHost.pathMatch=Context path {0} must match the directory or WAR file name: {1}
   standardHost.pathMissing=Context path {0} is not currently in use
   standardHost.pathRequired=Context path is required
   standardHost.pathUsed=Context path {0} is already in use
  
  
  
  1.30      +29 -4     jakarta-tomcat-4.0/catalina/src/share/org/apache/catalina/core/StandardHost.java
  
  Index: StandardHost.java
  ===================================================================
  RCS file: /home/cvs/jakarta-tomcat-4.0/catalina/src/share/org/apache/catalina/core/StandardHost.java,v
  retrieving revision 1.29
  retrieving revision 1.30
  diff -u -r1.29 -r1.30
  --- StandardHost.java	9 Jun 2002 02:19:42 -0000	1.29
  +++ StandardHost.java	10 Jan 2003 15:52:18 -0000	1.30
  @@ -855,6 +855,31 @@
   
   
       /**
  +     * Remove an existing web application, attached to the specified context
  +     * path.  If this application is successfully removed, a
  +     * ContainerEvent of type <code>REMOVE_EVENT</code> will be sent to all
  +     * registered listeners, with the removed <code>Context</code> as
  +     * an argument. Deletes the web application war file and/or directory
  +     * if they exist in the Host's appBase.
  +     *
  +     * @param contextPath The context path of the application to be removed
  +     * @param undeploy boolean flag to remove web application from server
  +     *
  +     * @exception IllegalArgumentException if the specified context path
  +     *  is malformed (it must be "" or start with a slash)
  +     * @exception IllegalArgumentException if the specified context path does
  +     *  not identify a currently installed web application
  +     * @exception IOException if an input/output error occurs during
  +     *  removal
  +     */
  +    public void remove(String contextPath, boolean undeploy) throws IOException {
  +
  +        deployer.remove(contextPath,undeploy);
  +
  +    }
  +
  +
  +    /**
        * Start an existing web application, attached to the specified context
        * path.  Only starts a web application if it is not running.
        *
  
  
  
  1.11      +175 -4    jakarta-tomcat-4.0/catalina/src/share/org/apache/catalina/core/StandardHostDeployer.java
  
  Index: StandardHostDeployer.java
  ===================================================================
  RCS file: /home/cvs/jakarta-tomcat-4.0/catalina/src/share/org/apache/catalina/core/StandardHostDeployer.java,v
  retrieving revision 1.10
  retrieving revision 1.11
  diff -u -r1.10 -r1.11
  --- StandardHostDeployer.java	1 Aug 2002 01:41:43 -0000	1.10
  +++ StandardHostDeployer.java	10 Jan 2003 15:52:18 -0000	1.11
  @@ -80,6 +80,7 @@
   import org.apache.catalina.LifecycleException;
   import org.apache.catalina.LifecycleListener;
   import org.apache.catalina.startup.ContextRuleSet;
  +import org.apache.catalina.startup.ExpandWar;
   import org.apache.catalina.startup.NamingRuleSet;
   import org.apache.catalina.util.StringManager;
   import org.apache.commons.digester.Digester;
  @@ -230,8 +231,14 @@
                                 contextPath, war.toString()));
           String url = war.toString();
           String docBase = null;
  +        boolean isWAR = false;
           if (url.startsWith("jar:")) {
               url = url.substring(4, url.length() - 2);
  +            if (!url.toLowerCase().endsWith(".war")) {
  +                throw new IllegalArgumentException
  +                    (sm.getString("standardHost.warURL", url));
  +            }
  +            isWAR = true;
           }
           if (url.startsWith("file://"))
               docBase = url.substring(7);
  @@ -241,6 +248,43 @@
               throw new IllegalArgumentException
                   (sm.getString("standardHost.warURL", url));
   
  +        // Determine if directory/war to install is in the host appBase
  +        boolean isAppBase = false;
  +        File appBase = new File(host.getAppBase());
  +        File contextFile = new File(docBase);
  +        File baseDir = contextFile.getParentFile();
  +        if (appBase.getCanonicalPath().equals(baseDir.getCanonicalPath())) {
  +            isAppBase = true;
  +        }
  +
  +        // For security, if deployXML is false only allow directories
  +        // and war files from the hosts appBase
  +        if (!host.isDeployXML() && !isAppBase) {
  +            throw new IllegalArgumentException
  +                (sm.getString("standardHost.installBase", url));
  +        }
  +
  +        // Make sure contextPath and directory/war names match when
  +        // installing from the host appBase
  +        if (isAppBase && (host.getAutoDeploy() || host.getLiveDeploy())) {
  +            String filename = contextFile.getName();
  +            if (isWAR) {
  +                filename = filename.substring(0,filename.length()-4);
  +            }
  +            if (contextPath.length() == 0 && !filename.equals("ROOT")) {
  +                throw new IllegalArgumentException
  +                    (sm.getString("standardHost.pathMatch", "/", "ROOT"));
  +            } else if (!filename.equals(contextPath.substring(1))) {
  +                throw new IllegalArgumentException
  +                    (sm.getString("standardHost.pathMatch", contextPath, filename));
  +            }
  +        }
  +
  +        // Expand war file if host wants wars unpacked
  +        if (isWAR && host.isUnpackWARs()) {
  +            docBase = ExpandWar.expand(host,war,contextPath);
  +        }
  +
           // Install the new web application
           try {
               Class clazz = Class.forName(host.getContextClass());
  @@ -428,6 +472,110 @@
   
   
       /**
  +     * Remove an existing web application, attached to the specified context
  +     * path.  If this application is successfully removed, a
  +     * ContainerEvent of type <code>REMOVE_EVENT</code> will be sent to all
  +     * registered listeners, with the removed <code>Context</code> as
  +     * an argument. Deletes the web application war file and/or directory
  +     * if they exist in the Host's appBase.
  +     *
  +     * @param contextPath The context path of the application to be removed
  +     * @param undeploy boolean flag to remove web application from server
  +     *
  +     * @exception IllegalArgumentException if the specified context path
  +     *  is malformed (it must be "" or start with a slash)
  +     * @exception IllegalArgumentException if the specified context path does
  +     *  not identify a currently installed web application
  +     * @exception IOException if an input/output error occurs during
  +     *  removal
  +     */
  +    public void remove(String contextPath, boolean undeploy) throws IOException {
  +
  +        // Validate the format and state of our arguments
  +        if (contextPath == null)
  +            throw new IllegalArgumentException
  +                (sm.getString("standardHost.pathRequired"));
  +        if (!contextPath.equals("") && !contextPath.startsWith("/"))
  +            throw new IllegalArgumentException
  +                (sm.getString("standardHost.pathFormat", contextPath));
  +
  +        // Locate the context and associated work directory
  +        Context context = findDeployedApp(contextPath);
  +        if (context == null)
  +            throw new IllegalArgumentException
  +                (sm.getString("standardHost.pathMissing", contextPath));
  +
  +        // Remove this web application
  +        host.log(sm.getString("standardHost.removing", contextPath));
  +        try {
  +            // Get the work directory for the Context
  +            File workDir = (File)
  +                context.getServletContext().getAttribute(Globals.WORK_DIR_ATTR);
  +            host.removeChild(context);
  +
  +            if (undeploy) {
  +                // Remove the web application directory and/or war file if it
  +                // exists in the Host's appBase directory.
  +    
  +                // Determine if directory/war to remove is in the host appBase
  +                boolean isAppBase = false;
  +                File appBase = new File(host.getAppBase());
  +                File contextFile = new File(context.getDocBase());
  +                File baseDir = contextFile.getParentFile();
  +                if (appBase.getCanonicalPath().equals(baseDir.getCanonicalPath())) {
  +                    isAppBase = true;
  +                }
  +    
  +                boolean isWAR = false;
  +                if (contextFile.getName().toLowerCase().endsWith(".war")) {
  +                    isWAR = true;
  +                }
  +    
  +                // Only remove directory and/or war if they are located in the
  +                // Host's appBase and autoDeploy or liveDeploy are true
  +                if (isAppBase && (host.getAutoDeploy() || host.getLiveDeploy())) {
  +                    String filename = contextFile.getName();
  +                    if (isWAR) {
  +                        filename = filename.substring(0,filename.length()-4);
  +                    }
  +                    if (contextPath.length() == 0 && filename.equals("ROOT") ||
  +                        filename.equals(contextPath.substring(1))) {
  +                        if (!isWAR) {
  +                            if (contextFile.isDirectory()) {
  +                                deleteDir(contextFile);
  +                            }
  +                            if (host.isUnpackWARs()) {
  +                                File contextWAR = new File(context.getDocBase() + ".war");
  +                                if (contextWAR.exists()) {
  +                                    contextWAR.delete();
  +                                }
  +                            }
  +                        } else {
  +                            contextFile.delete();
  +                        }
  +                    }
  +                    if (host.isDeployXML()) {
  +                        File docBaseXml = new File(appBase,filename + ".xml");
  +                        docBaseXml.delete();
  +                    }
  +                }
  +    
  +                // Remove the work directory for the Context
  +                if (workDir != null && workDir.exists()) {
  +                    deleteDir(workDir);
  +                }
  +            }
  +
  +            host.fireContainerEvent(REMOVE_EVENT, context);
  +        } catch (Exception e) {
  +            host.log(sm.getString("standardHost.removeError", contextPath), e);
  +            throw new IOException(e.toString());
  +        }
  +
  +    }
  +
  +
  +    /**
        * Start an existing web application, attached to the specified context
        * path.  Only starts a web application if it is not running.
        *
  @@ -565,5 +713,28 @@
   
       }
   
  +    /**
  +     * Delete the specified directory, including all of its contents and
  +     * subdirectories recursively.
  +     *
  +     * @param dir File object representing the directory to be deleted
  +     */
  +    protected void deleteDir(File dir) {
  +
  +        String files[] = dir.list();
  +        if (files == null) {
  +            files = new String[0];
  +        }
  +        for (int i = 0; i < files.length; i++) {
  +            File file = new File(dir, files[i]);
  +            if (file.isDirectory()) {
  +                deleteDir(file);
  +            } else {
  +                file.delete();
  +            }
  +        }
  +        dir.delete();
  +
  +    }
   
   }
  
  
  
  1.13      +466 -216  jakarta-tomcat-4.0/catalina/src/share/org/apache/catalina/servlets/HTMLManagerServlet.java
  
  Index: HTMLManagerServlet.java
  ===================================================================
  RCS file: /home/cvs/jakarta-tomcat-4.0/catalina/src/share/org/apache/catalina/servlets/HTMLManagerServlet.java,v
  retrieving revision 1.12
  retrieving revision 1.13
  diff -u -r1.12 -r1.13
  --- HTMLManagerServlet.java	18 Sep 2002 14:08:34 -0000	1.12
  +++ HTMLManagerServlet.java	10 Jan 2003 15:52:18 -0000	1.13
  @@ -64,12 +64,16 @@
   
   package org.apache.catalina.servlets;
   
  +import java.io.File;
   import java.io.IOException;
   import java.io.PrintWriter;
   import java.io.StringWriter;
  +import java.net.URL;
  +import java.net.MalformedURLException;
   import java.text.MessageFormat;
   import java.util.Date;
   import java.util.Iterator;
  +import java.util.List;
   import java.util.Locale;
   import java.util.Map;
   import java.util.TreeMap;
  @@ -77,7 +81,11 @@
   import javax.servlet.http.HttpServletRequest;
   import javax.servlet.http.HttpServletResponse;
   import org.apache.catalina.Context;
  +import org.apache.catalina.Host;
   import org.apache.catalina.util.ServerInfo;
  +import org.apache.commons.fileupload.FileItem;
  +import org.apache.commons.fileupload.FileUpload;
  +import org.apache.commons.fileupload.FileUploadException;
   
   /**
   * Servlet that enables remote management of the web applications installed
  @@ -127,57 +135,164 @@
           String installWar = request.getParameter("installWar");
   
           // Prepare our output writer to generate the response message
  -        response.setContentType("text/html");
           Locale locale = Locale.getDefault();
  +        String charset = context.getCharsetMapper().getCharset(locale);
           response.setLocale(locale);
  -        PrintWriter writer = response.getWriter();
  +        response.setContentType("text/html; charset=" + charset);
   
  +        String message = "";
           // Process the requested command
  -        if (command == null) {
  -            response.sendRedirect(request.getRequestURI()+"/list");
  +        if (command == null || command.equals("/")) {
           } else if (command.equals("/install")) {
  -            install(writer, installConfig, installPath, installWar);
  +            message = install(installConfig, installPath, installWar);
           } else if (command.equals("/list")) {
  -            list(writer, "");
           } else if (command.equals("/reload")) {
  -            reload(writer, path);
  +            message = reload(path);
           } else if (command.equals("/remove")) {
  -            remove(writer, path);
  +            message = remove(path);
           } else if (command.equals("/sessions")) {
  -            sessions(writer, path);
  +            message = sessions(path);
           } else if (command.equals("/start")) {
  -            start(writer, path);
  +            message = start(path);
           } else if (command.equals("/stop")) {
  -            stop(writer, path);
  +            message = stop(path);
           } else {
  -            String message =
  +            message =
                   sm.getString("managerServlet.unknownCommand", command);
  -            list(writer, message);
           }
   
  -        // Finish up the response
  -        writer.flush();
  -        writer.close();
  +        list(request, response, message);
  +    }
  +
  +    /**
  +     * Process a GET request for the specified resource.
  +     *
  +     * @param request The servlet request we are processing
  +     * @param response The servlet response we are creating
  +     *
  +     * @exception IOException if an input/output error occurs
  +     * @exception ServletException if a servlet-specified error occurs
  +     */
  +    public void doPost(HttpServletRequest request,
  +                      HttpServletResponse response)
  +        throws IOException, ServletException {
  +
  +        // Identify the request parameters that we need
  +        String command = request.getPathInfo();
  +
  +        if (command == null || !command.equals("/upload")) {
  +            doGet(request,response);
  +            return;
  +        }
  +
  +        // Prepare our output writer to generate the response message
  +        Locale locale = Locale.getDefault();
  +        String charset = context.getCharsetMapper().getCharset(locale);
  +        response.setLocale(locale);
  +        response.setContentType("text/html; charset=" + charset);
  +
  +        String message = "";
  +
  +        // Create a new file upload handler
  +        FileUpload upload = new FileUpload();
  +
  +        // Get the tempdir
  +        File tempdir = (File) getServletContext().getAttribute
  +            ("javax.servlet.context.tempdir");
  +        // Set upload parameters
  +        upload.setSizeMax(-1);
  +        upload.setRepositoryPath(tempdir.getCanonicalPath());
  +    
  +        // Parse the request
  +        String war = null;
  +        FileItem warUpload = null;
  +        try {
  +            List items = upload.parseRequest(request);
  +        
  +            // Process the uploaded fields
  +            Iterator iter = items.iterator();
  +            while (iter.hasNext()) {
  +                FileItem item = (FileItem) iter.next();
  +        
  +                if (!item.isFormField()) {
  +                    if (item.getFieldName().equals("installWar") &&
  +                        warUpload == null) {
  +                        warUpload = item;
  +                    } else {
  +                        item.delete();
  +                    }
  +                }
  +            }
  +            while(true) {
  +                if (warUpload == null) {
  +                    message = sm.getString("htmlManagerServlet.installUploadNoFile");
  +                    break;
  +                }
  +                war = warUpload.getName();
  +                if (!war.toLowerCase().endsWith(".war")) {
  +                    message = sm.getString("htmlManagerServlet.installUploadNotWar",war);
  +                    break;
  +                }
  +                // Identify the appBase of the owning Host of this Context (if any)
  +                String appBase = null;
  +                File appBaseDir = null;
  +                appBase = ((Host) context.getParent()).getAppBase();
  +                appBaseDir = new File(appBase);
  +                if (!appBaseDir.isAbsolute()) {
  +                    appBaseDir = new File(System.getProperty("catalina.base"),
  +                                          appBase);
  +                }
  +                File file = new File(appBaseDir,war);
  +                if (file.exists()) {
  +                    message = sm.getString("htmlManagerServlet.installUploadWarExists",war);
  +                    break;
  +                }
  +                warUpload.write(file.getCanonicalPath());
  +                try {
  +                    URL url = file.toURL();
  +                    war = url.toString();
  +                    war = "jar:" + war + "!/";
  +                } catch(MalformedURLException e) {
  +                    file.delete();
  +                    throw e;
  +                }
  +                break;
  +            }
  +        } catch(Exception e) {
  +            message = sm.getString
  +                ("htmlManagerServlet.installUploadFail", e.getMessage());
  +        } finally {
  +            if (warUpload != null) {
  +                warUpload.delete();
  +            }
  +            warUpload = null;
  +        }
  +
  +        // If there were no errors, install the WAR
  +        if (message.length() == 0) {
  +            message = install(null, null, war);
  +        }
  +
  +        list(request, response, message);
       }
   
       /**
        * Install an application for the specified path from the specified
        * web application archive.
        *
  -     * @param writer Writer to render results to
        * @param config URL of the context configuration file to be installed
        * @param path Context path of the application to be installed
        * @param war URL of the web application archive to be installed
  +     * @return message String
        */
  -    protected void install(PrintWriter writer, String config,
  -                           String path, String war) {
  +    protected String install(String config, String path, String war) {
   
           StringWriter stringWriter = new StringWriter();
           PrintWriter printWriter = new PrintWriter(stringWriter);
   
           super.install(printWriter, config, path, war);
   
  -        list(writer, stringWriter.toString());
  +        return stringWriter.toString();
       }
   
       /**
  @@ -187,33 +302,54 @@
        * @param writer Writer to render to
        * @param message a message to display
        */
  -    public void list(PrintWriter writer, String message) {
  +    public void list(HttpServletRequest request,
  +                     HttpServletResponse response,
  +                     String message) throws IOException {
   
           if (debug >= 1)
               log("list: Listing contexts for virtual host '" +
                   deployer.getName() + "'");
   
  +        PrintWriter writer = response.getWriter();
  +
           // HTML Header Section
           writer.print(HTML_HEADER_SECTION);
   
           // Body Header Section
  -        Object[] args = new Object[1];
  -        args[0] = sm.getString("htmlManagerServlet.title");
  +        Object[] args = new Object[2];
  +        args[0] = request.getContextPath();
  +        args[1] = sm.getString("htmlManagerServlet.title");
           writer.print(MessageFormat.format(BODY_HEADER_SECTION, args));
   
           // Message Section
           args = new Object[3];
           args[0] = sm.getString("htmlManagerServlet.messageLabel");
  -        args[1] = (message != null) ? message : "";
  +        args[1] = (message == null || message.length() == 0) ? "OK" : message;
           writer.print(MessageFormat.format(MESSAGE_SECTION, args));
   
  +        // Manager Section
  +        args = new Object[7];
  +        args[0] = sm.getString("htmlManagerServlet.manager");
  +        args[1] = response.encodeURL(request.getContextPath() + "/html/list");
  +        args[2] = sm.getString("htmlManagerServlet.list");
  +        args[3] = response.encodeURL
  +            (request.getContextPath() + "/" +
  +             sm.getString("htmlManagerServlet.helpHtmlManagerFile"));
  +        args[4] = sm.getString("htmlManagerServlet.helpHtmlManager");
  +        args[5] = response.encodeURL
  +            (request.getContextPath() + "/" +
  +             sm.getString("htmlManagerServlet.helpManagerFile"));
  +        args[6] = sm.getString("htmlManagerServlet.helpManager");
  +        writer.print(MessageFormat.format(MANAGER_SECTION, args));
  +
           // Apps Header Section
  -        args = new Object[5];
  +        args = new Object[6];
           args[0] = sm.getString("htmlManagerServlet.appsTitle");
           args[1] = sm.getString("htmlManagerServlet.appsPath");
           args[2] = sm.getString("htmlManagerServlet.appsName");
           args[3] = sm.getString("htmlManagerServlet.appsAvailable");
           args[4] = sm.getString("htmlManagerServlet.appsSessions");
  +        args[5] = sm.getString("htmlManagerServlet.appsTasks");
           writer.print(MessageFormat.format(APPS_HEADER_SECTION, args));
   
           // Apps Row Section
  @@ -243,24 +379,33 @@
               }
   
               if (context != null ) {
  -                args = new Object[6];
  +                args = new Object[5];
                   args[0] = displayPath;
                   args[1] = context.getDisplayName();
                   if (args[1] == null) {
                       args[1] = "&nbsp;";
                   }
                   args[2] = new Boolean(context.getAvailable());
  -                args[3] =
  +                args[3] = response.encodeURL
  +                    (request.getContextPath() + "/html/sessions?path=" + displayPath);
  +                args[4] =
                       new Integer(context.getManager().findSessions().length);
                   writer.print
                       (MessageFormat.format(APPS_ROW_DETAILS_SECTION, args));
   
  -                args = new Object[5];
  -                args[0] = displayPath;
  +                args = new Object[8];
  +                args[0] = response.encodeURL
  +                    (request.getContextPath() + "/html/start?path=" + displayPath);
                   args[1] = appsStart;
  -                args[2] = appsStop;
  -                args[3] = appsReload;
  -                args[4] = appsRemove;
  +                args[2] = response.encodeURL
  +                    (request.getContextPath() + "/html/stop?path=" + displayPath);
  +                args[3] = appsStop;
  +                args[4] = response.encodeURL
  +                    (request.getContextPath() + "/html/reload?path=" + displayPath);
  +                args[5] = appsReload;
  +                args[6] = response.encodeURL
  +                    (request.getContextPath() + "/html/remove?path=" + displayPath);
  +                args[7] = appsRemove;
                   if (context.getPath().equals(this.context.getPath())) {
                       writer.print(MessageFormat.format(
                           MANAGER_APP_ROW_BUTTON_SECTION, args));
  @@ -276,14 +421,23 @@
           }
   
           // Install Section
  -        args = new Object[5];
  +        args = new Object[7];
           args[0] = sm.getString("htmlManagerServlet.installTitle");
  -        args[1] = sm.getString("htmlManagerServlet.installPath");
  -        args[2] = sm.getString("htmlManagerServlet.installConfig");
  -        args[3] = sm.getString("htmlManagerServlet.installWar");
  -        args[4] = sm.getString("htmlManagerServlet.installButton");
  +        args[1] = sm.getString("htmlManagerServlet.installServer");
  +        args[2] = response.encodeURL(request.getContextPath() + "/html/intall");
  +        args[3] = sm.getString("htmlManagerServlet.installPath");
  +        args[4] = sm.getString("htmlManagerServlet.installConfig");
  +        args[5] = sm.getString("htmlManagerServlet.installWar");
  +        args[6] = sm.getString("htmlManagerServlet.installButton");
           writer.print(MessageFormat.format(INSTALL_SECTION, args));
   
  +        args = new Object[4];
  +        args[0] = sm.getString("htmlManagerServlet.installUpload");
  +        args[1] = response.encodeURL(request.getContextPath() + "/html/upload");
  +        args[2] = sm.getString("htmlManagerServlet.installUploadFile");
  +        args[3] = sm.getString("htmlManagerServlet.installButton");
  +        writer.print(MessageFormat.format(UPLOAD_SECTION, args));
  +
           // Server Header Section
           args = new Object[7];
           args[0] = sm.getString("htmlManagerServlet.serverTitle");
  @@ -307,6 +461,10 @@
   
           // HTML Tail Section
           writer.print(HTML_TAIL_SECTION);
  +
  +        // Finish up the response
  +        writer.flush();
  +        writer.close();
       }
   
       /**
  @@ -314,17 +472,17 @@
        *
        * @see ManagerServlet#reload(PrintWriter, String)
        *
  -     * @param writer Writer to render to
        * @param path Context path of the application to be restarted
  +     * @return message String
        */
  -    protected void reload(PrintWriter writer, String path) {
  +    protected String reload(String path) {
   
           StringWriter stringWriter = new StringWriter();
           PrintWriter printWriter = new PrintWriter(stringWriter);
   
           super.reload(printWriter, path);
   
  -        list(writer, stringWriter.toString());
  +        return stringWriter.toString();
       }
   
       /**
  @@ -332,17 +490,17 @@
        *
        * @see ManagerServlet#remove(PrintWriter, String)
        *
  -     * @param writer Writer to render to
        * @param path Context path of the application to be removed
  +     * @return message String
        */
  -    protected void remove(PrintWriter writer, String path) {
  +    protected String remove(String path) {
   
           StringWriter stringWriter = new StringWriter();
           PrintWriter printWriter = new PrintWriter(stringWriter);
   
           super.remove(printWriter, path);
   
  -        list(writer, stringWriter.toString());
  +        return stringWriter.toString();
       }
   
       /**
  @@ -350,17 +508,17 @@
        *
        * @see ManagerServlet#sessions(PrintWriter, String)
        *
  -     * @param writer Writer to render to
        * @param path Context path of the application to list session information for
  +     * @return message String
        */
  -    public void sessions(PrintWriter writer, String path) {
  +    public String sessions(String path) {
   
           StringWriter stringWriter = new StringWriter();
           PrintWriter printWriter = new PrintWriter(stringWriter);
   
           super.sessions(printWriter, path);
   
  -        list(writer, stringWriter.toString());
  +        return stringWriter.toString();
       }
   
       /**
  @@ -368,17 +526,17 @@
        *
        * @see ManagerServlet#start(PrintWriter, String)
        *
  -     * @param writer Writer to render to
        * @param path Context path of the application to be started
  +     * @return message String
        */
  -    public void start(PrintWriter writer, String path) {
  +    public String start(String path) {
   
           StringWriter stringWriter = new StringWriter();
           PrintWriter printWriter = new PrintWriter(stringWriter);
   
           super.start(printWriter, path);
   
  -        list(writer, stringWriter.toString());
  +        return stringWriter.toString();
       }
   
       /**
  @@ -386,17 +544,17 @@
        *
        * @see ManagerServlet#stop(PrintWriter, String)
        *
  -     * @param writer Writer to render to
        * @param path Context path of the application to be stopped
  +     * @return message String
        */
  -    protected void stop(PrintWriter writer, String path) {
  +    protected String stop(String path) {
   
           StringWriter stringWriter = new StringWriter();
           PrintWriter printWriter = new PrintWriter(stringWriter);
   
           super.stop(printWriter, path);
   
  -        list(writer, stringWriter.toString());
  +        return stringWriter.toString();
       }
   
       // ------------------------------------------------------ Private Constants
  @@ -406,195 +564,287 @@
       // (maximium of 10).
   
       private static final String HTML_HEADER_SECTION =
  -        "<html> \n" +
  -        "<head> \n" +
  -        "<style> \n" +
  -        "  table { width: 100%; } \n" +
  -        "  td.page-title {  \n" +
  -        "    text-align: center; \n" +
  -        "    vertical-align: top; \n" +
  -        "    font-family:verdana,sans-serif; \n" +
  -        "    font-weight: bold; \n" +
  -        "    background: white; \n" +
  -        "    color: black; \n" +
  -        "  } \n" +
  -        "  td.title { \n" +
  -        "    text-align: left; \n" +
  -        "    vertical-align: top; \n" +
  -        "    font-family:verdana,sans-serif; \n" +
  -        "    font-style:italic; \n" +
  -        "    font-weight: bold; \n" +
  -        "    background: #D2A41C; \n" +
  -        "  } \n" +
  -        "  td.header-left { \n" +
  -        "    text-align: left; \n" +
  -        "    vertical-align: top; \n" +
  -        "    font-family:verdana,sans-serif; \n" +
  -        "    font-weight: bold; \n" +
  -        "    background: #FFDC75; \n" +
  -        "  } \n" +
  -        "  td.header-center { \n" +
  -        "    text-align: center; \n" +
  -        "    vertical-align: top; \n" +
  -        "    font-family:verdana,sans-serif; \n" +
  -        "    font-weight: bold; \n" +
  -        "    background: #FFDC75; \n" +
  -        "  } \n" +
  -        "  td.row-left { \n" +
  -        "    text-align: left; \n" +
  -        "    vertical-align: middle; \n" +
  -        "    font-family:verdana,sans-serif; \n" +
  -        "    color: black; \n" +
  -        "    background: white; \n" +
  -        "  } \n" +
  -        "  td.row-center { \n" +
  -        "    text-align: center; \n" +
  -        "    vertical-align: middle; \n" +
  -        "    font-family:verdana,sans-serif; \n" +
  -        "    color: black; \n" +
  -        "    background: white; \n" +
  -        "  } \n" +
  -        "  td.row-right { \n" +
  -        "    text-align: right; \n" +
  -        "    vertical-align: middle; \n" +
  -        "    font-family:verdana,sans-serif; \n" +
  -        "    color: black; \n" +
  -        "    background: white; \n" +
  -        "  } \n" +
  -        "</style> \n";
  +        "<html>\n" +
  +        "<head>\n" +
  +        "<style>\n" +
  +        "  table { width: 100%; }\n" +
  +        "  td.page-title {\n" +
  +        "    text-align: center;\n" +
  +        "    vertical-align: top;\n" +
  +        "    font-family:verdana,sans-serif;\n" +
  +        "    font-weight: bold;\n" +
  +        "    background: white;\n" +
  +        "    color: black;\n" +
  +        "  }\n" +
  +        "  td.title {\n" +
  +        "    text-align: left;\n" +
  +        "    vertical-align: top;\n" +
  +        "    font-family:verdana,sans-serif;\n" +
  +        "    font-style:italic;\n" +
  +        "    font-weight: bold;\n" +
  +        "    background: #D2A41C;\n" +
  +        "  }\n" +
  +        "  td.header-left {\n" +
  +        "    text-align: left;\n" +
  +        "    vertical-align: top;\n" +
  +        "    font-family:verdana,sans-serif;\n" +
  +        "    font-weight: bold;\n" +
  +        "    background: #FFDC75;\n" +
  +        "  }\n" +
  +        "  td.header-center {\n" +
  +        "    text-align: center;\n" +
  +        "    vertical-align: top;\n" +
  +        "    font-family:verdana,sans-serif;\n" +
  +        "    font-weight: bold;\n" +
  +        "    background: #FFDC75;\n" +
  +        "  }\n" +
  +        "  td.row-left {\n" +
  +        "    text-align: left;\n" +
  +        "    vertical-align: middle;\n" +
  +        "    font-family:verdana,sans-serif;\n" +
  +        "    color: black;\n" +
  +        "    background: white;\n" +
  +        "  }\n" +
  +        "  td.row-center {\n" +
  +        "    text-align: center;\n" +
  +        "    vertical-align: middle;\n" +
  +        "    font-family:verdana,sans-serif;\n" +
  +        "    color: black;\n" +
  +        "    background: white;\n" +
  +        "  }\n" +
  +        "  td.row-right {\n" +
  +        "    text-align: right;\n" +
  +        "    vertical-align: middle;\n" +
  +        "    font-family:verdana,sans-serif;\n" +
  +        "    color: black;\n" +
  +        "    background: white;\n" +
  +        "  }\n" +
  +        "</style>\n";
   
       private static final String BODY_HEADER_SECTION =
  -        "<title>{0}</title> \n" +
  -        "</head> \n" +
  +        "<title>{0}</title>\n" +
  +        "</head>\n" +
           "\n" +
  -        "<body bgcolor=\"#FFFFFF\"> \n" +
  +        "<body bgcolor=\"#FFFFFF\">\n" +
           "\n" +
  -        "<table border=\"2\" cellspacing=\"0\" cellpadding=\"3\" " +
  -        "bordercolor=\"#000000\"> \n" +
  -        "<tr> \n" +
  -        " <td class=\"page-title\" bordercolor=\"#000000\" align=\"left\" " +
  -        "nowrap> \n" +
  -        "  <font size=\"+2\">{0}</font> \n" +
  -        " </td> \n" +
  -        "</tr> \n" +
  -        "</table> \n" +
  -        "<br> \n" +
  +        "<table cellspacing=\"4\" width=\"100%\" border=\"0\">\n" +
  +        " <tr>\n" +
  +        "  <td colspan=\"2\">\n" +
  +        "   <a href=\"http://jakarta.apache.org/\">\n" +
  +        "    <img border=\"0\" alt=\"The Jakarta Project\" align=\"left\"\n" +
  +        "         src=\"{0}/images/jakarta-logo.gif\">\n" +
  +        "   </a>\n" +
  +        "   <a href=\"http://jakarta.apache.org/tomcat/\">\n" +
  +        "    <img border=\"0\" alt=\"The Tomcat Servlet/JSP Container\"\n" +
  +        "         align=\"right\" src=\"{0}/images/tomcat.gif\">\n" +
  +        "   </a>\n" +
  +        "  </td>\n" +
  +        " </tr>\n" +
  +        "</table>\n" +
  +        "<hr size=\"1\" noshade\"\">\n" +
  +        "<table cellspacing=\"4\" width=\"100%\" border=\"0\">\n" +
  +        " <tr>\n" +
  +        "  <td class=\"page-title\" bordercolor=\"#000000\" align=\"left\" nowrap>\n" +
  +        "   <font size=\"+2\">{1}</font>\n" +
  +        "  </td>\n" +
  +        " </tr>\n" +
  +        "</table>\n" +
  +        "<br>\n" +
           "\n";
   
       private static final String MESSAGE_SECTION =
  -        "<table border=\"1\" cellspacing=\"0\" cellpadding=\"3\"> \n" +
  -        " <tr> \n" +
  -        "  <td class=\"row-left\"><small><b>{0}</b>&nbsp;{1}</small></td>\n" +
  -        " </tr> \n" +
  -        "</table> \n" +
  -        "<br> \n" +
  +        "<table border=\"1\" cellspacing=\"0\" cellpadding=\"3\">\n" +
  +        " <tr>\n" +
  +        "  <td class=\"row-left\" width=\"10%\"><small><b>{0}</b></small>&nbsp;</td>\n" +
  +        "  <td class=\"row-left\"><pre>{1}</pre></td>\n" +
  +        " </tr>\n" +
  +        "</table>\n" +
  +        "<br>\n" +
  +        "\n";
  +
  +    private static final String MANAGER_SECTION =
  +        "<table border=\"1\" cellspacing=\"0\" cellpadding=\"3\">\n" +
  +        "<tr>\n" +
  +        " <td colspan=\"3\" class=\"title\">{0}</td>\n" +
  +        "</tr>\n" +
  +        " <tr>\n" +
  +        "  <td class=\"row-left\"><a href=\"{1}\">{2}</a></td>\n" +
  +        "  <td class=\"row-center\"><a href=\"{3}\">{4}</a></td>\n" +
  +        "  <td class=\"row-right\"><a href=\"{5}\">{6}</a></td>\n" +
  +        " </tr>\n" +
  +        "</table>\n" +
  +        "<br>\n" +
           "\n";
   
       private static final String APPS_HEADER_SECTION =
  -        "<table border=\"1\" cellspacing=\"0\" cellpadding=\"3\"> \n" +
  -        "<tr> \n" +
  -        " <td colspan=\"10\" class=\"title\">{0}</td> \n" +
  -        "</tr> \n" +
  -        "<tr> \n" +
  -        " <td class=\"header-left\"><small>{1}</small></td> \n" +
  -        " <td class=\"header-left\"><small>{2}</small></td> \n" +
  -        " <td class=\"header-center\"><small>{3}</small></td> \n" +
  -        " <td class=\"header-center\"><small>{4}</small></td> \n" +
  -        " <td class=\"header-center\">&nbsp;</td> \n" +
  -        "</tr> \n";
  +        "<table border=\"1\" cellspacing=\"0\" cellpadding=\"3\">\n" +
  +        "<tr>\n" +
  +        " <td colspan=\"5\" class=\"title\">{0}</td>\n" +
  +        "</tr>\n" +
  +        "<tr>\n" +
  +        " <td class=\"header-left\"><small>{1}</small></td>\n" +
  +        " <td class=\"header-left\"><small>{2}</small></td>\n" +
  +        " <td class=\"header-center\"><small>{3}</small></td>\n" +
  +        " <td class=\"header-center\"><small>{4}</small></td>\n" +
  +        " <td class=\"header-center\"><small>{5}</small></td>\n" +
  +        "</tr>\n";
   
       private static final String APPS_ROW_DETAILS_SECTION =
  -        "<tr> \n" +
  +        "<tr>\n" +
           " <td class=\"row-left\"><small><a href=\"{0}\">{0}</a>" +
  -        "</small></td> \n" +
  -        " <td class=\"row-left\"><small>{1}</small></td> \n" +
  -        " <td class=\"row-center\"><small>{2}</small></td> \n" +
  +        "</small></td>\n" +
  +        " <td class=\"row-left\"><small>{1}</small></td>\n" +
  +        " <td class=\"row-center\"><small>{2}</small></td>\n" +
           " <td class=\"row-center\">" +
  -        "<small><a href=\"sessions?path={0}\">{3}</a></small></td> \n";
  +        "<small><a href=\"{3}\">{4}</a></small></td>\n";
   
       private static final String MANAGER_APP_ROW_BUTTON_SECTION =
  -        " <td class=\"row-left\"> \n" +
  -        "  <small> \n" +
  -        "  &nbsp;{1}&nbsp; \n" +
  -        "  &nbsp;{2}&nbsp; \n" +
  -        "  &nbsp;{3}&nbsp; \n" +
  -        "  &nbsp;{4}&nbsp; \n" +
  -        "  </small> \n" +
  -        " </td> \n" +
  -        "</tr> \n";
  +        " <td class=\"row-left\">\n" +
  +        "  <small>\n" +
  +        "  &nbsp;{1}&nbsp;\n" +
  +        "  &nbsp;{3}&nbsp;\n" +
  +        "  &nbsp;{5}&nbsp;\n" +
  +        "  &nbsp;{7}&nbsp;\n" +
  +        "  </small>\n" +
  +        " </td>\n" +
  +        "</tr>\n";
   
       private static final String STARTED_APPS_ROW_BUTTON_SECTION =
  -        " <td class=\"row-left\"> \n" +
  -        "  <small> \n" +
  -        "  &nbsp;{1}&nbsp; \n" +
  -        "  &nbsp;<a href=\"stop?path={0}\">{2}</a>&nbsp; \n" +
  -        "  &nbsp;<a href=\"reload?path={0}\">{3}</a>&nbsp; \n" +
  -        "  &nbsp;<a href=\"remove?path={0}\">{4}</a>&nbsp; \n" +
  -        "  </small> \n" +
  -        " </td> \n" +
  -        "</tr> \n";
  +        " <td class=\"row-left\">\n" +
  +        "  <small>\n" +
  +        "  &nbsp;{1}&nbsp;\n" +
  +        "  &nbsp;<a href=\"{2}\">{3}</a>&nbsp;\n" +
  +        "  &nbsp;<a href=\"{4}\">{5}</a>&nbsp;\n" +
  +        "  &nbsp;<a href=\"{6}\">{7}</a>&nbsp;\n" +
  +        "  </small>\n" +
  +        " </td>\n" +
  +        "</tr>\n";
   
       private static final String STOPPED_APPS_ROW_BUTTON_SECTION =
  -        " <td class=\"row-left\"> \n" +
  -        "  <small> \n" +
  -        "  &nbsp;<a href=\"start?path={0}\">{1}</a>&nbsp; \n" +
  -        "  &nbsp;{2}&nbsp; \n" +
  -        "  &nbsp;{3}&nbsp; \n" +
  -        "  &nbsp;<a href=\"remove?path={0}\">{4}</a>&nbsp; \n" +
  -        "  </small> \n" +
  -        " </td> \n" +
  -        "</tr> \n";
  +        " <td class=\"row-left\">\n" +
  +        "  <small>\n" +
  +        "  &nbsp;<a href=\"{0}\">{1}</a>&nbsp;\n" +
  +        "  &nbsp;{3}&nbsp;\n" +
  +        "  &nbsp;{5}&nbsp;\n" +
  +        "  &nbsp;<a href=\"{6}\">{7}</a>&nbsp;\n" +
  +        "  </small>\n" +
  +        " </td>\n" +
  +        "</tr>\n";
   
       private static final String INSTALL_SECTION =
  -        "<tr> \n" +
  -        " <td colspan=\"10\" class=\"header-left\"><small>{0}</small></td>\n" +
  -        "</tr> \n" +
  -        "<tr> \n" +
  -        "<form method=\"get\" action=\"install\"> \n" +
  -        "<input type=\"hidden\" name=\"path\"> \n" +
  -        " <td colspan=\"10\" class=\"row-left\"> \n" +
  -        "  <small>{1}</small> \n" +
  -        "  <input type=\"text\" name=\"installPath\" size=\"10\"> \n" +
  -        "  &nbsp;<small>{2}</small> \n" +
  -        "  <input type=\"text\" name=\"installConfig\" size=\"18\"> \n" +
  -        "  &nbsp;<small>{3}</small> \n" +
  -        "  <input type=\"text\" name=\"installWar\" size=\"18\">&nbsp; \n" +
  -        "  <input type=\"submit\" value=\"{4}\"> \n" +
  -        " </td> \n" +
  -        "</form> \n" +
  -        "</tr> \n" +
  -        "</table> \n" +
  -        "<br> \n" +
  +        "</table>\n" +
  +        "<br>\n" +
  +        "<table border=\"1\" cellspacing=\"0\" cellpadding=\"3\">\n" +
  +        "<tr>\n" +
  +        " <td colspan=\"2\" class=\"title\">{0}</td>\n" +
  +        "</tr>\n" +
  +        "<tr>\n" +
  +        " <td colspan=\"2\" class=\"header-left\"><small>{1}</small></td>\n" +
  +        "</tr>\n" +
  +        "<tr>\n" +
  +        " <td colspan=\"2\">\n" +
  +        "<form method=\"get\" action=\"{2}\">\n" +
  +        "<table cellspacing=\"0\" cellpadding=\"3\">\n" +
  +        "<tr>\n" +
  +        " <td class=\"row-right\">\n" +
  +        "  <small>{3}</small>\n" +
  +        " </td>\n" +
  +        " <td class=\"row-left\">\n" +
  +        "  <input type=\"text\" name=\"installPath\" size=\"20\">\n" +
  +        " </td>\n" +
  +        "</tr>\n" +
  +        "<tr>\n" +
  +        " <td class=\"row-right\">\n" +
  +        "  <small>{4}</small>\n" +
  +        " </td>\n" +
  +        " <td class=\"row-left\">\n" +
  +        "  <input type=\"text\" name=\"installConfig\" size=\"20\">\n" +
  +        " </td>\n" +
  +        "</tr>\n" +
  +        "<tr>\n" +
  +        " <td class=\"row-right\">\n" +
  +        "  <small>{5}</small>\n" +
  +        " </td>\n" +
  +        " <td class=\"row-left\">\n" +
  +        "  <input type=\"text\" name=\"installWar\" size=\"40\">\n" +
  +        " </td>\n" +
  +        "</tr>\n" +
  +        "<tr>\n" +
  +        " <td class=\"row-right\">\n" +
  +        "  &nbsp;\n" +
  +        " </td>\n" +
  +        " <td class=\"row-left\">\n" +
  +        "  <input type=\"submit\" value=\"{6}\">\n" +
  +        " </td>\n" +
  +        "</tr>\n" +
  +        "</table>\n" +
  +        "</form>\n" +
  +        "</td>\n" +
  +        "</tr>\n";
  +
  +    private static final String UPLOAD_SECTION =
  +        "<tr>\n" +
  +        " <td colspan=\"2\" class=\"header-left\"><small>{0}</small></td>\n" +
  +        "</tr>\n" +
  +        "<tr>\n" +
  +        " <td colspan=\"2\">\n" +
  +        "<form action=\"{1}\" method=\"post\" enctype=\"multipart/form-data\">\n" +
  +        "<table cellspacing=\"0\" cellpadding=\"3\">\n" +
  +        "<tr>\n" +
  +        " <td class=\"row-right\">\n" +
  +        "  <small>{2}</small>\n" +
  +        " </td>\n" +
  +        " <td class=\"row-left\">\n" +
  +        "  <input type=\"file\" name=\"installWar\" size=\"40\">\n" +
  +        " </td>\n" +
  +        "</tr>\n" +
  +        "<tr>\n" +
  +        " <td class=\"row-right\">\n" +
  +        "  &nbsp;\n" +
  +        " </td>\n" +
  +        " <td class=\"row-left\">\n" +
  +        "  <input type=\"submit\" value=\"{3}\">\n" +
  +        " </td>\n" +
  +        "</tr>\n" +
  +        "</table>\n" +
  +        "</form>\n" +
  +        "</table>\n" +
  +        "<br>\n" +
           "\n";
   
       private static final String SERVER_HEADER_SECTION =
  -        "<table border=\"1\" cellspacing=\"0\" cellpadding=\"3\"> \n" +
  -        "<tr> \n" +
  -        " <td colspan=\"10\" class=\"title\">{0}</td>  \n" +
  -        "</tr> \n" +
  -        "<tr> \n" +
  -        " <td class=\"header-center\"><small>{1}</small></td> \n" +
  -        " <td class=\"header-center\"><small>{2}</small></td> \n" +
  -        " <td class=\"header-center\"><small>{3}</small></td> \n" +
  -        " <td class=\"header-center\"><small>{4}</small></td> \n" +
  -        " <td class=\"header-center\"><small>{5}</small></td> \n" +
  -        " <td class=\"header-center\"><small>{6}</small></td> \n" +
  -        "</tr> \n";
  +        "<table border=\"1\" cellspacing=\"0\" cellpadding=\"3\">\n" +
  +        "<tr>\n" +
  +        " <td colspan=\"6\" class=\"title\">{0}</td>\n" +
  +        "</tr>\n" +
  +        "<tr>\n" +
  +        " <td class=\"header-center\"><small>{1}</small></td>\n" +
  +        " <td class=\"header-center\"><small>{2}</small></td>\n" +
  +        " <td class=\"header-center\"><small>{3}</small></td>\n" +
  +        " <td class=\"header-center\"><small>{4}</small></td>\n" +
  +        " <td class=\"header-center\"><small>{5}</small></td>\n" +
  +        " <td class=\"header-center\"><small>{6}</small></td>\n" +
  +        "</tr>\n";
   
       private static final String SERVER_ROW_SECTION =
  -        "<tr> \n" +
  -        " <td class=\"row-center\"><small>{0}</small></td> \n" +
  -        " <td class=\"row-center\"><small>{1}</small></td> \n" +
  -        " <td class=\"row-center\"><small>{2}</small></td> \n" +
  -        " <td class=\"row-center\"><small>{3}</small></td> \n" +
  -        " <td class=\"row-center\"><small>{4}</small></td> \n" +
  -        " <td class=\"row-center\"><small>{5}</small></td> \n" +
  -        "</tr> \n" +
  -        "</table> \n" +
  -        "<br> \n" +
  +        "<tr>\n" +
  +        " <td class=\"row-center\"><small>{0}</small></td>\n" +
  +        " <td class=\"row-center\"><small>{1}</small></td>\n" +
  +        " <td class=\"row-center\"><small>{2}</small></td>\n" +
  +        " <td class=\"row-center\"><small>{3}</small></td>\n" +
  +        " <td class=\"row-center\"><small>{4}</small></td>\n" +
  +        " <td class=\"row-center\"><small>{5}</small></td>\n" +
  +        "</tr>\n" +
  +        "</table>\n" +
  +        "<br>\n" +
           "\n";
   
       private static final String HTML_TAIL_SECTION =
  -        "</body> \n" +
  +        "<hr size=\"1\" noshade\"\">\n" +
  +        "<center><font size=\"-1\" color=\"#525D76\">\n" +
  +        " <em>Copyright &copy; 1999-2002, Apache Software Foundation</em>" +
  +        "</font></center>\n" +
  +        "\n" +
  +        "</body>\n" +
           "</html>";
   }
  
  
  
  1.20      +20 -7     jakarta-tomcat-4.0/catalina/src/share/org/apache/catalina/servlets/LocalStrings.properties
  
  Index: LocalStrings.properties
  ===================================================================
  RCS file: /home/cvs/jakarta-tomcat-4.0/catalina/src/share/org/apache/catalina/servlets/LocalStrings.properties,v
  retrieving revision 1.19
  retrieving revision 1.20
  diff -u -r1.19 -r1.20
  --- LocalStrings.properties	29 Aug 2002 14:01:19 -0000	1.19
  +++ LocalStrings.properties	10 Jan 2003 15:52:18 -0000	1.20
  @@ -10,20 +10,34 @@
   htmlManagerServlet.appsSessions=Sessions
   htmlManagerServlet.appsStart=Start
   htmlManagerServlet.appsStop=Stop
  +htmlManagerServlet.appsTasks=Commands
   htmlManagerServlet.appsTitle=Applications
  +htmlManagerServlet.helpHtmlManager=HTML Manager Help
  +htmlManagerServlet.helpHtmlManagerFile=html-manager-howto.html
  +htmlManagerServlet.helpManager=Manager Help
  +htmlManagerServlet.helpManagerFile=manager-howto.html
   htmlManagerServlet.installButton=Install
  -htmlManagerServlet.installConfig=Config URL:
  -htmlManagerServlet.installPath=Path:
  +htmlManagerServlet.installConfig=XML Configuration file URL:
  +htmlManagerServlet.installPath=Context Path (optional):
  +htmlManagerServlet.installServer=Install directory or WAR file located on server
   htmlManagerServlet.installTitle=Install
  -htmlManagerServlet.installWar=WAR URL:
  +htmlManagerServlet.installUpload=Upload a WAR file to install
  +htmlManagerServlet.installUploadFail=FAIL - Install Upload Failed, Exception: {0}
  +htmlManagerServlet.installUploadFile=Select WAR file to upload
  +htmlManagerServlet.installUploadNotWar=FAIL - File uploaded \"{0}\" must be a .war
  +htmlManagerServlet.installUploadNoFile=FAIL - File upload failed, no file
  +htmlManagerServlet.installUploadWarExists=FAIL - War file \"{0}\" already exists on server
  +htmlManagerServlet.installWar=WAR or Directory URL:
  +htmlManagerServlet.list=List Applications
  +htmlManagerServlet.manager=Manager
   htmlManagerServlet.messageLabel=Message:
   htmlManagerServlet.serverJVMVendor=JVM Vendor
   htmlManagerServlet.serverJVMVersion=JVM Version
  -htmlManagerServlet.serverOSArch=OS Arch
  +htmlManagerServlet.serverOSArch=OS Architecture
   htmlManagerServlet.serverOSName=OS Name
   htmlManagerServlet.serverOSVersion=OS Version
  -htmlManagerServlet.serverTitle=Server
  -htmlManagerServlet.serverVersion=Server Version
  +htmlManagerServlet.serverTitle=Server Information
  +htmlManagerServlet.serverVersion=Tomcat Version
   htmlManagerServlet.title=Tomcat Web Application Manager
   invokerServlet.allocate=Cannot allocate servlet instance for path {0}
   invokerServlet.cannotCreate=Cannot create servlet wrapper for path {0}
  @@ -51,7 +65,6 @@
   managerServlet.noDirectory=FAIL - Non-directory document base for path {0}
   managerServlet.noDocBase=FAIL - Cannot remove document base for path {0}
   managerServlet.noGlobal=FAIL - No global JNDI resources are available
  -managerServlet.noPath=FAIL - No context path was specified
   managerServlet.noReload=FAIL - Reload not supported on WAR deployed at path
   {0}
   managerServlet.noRename=FAIL - Cannot deploy uploaded WAR for path {0}
  
  
  
  1.3       +0 -1      jakarta-tomcat-4.0/catalina/src/share/org/apache/catalina/servlets/LocalStrings_fr.properties
  
  Index: LocalStrings_fr.properties
  ===================================================================
  RCS file: /home/cvs/jakarta-tomcat-4.0/catalina/src/share/org/apache/catalina/servlets/LocalStrings_fr.properties,v
  retrieving revision 1.2
  retrieving revision 1.3
  diff -u -r1.2 -r1.3
  --- LocalStrings_fr.properties	11 Dec 2002 16:22:59 -0000	1.2
  +++ LocalStrings_fr.properties	10 Jan 2003 15:52:18 -0000	1.3
  @@ -51,7 +51,6 @@
   managerServlet.noDirectory=ECHEC - La base de document n''est pas un répertoire pour le chemin {0}
   managerServlet.noDocBase=ECHEC - Impossible de retirer la base de document pour le chemin {0}
   managerServlet.noGlobal=ECHEC - Aucune ressource JNDI globale n''est disponible
  -managerServlet.noPath=ECHEC - Aucun chemin de contexte n''a été spécifié
   managerServlet.noReload=ECHEC - Rechargement non supporté par le WAR déployé au chemin
   {0}
   managerServlet.noRename=ECHEC - Impossible de déployer un WAR téléchargé pour le chemin {0}
  
  
  
  1.5       +0 -1      jakarta-tomcat-4.0/catalina/src/share/org/apache/catalina/servlets/LocalStrings_ja.properties
  
  Index: LocalStrings_ja.properties
  ===================================================================
  RCS file: /home/cvs/jakarta-tomcat-4.0/catalina/src/share/org/apache/catalina/servlets/LocalStrings_ja.properties,v
  retrieving revision 1.4
  retrieving revision 1.5
  diff -u -r1.4 -r1.5
  --- LocalStrings_ja.properties	27 Feb 2002 22:43:56 -0000	1.4
  +++ LocalStrings_ja.properties	10 Jan 2003 15:52:18 -0000	1.5
  @@ -18,7 +18,6 @@
   managerServlet.listitem={0}:{1}:{2}:{3}
   managerServlet.noCommand=\u5931\u6557 - \u30b3\u30de\u30f3\u30c9\u304c\u6307\u5b9a\u3055\u308c\u3066\u3044\u307e\u305b\u3093
   managerServlet.noContext=\u5931\u6557 - \u30d1\u30b9 {0} \u306e\u30b3\u30f3\u30c6\u30ad\u30b9\u30c8\u304c\u5b58\u5728\u3057\u307e\u305b\u3093
  -managerServlet.noPath=\u5931\u6557 - \u30b3\u30f3\u30c6\u30ad\u30b9\u30c8\u30d1\u30b9\u304c\u6307\u5b9a\u3055\u308c\u3066\u3044\u307e\u305b\u3093
   managerServlet.noRole=\u5931\u6557 - \u30e6\u30fc\u30b6\u306f\u30ed\u30fc\u30eb {0} \u3092\u6301\u3063\u3066\u3044\u307e\u305b\u3093
   managerServlet.noWrapper=\u30b3\u30f3\u30c6\u30ca\u306f\uff0c\u3053\u306e\u30b5\u30fc\u30d6\u30ec\u30c3\u30c8\u306b\u5bfe\u3057\u3066\u547c\u3073\u51fa\u3055\u308c\u305fsetWrapper()\u3092\u6301\u3063\u3066\u3044\u307e\u305b\u3093
   managerServlet.reloaded=OK - \u30b3\u30f3\u30c6\u30ad\u30b9\u30c8\u30d1\u30b9 {0} \u306e\u30a2\u30d7\u30ea\u30b1\u30fc\u30b7\u30e7\u30f3\u3092\u30ea\u30ed\u30fc\u30c9\u3057\u307e\u3059
  
  
  
  1.30      +102 -15   jakarta-tomcat-4.0/catalina/src/share/org/apache/catalina/servlets/ManagerServlet.java
  
  Index: ManagerServlet.java
  ===================================================================
  RCS file: /home/cvs/jakarta-tomcat-4.0/catalina/src/share/org/apache/catalina/servlets/ManagerServlet.java,v
  retrieving revision 1.29
  retrieving revision 1.30
  diff -u -r1.29 -r1.30
  --- ManagerServlet.java	4 Jan 2003 13:43:49 -0000	1.29
  +++ ManagerServlet.java	10 Jan 2003 15:52:18 -0000	1.30
  @@ -72,6 +72,7 @@
   import java.io.IOException;
   import java.io.PrintWriter;
   import java.net.URL;
  +import java.net.MalformedURLException;
   import java.util.Enumeration;
   import java.util.Iterator;
   import java.util.Locale;
  @@ -101,6 +102,7 @@
   import org.apache.catalina.UserDatabase;
   import org.apache.catalina.Wrapper;
   import org.apache.catalina.core.StandardServer;
  +import org.apache.catalina.util.ServerInfo;
   import org.apache.catalina.util.StringManager;
   import org.apache.naming.resources.ProxyDirContext;
   import org.apache.naming.resources.WARDirContext;
  @@ -148,6 +150,7 @@
    * <li><b>/roles</b> - Enumerate the available security role names and
    *     descriptions from the user database connected to the <code>users</code>
    *     resource reference.
  + * <li><b>/serverinfo</b> - Display system OS and JVM properties.
    * <li><b>/sessions?path=/xxx</b> - List session information about the web
    *     application attached to context path <code>/xxx</code> for this
    *     virtual host.</li>
  @@ -330,9 +333,10 @@
           String war = request.getParameter("war");
   
           // Prepare our output writer to generate the response message
  -        response.setContentType("text/plain");
           Locale locale = Locale.getDefault();
  +        String charset = context.getCharsetMapper().getCharset(locale);
           response.setLocale(locale);
  +        response.setContentType("text/plain; charset=" + charset);
           PrintWriter writer = response.getWriter();
   
           // Process the requested command (note - "/deploy" is not listed here)
  @@ -350,6 +354,8 @@
               resources(writer, type);
           } else if (command.equals("/roles")) {
               roles(writer);
  +        } else if (command.equals("/serverinfo")) {
  +            serverinfo(writer);
           } else if (command.equals("/sessions")) {
               sessions(writer, path);
           } else if (command.equals("/start")) {
  @@ -497,7 +503,7 @@
           }
   
           // Validate the requested context path
  -        if ((path == null) || (!path.startsWith("/") && path.equals(""))) {
  +        if ((path == null) || path.length() == 0 || !path.startsWith("/")) {
               writer.println(sm.getString("managerServlet.invalidPath", path));
               return;
           }
  @@ -586,7 +592,7 @@
                              String path, String war) {
   
           if (debug >= 1) {
  -            if (config != null) {
  +            if (config != null && config.length() > 0) {
                   if (war != null) {
                       log("install: Installing context configuration at '" +
                           config + "' from '" + war + "'");
  @@ -600,7 +606,32 @@
               }
           }
   
  -        if (config != null) {
  +        // See if directory/war is relative to host appBase
  +        if (war != null && war.indexOf('/') < 0 ) {
  +            // Identify the appBase of the owning Host of this Context (if any)
  +            String appBase = null;
  +            File appBaseDir = null;
  +            if (context.getParent() instanceof Host) {
  +                appBase = ((Host) context.getParent()).getAppBase();
  +                appBaseDir = new File(appBase);
  +                if (!appBaseDir.isAbsolute()) {
  +                    appBaseDir = new File(System.getProperty("catalina.base"),
  +                                          appBase);
  +                }
  +                File file = new File(appBaseDir,war);
  +                try {
  +                    URL url = file.toURL();
  +                    war = url.toString();
  +                    if (war.toLowerCase().endsWith(".war")) {
  +                        war = "jar:" + war + "!/";
  +                    }
  +                } catch(MalformedURLException e) {
  +                    ;
  +                }
  +            }
  +        }
  +
  +        if (config != null && config.length() > 0) {
   
               if ((war != null) &&
                   (!war.startsWith("file:") && !war.startsWith("jar:"))) {
  @@ -624,7 +655,39 @@
   
           } else {
   
  -            if ((path == null) || (!path.startsWith("/") && path.equals(""))) {
  +            if ((war == null) ||
  +                (!war.startsWith("file:") && !war.startsWith("jar:"))) {
  +                writer.println(sm.getString("managerServlet.invalidWar", war));
  +                return;
  +            }
  +
  +            if (path == null || path.length() == 0) {
  +                int end = war.length();
  +                String filename = war.toLowerCase();
  +                if (filename.endsWith("!/")) {
  +                    filename = filename.substring(0,filename.length()-2);
  +                    end -= 2;
  +                }
  +                if (filename.endsWith(".war")) {
  +                    filename = filename.substring(0,filename.length()-2);
  +                    end -= 4;
  +                }
  +                if (filename.endsWith("/")) {
  +                    filename = filename.substring(0,filename.length()-1);
  +                    end--;
  +                }
  +                int beg = filename.lastIndexOf('/') + 1;
  +                if (beg < 0 || end < 0 || beg >= end) {
  +                    writer.println(sm.getString("managerServlet.invalidWar", war));
  +                    return;
  +                }
  +                path = "/" + war.substring(beg,end);
  +                if (path.equals("/ROOT")) {
  +                    path = "/";
  +                }
  +            }
  +
  +            if (path == null || path.length() == 0 || !path.startsWith("/")) {
                   writer.println(sm.getString("managerServlet.invalidPath",
                                               path));
                   return;
  @@ -633,11 +696,6 @@
               if("/".equals(path)) {
                   path = "";
               }
  -            if ((war == null) ||
  -                (!war.startsWith("file:") && !war.startsWith("jar:"))) {
  -                writer.println(sm.getString("managerServlet.invalidWar", war));
  -                return;
  -            }
   
               try {
                   Context context =  deployer.findDeployedApp(path);
  @@ -778,7 +836,7 @@
                   writer.println(sm.getString("managerServlet.noSelf"));
                   return;
               }
  -            deployer.remove(path);
  +            deployer.remove(path,true);
               writer.println(sm.getString("managerServlet.removed", displayPath));
           } catch (Throwable t) {
               log("ManagerServlet.remove[" + displayPath + "]", t);
  @@ -920,6 +978,35 @@
   
       }
   
  +
  +    /**
  +     * Writes System OS and JVM properties.
  +     * @param writer Writer to render to
  +     */
  +    protected void serverinfo(PrintWriter writer) {
  +        if (debug >= 1)
  +            log("serverinfo");
  +        try {
  +            StringBuffer props = new StringBuffer();
  +            props.append("Tomcat Version: ");
  +            props.append(ServerInfo.getServerInfo());
  +            props.append("\nOS Name: ");
  +            props.append(System.getProperty("os.name"));
  +            props.append("\nOS Version: ");
  +            props.append(System.getProperty("os.version"));
  +            props.append("\nOS Architecture: ");
  +            props.append(System.getProperty("os.arch"));
  +            props.append("\nJVM Version: ");
  +            props.append(System.getProperty("java.runtime.version"));
  +            props.append("\nJVM Vendor: ");
  +            props.append(System.getProperty("java.vm.vendor"));
  +            writer.println(props.toString());
  +        } catch (Throwable t) {
  +            getServletContext().log("ManagerServlet.serverinfo",t);
  +            writer.println(sm.getString("managerServlet.exception",
  +                                        t.toString()));
  +        }
  +    }
   
       /**
        * Session information for the web application at the specified context path.
  
  
  
  1.24      +7 -168    jakarta-tomcat-4.0/catalina/src/share/org/apache/catalina/startup/HostConfig.java
  
  Index: HostConfig.java
  ===================================================================
  RCS file: /home/cvs/jakarta-tomcat-4.0/catalina/src/share/org/apache/catalina/startup/HostConfig.java,v
  retrieving revision 1.23
  retrieving revision 1.24
  diff -u -r1.23 -r1.24
  --- HostConfig.java	30 May 2002 22:12:28 -0000	1.23
  +++ HostConfig.java	10 Jan 2003 15:52:18 -0000	1.24
  @@ -65,22 +65,12 @@
   package org.apache.catalina.startup;
   
   
  -import java.io.BufferedOutputStream;
   import java.io.File;
  -import java.io.FileInputStream;
  -import java.io.FileNotFoundException;
  -import java.io.FileOutputStream;
   import java.io.InputStream;
   import java.io.IOException;
  -import java.lang.reflect.InvocationTargetException;
  -import java.net.JarURLConnection;
  -import java.net.MalformedURLException;
   import java.net.URL;
   import java.util.ArrayList;
  -import java.util.Enumeration;
   import java.util.HashMap;
  -import java.util.jar.JarEntry;
  -import java.util.jar.JarFile;
   import javax.naming.NamingException;
   import javax.naming.directory.DirContext;
   import org.apache.naming.resources.ResourceAttributes;
  @@ -497,7 +487,7 @@
                       try {
                           URL url = new URL("jar:file:" +
                                             dir.getCanonicalPath() + "!/");
  -                        String path = expand(url);
  +                        String path = ExpandWar.expand(host,url);
                           url = new URL("file:" + path);
                           ((Deployer) host).install(contextPath, url);
                       } catch (Throwable t) {
  @@ -650,148 +640,7 @@
        */
       protected String expand(URL war) throws IOException {
   
  -        // Calculate the directory name of the expanded directory
  -        if (getDebug() >= 1) {
  -            log("expand(" + war.toString() + ")");
  -        }
  -        String pathname = war.toString().replace('\\', '/');
  -        if (pathname.endsWith("!/")) {
  -            pathname = pathname.substring(0, pathname.length() - 2);
  -        }
  -        int period = pathname.lastIndexOf('.');
  -        if (period >= pathname.length() - 4)
  -            pathname = pathname.substring(0, period);
  -        int slash = pathname.lastIndexOf('/');
  -        if (slash >= 0) {
  -            pathname = pathname.substring(slash + 1);
  -        }
  -        if (getDebug() >= 1) {
  -            log("  Proposed directory name: " + pathname);
  -        }
  -
  -        // Make sure that there is no such directory already existing
  -        File appBase = new File(host.getAppBase());
  -        if (!appBase.isAbsolute()) {
  -            appBase = new File(System.getProperty("catalina.base"),
  -                               host.getAppBase());
  -        }
  -        if (!appBase.exists() || !appBase.isDirectory()) {
  -            throw new IOException
  -                (sm.getString("standardHost.appBase",
  -                              appBase.getAbsolutePath()));
  -        }
  -        File docBase = new File(appBase, pathname);
  -        if (docBase.exists()) {
  -            // War file is already installed
  -            return (docBase.getAbsolutePath());
  -        }
  -
  -        // Create the new document base directory
  -        docBase.mkdir();
  -        if (getDebug() >= 2) {
  -            log("  Have created expansion directory " +
  -                docBase.getAbsolutePath());
  -        }
  -
  -        // Expand the WAR into the new document base directory
  -        JarURLConnection juc = (JarURLConnection) war.openConnection();
  -        juc.setUseCaches(false);
  -        /*
  -        JarFile jarFile = juc.getJarFile();
  -        if (getDebug() >= 2) {
  -            log("  Have opened JAR file successfully");
  -        }
  -        Enumeration jarEntries = jarFile.entries();
  -        if (getDebug() >= 2) {
  -            log("  Have retrieved entries enumeration");
  -        }
  -        while (jarEntries.hasMoreElements()) {
  -            JarEntry jarEntry = (JarEntry) jarEntries.nextElement();
  -            String name = jarEntry.getName();
  -            if (getDebug() >= 2) {
  -                log("  Am processing entry " + name);
  -            }
  -            int last = name.lastIndexOf('/');
  -            if (last >= 0) {
  -                File parent = new File(docBase,
  -                                       name.substring(0, last));
  -                if (getDebug() >= 2) {
  -                    log("  Creating parent directory " + parent);
  -                }
  -                parent.mkdirs();
  -            }
  -            if (name.endsWith("/")) {
  -                continue;
  -            }
  -            if (getDebug() >= 2) {
  -                log("  Creating expanded file " + name);
  -            }
  -            InputStream input = jarFile.getInputStream(jarEntry);
  -            expand(input, docBase, name);
  -            input.close();
  -        }
  -        jarFile.close();
  -        */
  -        JarFile jarFile = null;
  -        InputStream input = null;
  -        try {
  -            jarFile = juc.getJarFile();
  -            if (getDebug() >= 2) {
  -                log("  Have opened JAR file successfully");
  -            }
  -            Enumeration jarEntries = jarFile.entries();
  -            if (getDebug() >= 2) {
  -                log("  Have retrieved entries enumeration");
  -            }
  -            while (jarEntries.hasMoreElements()) {
  -                JarEntry jarEntry = (JarEntry) jarEntries.nextElement();
  -                String name = jarEntry.getName();
  -                if (getDebug() >= 2) {
  -                    log("  Am processing entry " + name);
  -                }
  -                int last = name.lastIndexOf('/');
  -                if (last >= 0) {
  -                    File parent = new File(docBase,
  -                                           name.substring(0, last));
  -                    if (getDebug() >= 2) {
  -                        log("  Creating parent directory " + parent);
  -                    }
  -                    parent.mkdirs();
  -                }
  -                if (name.endsWith("/")) {
  -                    continue;
  -                }
  -                if (getDebug() >= 2) {
  -                    log("  Creating expanded file " + name);
  -                }
  -                input = jarFile.getInputStream(jarEntry);
  -                expand(input, docBase, name);
  -                input.close();
  -                input = null;
  -            }
  -            jarFile.close();
  -            jarFile = null;
  -        } finally {
  -            if (input != null) {
  -                try {
  -                    input.close();
  -                } catch (Throwable t) {
  -                    ;
  -                }
  -                input = null;
  -            }
  -            if (jarFile != null) {
  -                try {
  -                    jarFile.close();
  -                } catch (Throwable t) {
  -                    ;
  -                }
  -                jarFile = null;
  -            }
  -        }
  -
  -        // Return the absolute path to our new document base directory
  -        return (docBase.getAbsolutePath());
  +        return ExpandWar.expand(host,war);
   
       }
   
  @@ -809,17 +658,7 @@
       protected void expand(InputStream input, File docBase, String name)
           throws IOException {
   
  -        File file = new File(docBase, name);
  -        BufferedOutputStream output =
  -            new BufferedOutputStream(new FileOutputStream(file));
  -        byte buffer[] = new byte[2048];
  -        while (true) {
  -            int n = input.read(buffer);
  -            if (n <= 0)
  -                break;
  -            output.write(buffer, 0, n);
  -        }
  -        output.close();
  +        ExpandWar.expand(input,docBase,name);
   
       }
   
  
  
  
  1.16      +1 -0      jakarta-tomcat-4.0/catalina/src/share/org/apache/catalina/startup/LocalStrings.properties
  
  Index: LocalStrings.properties
  ===================================================================
  RCS file: /home/cvs/jakarta-tomcat-4.0/catalina/src/share/org/apache/catalina/startup/LocalStrings.properties,v
  retrieving revision 1.15
  retrieving revision 1.16
  diff -u -r1.15 -r1.16
  --- LocalStrings.properties	4 Apr 2002 20:30:34 -0000	1.15
  +++ LocalStrings.properties	10 Jan 2003 15:52:18 -0000	1.16
  @@ -33,6 +33,7 @@
   engineConfig.cce=Lifecycle event data object {0} is not an Engine
   engineConfig.start=EngineConfig: Processing START
   engineConfig.stop=EngineConfig: Processing STOP
  +hostConfig.appBase=Application base directory {0} does not exist
   hostConfig.cce=Lifecycle event data object {0} is not a Host
   hostConfig.deploy=Deploying web application directory {0}
   hostConfig.deployDescriptor=Deploying configuration descriptor {0}
  
  
  
  1.2       +1 -0      jakarta-tomcat-4.0/catalina/src/share/org/apache/catalina/startup/LocalStrings_fr.properties
  
  Index: LocalStrings_fr.properties
  ===================================================================
  RCS file: /home/cvs/jakarta-tomcat-4.0/catalina/src/share/org/apache/catalina/startup/LocalStrings_fr.properties,v
  retrieving revision 1.1
  retrieving revision 1.2
  diff -u -r1.1 -r1.2
  --- LocalStrings_fr.properties	6 Nov 2002 09:21:18 -0000	1.1
  +++ LocalStrings_fr.properties	10 Jan 2003 15:52:18 -0000	1.2
  @@ -33,6 +33,7 @@
   engineConfig.cce=L''objet donnée évènement cycle de vie (Lifecycle event data object) {0} n''est pas un moteur (engine)
   engineConfig.start="EngineConfig": Traitement du "START"
   engineConfig.stop="EngineConfig": Traitement du "STOP"
  +hostConfig.appBase=Le r\351pertoire de base de l''application {0} n''existe pas
   hostConfig.cce=L''objet donnée évènement cycle de vie (Lifecycle event data object) {0} n''est pas un hôte
   hostConfig.deploy=Déploiement du répertoire {0} de l''application web
   hostConfig.deployDescriptor=Déploiement du descripteur de configuration {0}
  
  
  
  1.3       +1 -0      jakarta-tomcat-4.0/catalina/src/share/org/apache/catalina/startup/LocalStrings_ja.properties
  
  Index: LocalStrings_ja.properties
  ===================================================================
  RCS file: /home/cvs/jakarta-tomcat-4.0/catalina/src/share/org/apache/catalina/startup/LocalStrings_ja.properties,v
  retrieving revision 1.2
  retrieving revision 1.3
  diff -u -r1.2 -r1.3
  --- LocalStrings_ja.properties	17 Sep 2001 23:14:43 -0000	1.2
  +++ LocalStrings_ja.properties	10 Jan 2003 15:52:18 -0000	1.3
  @@ -26,6 +26,7 @@
   engineConfig.cce=\u30e9\u30a4\u30d5\u30b5\u30a4\u30af\u30eb\u30a4\u30d9\u30f3\u30c8\u30c7\u30fc\u30bf\u30aa\u30d6\u30b8\u30a7\u30af\u30c8 {0} \u306f\u30a8\u30f3\u30b8\u30f3\u3067\u306f\u3042\u308a\u307e\u305b\u3093
   engineConfig.start=EngineConfig: \u51e6\u7406\u3092\u958b\u59cb\u3057\u307e\u3059
   engineConfig.stop=EngineConfig: \u51e6\u7406\u3092\u505c\u6b62\u3057\u307e\u3059
  +hostConfig.appBase=\u30a2\u30d7\u30ea\u30b1\u30fc\u30b7\u30e7\u30f3\u30d9\u30fc\u30b9\u30c7\u30a3\u30ec\u30af\u30c8\u30ea {0} \u304c\u5b58\u5728\u3057\u307e\u305b\u3093
   hostConfig.cce=\u30e9\u30a4\u30d5\u30b5\u30a4\u30af\u30eb\u30a4\u30d9\u30f3\u30c8\u30c7\u30fc\u30bf\u30aa\u30d6\u30b8\u30a7\u30af\u30c8 {0} \u306f\u30db\u30b9\u30c8\u3067\u306f\u3042\u308a\u307e\u305b\u3093
   hostConfig.deploy=Web\u30a2\u30d7\u30ea\u30b1\u30fc\u30b7\u30e7\u30f3\u30c7\u30a3\u30ec\u30af\u30c8\u30ea {0} \u3092\u914d\u5099\u3057\u307e\u3059
   hostConfig.deployDir=Web\u30a2\u30d7\u30ea\u30b1\u30fc\u30b7\u30e7\u30f3\u30c7\u30a3\u30ec\u30af\u30c8\u30ea {0} \u3092\u914d\u5099\u3057\u307e\u3059
  
  
  
  1.1                  jakarta-tomcat-4.0/catalina/src/share/org/apache/catalina/startup/ExpandWar.java
  
  Index: ExpandWar.java
  ===================================================================
  /*
   * $Header: /home/cvs/jakarta-tomcat-4.0/catalina/src/share/org/apache/catalina/startup/ExpandWar.java,v 1.1 2003/01/10 15:52:18 glenn Exp $
   * $Revision: 1.1 $
   * $Date: 2003/01/10 15:52:18 $
   *
   * ====================================================================
   *
   * The Apache Software License, Version 1.1
   *
   * Copyright (c) 1999 The Apache Software Foundation.  All rights
   * reserved.
   *
   * Redistribution and use in source and binary forms, with or without
   * modification, are permitted provided that the following conditions
   * are met:
   *
   * 1. Redistributions of source code must retain the above copyright
   *    notice, this list of conditions and the following disclaimer.
   *
   * 2. Redistributions in binary form must reproduce the above copyright
   *    notice, this list of conditions and the following disclaimer in
   *    the documentation and/or other materials provided with the
   *    distribution.
   *
   * 3. The end-user documentation included with the redistribution, if
   *    any, must include the following acknowlegement:
   *       "This product includes software developed by the
   *        Apache Software Foundation (http://www.apache.org/)."
   *    Alternately, this acknowlegement may appear in the software itself,
   *    if and wherever such third-party acknowlegements normally appear.
   *
   * 4. The names "The Jakarta Project", "Tomcat", and "Apache Software
   *    Foundation" must not be used to endorse or promote products derived
   *    from this software without prior written permission. For written
   *    permission, please contact apache@apache.org.
   *
   * 5. Products derived from this software may not be called "Apache"
   *    nor may "Apache" appear in their names without prior written
   *    permission of the Apache Group.
   *
   * THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED
   * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
   * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
   * DISCLAIMED.  IN NO EVENT SHALL THE APACHE SOFTWARE FOUNDATION OR
   * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
   * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
   * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF
   * USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
   * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
   * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT
   * OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
   * SUCH DAMAGE.
   * ====================================================================
   *
   * This software consists of voluntary contributions made by many
   * individuals on behalf of the Apache Software Foundation.  For more
   * information on the Apache Software Foundation, please see
   * <http://www.apache.org/>.
   *
   * [Additional notices, if required by prior licensing conditions]
   *
   */
  
  
  package org.apache.catalina.startup;
  
  import java.io.BufferedOutputStream;
  import java.io.File;
  import java.io.FileOutputStream;
  import java.io.InputStream;
  import java.io.IOException;
  import java.net.JarURLConnection;
  import java.net.URL;
  import java.util.Enumeration;
  import java.util.jar.JarEntry;
  import java.util.jar.JarFile;
  
  import org.apache.catalina.Host;
  import org.apache.catalina.Logger;
  import org.apache.catalina.core.StandardHost;
  import org.apache.catalina.util.StringManager;
  
  /**
   * Expand out a WAR in a Host's appBase.
   *
   * @author Craig R. McClanahan
   * @author Remy Maucherat
   * @author Glenn L. Nielsen
   * @version $Revision: 1.1 $
   */
  
  public class ExpandWar {
  
      /**
       * The string resources for this package.
       */
      protected static final StringManager sm =
          StringManager.getManager(Constants.Package);
  
      /**
       * Expand the WAR file found at the specified URL into an unpacked
       * directory structure, and return the absolute pathname to the expanded
       * directory.
       *
       * @param host Host war is being installed for
       * @param war URL of the web application archive to be expanded
       *  (must start with "jar:")
       *
       * @exception IllegalArgumentException if this is not a "jar:" URL
       * @exception IOException if an input/output error was encountered
       *  during expansion
       */
      public static String expand(Host host, URL war) throws IOException {
  
          int debug = 0;
          Logger logger = host.getLogger();
  
          if (host instanceof StandardHost) {
              debug = ((StandardHost) host).getDebug();
          }
  
          // Calculate the directory name of the expanded directory
          if (debug >= 1) {
              logger.log("expand(" + war.toString() + ")");
          }
          String pathname = war.toString().replace('\\', '/');
          if (pathname.endsWith("!/")) {
              pathname = pathname.substring(0, pathname.length() - 2);
          }
          int period = pathname.lastIndexOf('.');
          if (period >= pathname.length() - 4)
              pathname = pathname.substring(0, period);
          int slash = pathname.lastIndexOf('/');
          if (slash >= 0) {
              pathname = pathname.substring(slash + 1);
          }
          if (debug >= 1) {
              logger.log("  Proposed directory name: " + pathname);
          }
          return expand(host,war,pathname);
      }
  
      /**
       * Expand the WAR file found at the specified URL into an unpacked
       * directory structure, and return the absolute pathname to the expanded
       * directory.
       *
       * @param host Host war is being installed for
       * @param war URL of the web application archive to be expanded
       *  (must start with "jar:")
       * @param pathname Context path name for web application
       *
       * @exception IllegalArgumentException if this is not a "jar:" URL
       * @exception IOException if an input/output error was encountered
       *  during expansion
       */
      public static String expand(Host host, URL war, String pathname) throws IOException {
  
          int debug = 0;
          Logger logger = host.getLogger();
  
          if (host instanceof StandardHost) {
              debug = ((StandardHost) host).getDebug();
          }
  
          // Make sure that there is no such directory already existing
          File appBase = new File(host.getAppBase());
          if (!appBase.isAbsolute()) {
              appBase = new File(System.getProperty("catalina.base"),
                                 host.getAppBase());
          }
          if (!appBase.exists() || !appBase.isDirectory()) {
              throw new IOException
                  (sm.getString("hostConfig.appBase",
                                appBase.getAbsolutePath()));
          }
          File docBase = new File(appBase, pathname);
          if (docBase.exists()) {
              // War file is already installed
              return (docBase.getAbsolutePath());
          }
  
          // Create the new document base directory
          docBase.mkdir();
          if (debug >= 2) {
              logger.log("  Have created expansion directory " +
                  docBase.getAbsolutePath());
          }
  
          // Expand the WAR into the new document base directory
          JarURLConnection juc = (JarURLConnection) war.openConnection();
          juc.setUseCaches(false);
          JarFile jarFile = null;
          InputStream input = null;
          try {
              jarFile = juc.getJarFile();
              if (debug >= 2) {
                  logger.log("  Have opened JAR file successfully");
              }
              Enumeration jarEntries = jarFile.entries();
              if (debug >= 2) {
                  logger.log("  Have retrieved entries enumeration");
              }
              while (jarEntries.hasMoreElements()) {
                  JarEntry jarEntry = (JarEntry) jarEntries.nextElement();
                  String name = jarEntry.getName();
                  if (debug >= 2) {
                      logger.log("  Am processing entry " + name);
                  }
                  int last = name.lastIndexOf('/');
                  if (last >= 0) {
                      File parent = new File(docBase,
                                             name.substring(0, last));
                      if (debug >= 2) {
                          logger.log("  Creating parent directory " + parent);
                      }
                      parent.mkdirs();
                  }
                  if (name.endsWith("/")) {
                      continue;
                  }
                  if (debug >= 2) {
                      logger.log("  Creating expanded file " + name);
                  }
                  input = jarFile.getInputStream(jarEntry);
                  expand(input, docBase, name);
                  input.close();
                  input = null;
              }
              jarFile.close();
              jarFile = null;
          } finally {
              if (input != null) {
                  try {
                      input.close();
                  } catch (Throwable t) {
                      ;
                  }
                  input = null;
              }
              if (jarFile != null) {
                  try {
                      jarFile.close();
                  } catch (Throwable t) {
                      ;
                  }
                  jarFile = null;
              }
          }
  
          // Return the absolute path to our new document base directory
          return (docBase.getAbsolutePath());
  
      }
  
      /**
       * Expand the specified input stream into the specified directory, creating
       * a file named from the specified relative path.
       *
       * @param input InputStream to be copied
       * @param docBase Document base directory into which we are expanding
       * @param name Relative pathname of the file to be created
       *
       * @exception IOException if an input/output error occurs
       */
      protected static void expand(InputStream input, File docBase, String name)
          throws IOException {
  
          File file = new File(docBase, name);
          BufferedOutputStream output =
              new BufferedOutputStream(new FileOutputStream(file));
          byte buffer[] = new byte[2048];
          while (true) {
              int n = input.read(buffer);
              if (n <= 0)
                  break;
              output.write(buffer, 0, n);
          }
          output.close();
  
      }
  
  }
  
  
  
  1.9       +20 -0     jakarta-tomcat-4.0/webapps/manager/build.xml
  
  Index: build.xml
  ===================================================================
  RCS file: /home/cvs/jakarta-tomcat-4.0/webapps/manager/build.xml,v
  retrieving revision 1.8
  retrieving revision 1.9
  diff -u -r1.8 -r1.9
  --- build.xml	16 Sep 2001 04:58:28 -0000	1.8
  +++ build.xml	10 Jan 2003 15:52:19 -0000	1.9
  @@ -20,6 +20,8 @@
     <target name="build-prepare">
       <mkdir dir="${webapps.build}"/>
       <mkdir dir="${webapps.build}/${webapp.name}"/>
  +    <mkdir dir="${webapps.build}/${webapp.name}/images"/>
  +    <mkdir dir="${webapps.build}/${webapp.name}/WEB-INF"/>
     </target>
   
   
  @@ -35,6 +37,24 @@
   
     <!-- ================= BUILD: Compile Server Components ================= -->
     <target name="build-main" depends="build-static">
  +
  +    <!-- Top Level Directory -->
  +    <style basedir="../tomcat-docs"
  +           destdir="${webapps.build}/${webapp.name}"
  +           extension=".html"
  +           style="tomcat-docs.xsl"
  +           excludes="build.xml project.xml"
  +           includes="manager-howto.xml,html-manager-howto.xml">
  +      <param name="relative-path" expression="."/>
  +      <param name="project-menu" expression="nomenu"/>
  +    </style>
  +
  +    <!-- Images Subdirectory -->
  +    <copy todir="${webapps.build}/${webapp.name}/images">
  +      <fileset dir="../tomcat-docs/images">
  +        <include name="jakarta-logo.gif,tomcat.gif"/>
  +      </fileset>
  +    </copy>
   
   <!--
       <javac   srcdir="WEB-INF/classes" 
  
  
  
  1.7       +54 -3     jakarta-tomcat-4.0/webapps/manager/WEB-INF/web.xml
  
  Index: web.xml
  ===================================================================
  RCS file: /home/cvs/jakarta-tomcat-4.0/webapps/manager/WEB-INF/web.xml,v
  retrieving revision 1.6
  retrieving revision 1.7
  diff -u -r1.6 -r1.7
  --- web.xml	13 Jun 2002 17:38:01 -0000	1.6
  +++ web.xml	10 Jan 2003 15:52:19 -0000	1.7
  @@ -38,7 +38,47 @@
     <!-- Define the Manager Servlet Mapping -->
     <servlet-mapping>
       <servlet-name>Manager</servlet-name>
  -    <url-pattern>/*</url-pattern>
  +      <url-pattern>/list</url-pattern>
  +  </servlet-mapping>
  +  <servlet-mapping>
  +    <servlet-name>Manager</servlet-name>
  +      <url-pattern>/sessions</url-pattern>
  +  </servlet-mapping>
  +  <servlet-mapping>
  +    <servlet-name>Manager</servlet-name>
  +      <url-pattern>/start</url-pattern>
  +  </servlet-mapping>
  +  <servlet-mapping>
  +    <servlet-name>Manager</servlet-name>
  +      <url-pattern>/stop</url-pattern>
  +  </servlet-mapping>
  +  <servlet-mapping>
  +    <servlet-name>Manager</servlet-name>
  +      <url-pattern>/install</url-pattern>
  +  </servlet-mapping>
  +  <servlet-mapping>
  +    <servlet-name>Manager</servlet-name>
  +      <url-pattern>/remove</url-pattern>
  +  </servlet-mapping>
  +  <servlet-mapping>
  +    <servlet-name>Manager</servlet-name>
  +      <url-pattern>/undeploy</url-pattern>
  +  </servlet-mapping>
  +  <servlet-mapping>
  +    <servlet-name>Manager</servlet-name>
  +      <url-pattern>/reload</url-pattern>
  +  </servlet-mapping>
  +  <servlet-mapping>
  +    <servlet-name>Manager</servlet-name>
  +      <url-pattern>/serverinfo</url-pattern>
  +  </servlet-mapping>
  +  <servlet-mapping>
  +    <servlet-name>Manager</servlet-name>
  +      <url-pattern>/roles</url-pattern>
  +  </servlet-mapping>
  +  <servlet-mapping>
  +    <servlet-name>Manager</servlet-name>
  +      <url-pattern>/resources</url-pattern>
     </servlet-mapping>
     <servlet-mapping>
       <servlet-name>HTMLManager</servlet-name>
  @@ -62,8 +102,19 @@
     <!-- Define a Security Constraint on this Application -->
     <security-constraint>
       <web-resource-collection>
  -      <web-resource-name>Entire Application</web-resource-name>
  -      <url-pattern>/*</url-pattern>
  +      <web-resource-name>HTMLManger and Manager command</web-resource-name>
  +      <url-pattern>/html/*</url-pattern>
  +      <url-pattern>/list</url-pattern>
  +      <url-pattern>/sessions</url-pattern>
  +      <url-pattern>/start</url-pattern>
  +      <url-pattern>/stop</url-pattern>
  +      <url-pattern>/install</url-pattern>
  +      <url-pattern>/remove</url-pattern>
  +      <url-pattern>/undeploy</url-pattern>
  +      <url-pattern>/reload</url-pattern>
  +      <url-pattern>/serverinfo</url-pattern>
  +      <url-pattern>/roles</url-pattern>
  +      <url-pattern>/resources</url-pattern>
       </web-resource-collection>
       <auth-constraint>
          <!-- NOTE:  This role is not present in the default users file -->
  
  
  
  1.17      +3 -0      jakarta-tomcat-4.0/webapps/tomcat-docs/index.xml
  
  Index: index.xml
  ===================================================================
  RCS file: /home/cvs/jakarta-tomcat-4.0/webapps/tomcat-docs/index.xml,v
  retrieving revision 1.16
  retrieving revision 1.17
  diff -u -r1.16 -r1.17
  --- index.xml	10 Sep 2002 09:06:55 -0000	1.16
  +++ index.xml	10 Jan 2003 15:52:19 -0000	1.17
  @@ -70,6 +70,9 @@
   <li><a href="class-loader-howto.html"><strong>Class Loader HOW-TO</strong></a>
       - Information about class loading in Tomcat 4, including where to place
       your application classes so that they are visible.</li>
  +<li><a href="html-manager-howto.html"><strong>HTML Manager App HOW-TO</strong></a> -
  +    Operating the <code>HTML Manager</code> web app to deploy, undeploy, and
  +    redeploy applications while Tomcat is running.</li>
   <li><a href="jndi-datasource-examples-howto.html">
       <strong>JNDI DataSource HOW-TO</strong></a>
       - Configuring a JNDI DataSoure with a dB connection pool.
  
  
  
  1.17      +213 -29   jakarta-tomcat-4.0/webapps/tomcat-docs/manager-howto.xml
  
  Index: manager-howto.xml
  ===================================================================
  RCS file: /home/cvs/jakarta-tomcat-4.0/webapps/tomcat-docs/manager-howto.xml,v
  retrieving revision 1.16
  retrieving revision 1.17
  diff -u -r1.16 -r1.17
  --- manager-howto.xml	30 Aug 2002 03:46:27 -0000	1.16
  +++ manager-howto.xml	10 Jan 2003 15:52:19 -0000	1.17
  @@ -13,6 +13,35 @@
   
   <body>
   
  +<section name="Table of Contents">
  +
  +<p>
  +<a href="#Introduction">Introduction</a><br />
  +<a href="#Configuring Manager Application Access">
  +Configuring Manager Application Access</a><br />
  +<a href="#Supported Manager Commands">Supported Manager Commands</a><br />
  +<blockquote>
  +<a href="#Deploy A New Application">Deploy A New Application</a><br />
  +<a href="#Install A New Application">Install A New Application</a><br />
  +<a href="#List Currently Deployed and Installed Applications">
  +List Currently Deployed and Installed Applications</a><br />
  +<a href="#Reload An Existing Application">Reload An Existing Application</a><br />
  +<a href="#Remove an Existing Application">Remove an Existing Application</a><br />
  +<a href="#List OS and JVM Properties">List OS and JVM Properties</a><br />
  +<a href="#List Available Global JNDI Resources">
  +List Available Global JNDI Resources</a><br />
  +<a href="#List Available Security Roles">List Available Security Roles</a><br />
  +<a href="#Session Statistics">Session Statistics</a><br />
  +<a href="#Start an Existing Application">Start an Existing Application</a><br />
  +<a href="#Stop an Existing Application">Stop an Existing Application</a><br />
  +<a href="#Undeploy an Existing Application">
  +Undeploy an Existing Application</a><br />
  +</blockquote>
  +<a href="#Executing Manager Commands With Ant">
  +Executing Manager Commands With Ant</a><br />
  +</p>
  +
  +</section>
   
   <section name="Introduction">
   
  @@ -36,6 +65,7 @@
   <li>Reload an existing web application, to reflect changes in the
       contents of <code>/WEB-INF/classes</code> or <code>/WEB-INF/lib</code>.
       </li>
  +<li>List the OS and JVM property values.</li>
   <li>List the available global JNDI resources, for use in deployment
       tools that are preparing <code>&lt;ResourceLink&gt;</code> elements
       nested in a <code>&lt;Context&gt;</code> deployment description.</li>
  @@ -196,8 +226,9 @@
       It is not possible to perform administrative commands on the
       Manager application itself.</li>
   <li><strong>war</strong> - URL of a web application archive (WAR) file,
  -    or pathname of a directory, that contains the web application.
  -    You can use URLs in any of the following formats:
  +    pathname of a directory which contains the web application, or a
  +    Context configuration ".xml" file.  You can use URLs in any of the
  +    following formats:
       <ul>
       <li><strong>file:/absolute/path/to/a/directory</strong> - The absolute
           path of a directory that contains the unpacked version of a web
  @@ -211,10 +242,13 @@
           URL to a local web application archive (WAR) file.  You can use any
           syntax that is valid for the <code>JarURLConnection</code> class
           for reference to an entire JAR file.</li>
  -    <li><strong>jar:http://hostname:port/path/to/a/warfile.war!/</strong> -
  -        You can also deploy web applications from a remote JAR file.  You can
  -        use any syntax that is valid for the <code>JarURLConnection</code>
  -        class for reference to an entire JAR file.</li>
  +    <li><strong>file:/absolute/path/to/a/context.xml</strong> - The
  +        absolute path of a web application Context configuration ".xml"
  +        file which contains the Context configuration element.</li>
  +    <li><strong>directory</strong> - The directory name for the web
  +        applciation context in the Host's application base directory.</li>
  +    <li><strong>webapp.war</strong> - The name of a web application war file
  +        located in the Host's application base directory.</li>
       </ul></li>
   </ul>
   
  @@ -240,7 +274,9 @@
   <p>Upload the web application archive (WAR) file that is specified as the
   request data in this HTTP PUT request, install it into the <code>appBase</code>
   directory of our corresponding virtual host, and start it on the context path
  -specified by the <code>path</code> request parameter.  The application can
  +specified by the <code>path</code> request parameter.  If no <code>path</code>
  +is specified the directory name or the war file name without the .war extension
  +is used as the path.  The application can
   later be undeployed (and the corresponding application directory removed)
   by use of the <code>/undeploy</code>.</p>
   
  @@ -290,20 +326,127 @@
   
   <subsection name="Install A New Application">
   
  +<p>Install and start a new web application, attached to the specified context
  +<code>path</code> (which must not be in use by any other web application).
  +This command is the logical opposite of the <code>/remove</code> command.</p>
  +
  +<p>There are a number of different ways the install command can be used.</p>
  +
  +<h3>Install a Directory or WAR by URL</h3>
  +
  +<p>Install a web application directory or ".war" file located on the Tomcat
  +server. If no <code>path</code> is specified the directory name or the war file
  +name without the ".war" extension is used as the path. The <code>war</code>
  +parameter specifies a URL (including the <code>file:</code> scheme) for either
  +a directory or a web application archive (WAR) file. The supported syntax for
  +a URL referring to a WAR file is described on the Javadocs page for the
  +<code>java.net.JarURLConnection</code> class.  Use only URLs that refer to
  +the entire WAR file.</p>
  +
  +<p>In this example the web application located in the directory
  +<code>/path/to/foo</code> on the Tomcat server is installed as the 
  +web application context named <code>/footoo</code>.
   <source>
  -http://localhost:8080/manager/install?path=/foo&amp;war=file:/path/to/foo
  +http://localhost:8080/manager/install?path=/footoo&amp;war=file:/path/to/foo
  +</source>
  +</p>
   
  -http://localhost:8080/manager/install?path=/bar&amp;war=jar:file:/path/to/bar.war!/
  +<p>In this example the ".war" file <code>/path/to/bar.war</code> on the
  +Tomcat server is installed as the web application context named
  +<code>/bar</code>. Notice that there is no <code>path</code> parameter
  +so the context path defaults to the name of the web application archive
  +file without the ".war" extension.
  +<source>
  +http://localhost:8080/manager/install?war=jar:file:/path/to/bar.war!/
   </source>
  +</p>
  +
  +<h3>Install a Directory or War from the Host appBase</h3>
  +
  +<p>Install a web application directory or ".war" file located in your Host
  +appBase directory. If no <code>path</code> is specified the directory name
  +or the war file name without the ".war" extension is used as the path.</p>
  +
  +<p>In this example the web application located in a sub directory named
  +<code>foo</code> in the Host appBase directory of the Tomcat server is
  +installed as the web application context named <code>/foo</code>. Notice
  +that there is no <code>path</code> parameter so the context path defaults
  +to the name of the web application directory.
  +<source>
  +http://localhost:8080/manager/install?war=foo
  +</source>
  +</p>
  +
  +<p>In this example the ".war" file <code>bar.war</code> located in your
  +Host appBase directory on the Tomcat server is installed as the web
  +application context named <code>/bartoo</code>.
  +<source>
  +http://localhost:8080/manager/install?path=/bartoo&amp;war=bar.war
  +</source>
  +</p>
  +
  +<h3>Install using a Context configuration ".xml" file</h3>
  +
  +<p>If the Host deployXML flag is set to true you can install a web
  +application using a Context configuration ".xml" file and an optional
  +".war" file or web application directory. The context <code>path</code>
  +is not used when installing a web application using a context ".xml"
  +configuration file.</p>
  +
  +<p>A Context configuration ".xml" file can contain valid XML for a
  +web application Context just as if it were configured in your
  +Tomcat <code>server.xml</code> configuration file. Here is an
  +example:
  +<source>
  +&lt;Context path="/foobar" docBase="/path/to/application/foobar"
  +         debug="0"&gt;
  +
  +  &lt;!-- Link to the user database we will get roles from --&gt;
  +  &lt;ResourceLink name="users" global="UserDatabase"
  +                type="org.apache.catalina.UserDatabase"/&gt;
  +
  +&lt;/Context&gt;
  +</source>
  +</p>
  +
  +<p>When the optional <code>war</code> parameter is set to the URL
  +for a web application ".war" file or directory it overrides any
  +docBase configured in the context configuration ".xml" file.</p>
  +
  +<p>Here is an example of installing an application using a Context
  +configuration ".xml" file.
  +<source>
  +http://localhost:8080/manager/install?config=file:/path/to/context.xml
  +</source>
  +</p>
  +
  +<p>Here is an example of installing an application using a Context
  +configuration ".xml" file and a web application ".war" file located
  +on the server.
  +<source>                                                          
  +http://localhost:8080/manager/install?config=file:/path/to/context.xml&amp;war=jar:file:/path/to/bar.war!/
  +</source>
  +</p>
  +
  +<h3>Installation Notes</h3>
  +
  +<p>If the Host is configured with unpackWARs=true and you install a war
  +file, the war will be unpacked into a directory in your Host appBase
  +directory.</p>
  +
  +<p>If the application war or directory is installed in your Host appBase
  +directory and either the Host is configured with autoDeploy=true or
  +liveDeploy=true, the Context path must match the directory name or
  +war file name without the ".war" extension.</p>
  +
  +<p>For security when untrusted users can manage web applications the
  +Host deployXML flag can be set to false.  This prevents untrusted users
  +from installing web applications using a configuration XML file and
  +also prevents them from installing application directories or ".war"
  +files located outside of their Host appBase.</p>
   
  -<p>Install and start a new web application, attached to the specified context
  -path (which must not be in use by any other web application).  The
  -<code>war</code> parameter specifies a URL (including the <code>file:</code>
  -scheme) for either a directory or a web application archive (WAR) file.
  -The supported syntax for a URL referring to a WAR file is described on the
  -Javadocs page for the <code>java.net.JarURLConnection</code> class.  Use
  -only URLs that refer to the entire WAR file.  This command is the logical
  -opposite of the <code>/remove</code> command.</p>
  +
  +<h3>Install Response</h3>
   
   <p>If installation and startup is successful, you will receive a response
   like this:</p>
  @@ -347,12 +490,22 @@
       <blockquote>
       <p>The context path must start with a slash character, unless you are
       referencing the ROOT web application -- in which case the context path
  -    must be a zero-length string.</p>
  +    must be a "/" string.</p>
       </blockquote></li>
  -<li><em>No context path was specified</em>
  +<li><em>Context path must match the directory or WAR file name:</em>
       <blockquote>
  -    The <code>path</code> parameter is required.
  -    </blockquote></li>
  +    If the application war or directory is installed in your Host appBase
  +    directory and either the Host is configured with autoDeploy=true or
  +    liveDeploy=true, the Context path must match the directory name or
  +    war file name without the ".war" extension.
  +    </blockquote></li>
  +<li><em>Only web applications in the Host web application directory can
  +     be installed</em>
  +     <blockquote>
  +     If the Host deployXML flag is set to false this error will happen
  +     if an attempt is made to install a web application directory or
  +      ".war" file outside of the Host appBase directory.
  +     </blockquote></li>
   </ul>
   
   </subsection>
  @@ -384,12 +537,16 @@
   </source>
   
   <p>Signal an existing application to shut itself down and reload.  This can
  -be useful when you've recompiled classes on an application that is not
  -configured with the <code>reloadable="true"</code> attribute in its
  -<code>&lt;Context&gt;</code> entry in
  -<code>$CATALINA_HOME/conf/server.xml</code>, or when you've made other
  -changes (such as to <code>conf/web.xml</code>) that are not automatically
  -recognized by Tomcat.</p>
  +be useful when the web application context is not reloadable and you have
  +updated classes or property files in the <code>/WEB-INF/classes</code>
  +directory or when you have added or updated jar files in the
  +<code>/WEB-INF/lib</code> directory.
  +</p>
  +<p><strong>NOTE:</strong> The <code>/WEB-INF/web.xml</code>
  +web application configuration file is not reread on a reload.
  +If you have made changes to your web.xml file you must stop
  +then start the web application.
  +</p>
   
   <p>If this command succeeds, you will see a response like this:</p>
   <source>
  @@ -419,7 +576,7 @@
       <blockquote>
       The <code>path</code> parameter is required.
       </blockquote></li>
  -<li><em>Reload note supported on WAR deployed at path /foo</em>
  +<li><em>Reload not supported on WAR deployed at path /foo</em>
       <blockquote>
       Currently, application reloading (to pick up changes to the classes or
       <code>web.xml</code> file) is not supported when a web application is
  @@ -438,6 +595,13 @@
   http://localhost:8080/manager/remove?path=/examples
   </source>
   
  +<p><strong><font color="red">WARNING</font> - This command will delete the
  +contents of the web application directory and/or ".war file if it exists within
  +the <code>appBase</code> directory (typically "webapps") for this virtual host
  +</strong>.  The web application temporary work directory is also deleted.  If
  +you simply want to take an application out of service, you should use the
  +<code>/stop</code> command instead.</p>
  +
   <p>Signal an existing application to gracefully shut itself down, and then
   remove it from Tomcat (which also makes this context path available for
   reuse later).  This command is the logical opposite of the
  @@ -475,6 +639,26 @@
   
   </subsection>
   
  +<subsection name="List OS and JVM Properties">
  +
  +<source>
  +http://localhost:8080/manager/serverinfo
  +</source>
  +
  +<p>Lists information about the Tomcat version, OS, and JVM properties.</p>
  +
  +<p>If an error occurs, the response will start with <code>FAIL</code> and
  +include an error message.  Possible causes for problems include:</p>
  +<ul>
  +<li><em>Encountered exception</em>
  +    <blockquote>
  +    <p>An exception was encountered trying to enumerate the system properties.
  +    Check the Tomcat 4 logs for the details.</p>
  +    </blockquote></li>
  +</ul>
  +
  +</subsection>
  +
   <subsection name="List Available Global JNDI Resources">
   
   <source>
  @@ -698,7 +882,7 @@
   delete the contents of the web application directory if it exists within the
   <code>appBase</code> directory (typically "webapps") for this virtual host
   </strong>.  If you simply want to take an application out of service,
  -you should use the <code>/remove</code> command instead.</p>
  +you should use the <code>/stop</code> command instead.</p>
   
   <p>Signal an existing application to gracefully shut itself down, and
   remove it from Tomcat (which also makes this context path available for
  
  
  
  1.19      +1 -0      jakarta-tomcat-4.0/webapps/tomcat-docs/project.xml
  
  Index: project.xml
  ===================================================================
  RCS file: /home/cvs/jakarta-tomcat-4.0/webapps/tomcat-docs/project.xml,v
  retrieving revision 1.18
  retrieving revision 1.19
  diff -u -r1.18 -r1.19
  --- project.xml	10 Sep 2002 09:06:55 -0000	1.18
  +++ project.xml	10 Jan 2003 15:52:19 -0000	1.19
  @@ -30,6 +30,7 @@
           <item name="CGI HOW-TO"            href="cgi-howto.html"/>
           <item name="Class Loader HOW-TO"   href="class-loader-howto.html"/>
           <item name="Connectors List"       href="config/connectors.html"/>
  +        <item name="HTML Manager App HOW-TO" href="html-manager-howto.html"/>
           <item name="JK Documentation"      href="jk2/index.html"/>
           <item name="JNDI DataSource HOW-TO" 
                 href="jndi-datasource-examples-howto.html"/>
  
  
  
  1.1                  jakarta-tomcat-4.0/webapps/tomcat-docs/html-manager-howto.xml
  
  Index: html-manager-howto.xml
  ===================================================================
  <?xml version="1.0"?>
  <!DOCTYPE document [
    <!ENTITY project SYSTEM "project.xml">
  ]>
  <document>
  
      &project;
  
      <properties>
          <author email="glenn@apache.org">Glenn L. Nielsen</author>
          <title>Tomcat Web Application Manager How To</title>
      </properties>
  
  <body>
  
  <section name="Introduction">
  
  <p>In many production environments, it is very useful to have the capability
  to manage your web applications without having to shut down and restart the
  entire Tomcat container.  The <a href="manager-howto.html">manager</a> web
  application provides this capability. This documentation is for the HTML web
  interface version of the manager which makes administering web applications
  easier.</p>
  
  <p>The interface is divided into five sections:
  <ul>
    <li><strong>Message</strong> - Displays success and failure messages.</li>
    <li><strong>Manager</strong> - General manager operations like list and
        help.</li>
    <li><strong>Applications</strong> - List of web applications and
        commands.</li>
    <li><strong>Install</strong> - Installing web applications.</li>
    <li><strong>Server Information</strong> - Information about the Tomcat
        server.</li>
  </ul>
  </p>
  
  </section>
  
  <section name="Message">
  
  <p>
  Displays information about the success or failure of the last web application
  manager command you performed. If it suceeded <strong>OK</strong> is displayed
  and may be followed by a success message. If it failed <strong>FAIL</strong>
  is displayed followed by an error message. Common failure messages will be
  documented below for each command.  The complete list of failure messages for
  each command can be found in the <a href="manager-howto.html">manager</a> web
  application documentation.
  </p>
  
  </section>
  
  <section name="Manager">
  
  <p>The Manager section has three links:
  <ul>
    <li><strong>List Applications</strong> - Redisplay a list of web
        applications.</li>
    <li><strong>HTML Manager Help</strong> - A link to this document.</li>
    <li><strong>Manager Help</strong> - A link to the comprehensive Manager
        App HOW TO.</li>
  </ul>
  </p>
  
  </section>
  
  <section name="Applications">
  
  <p>The Applications section lists information about all the installed web
  applications and provides links for managing them. For each web application
  the following is displayed:
  <ul>
    <li><strong>Path</strong> - The web applicaton context path.</li>
    <li><strong>Display Name</strong> - The display name for the web application
        if it has one configured in its "web.xml" file.</li>
    <li><strong>Running</strong> - Whether the web application is running and
        available (true), or not running and unavailable (false).</li>
    <li><strong>Sessions</strong> - The number of active sessions for remote
        users of this web application.  The number of sessions is a link which
        when submitted displays more details about session usage by the web
        application in the Message box.</li>
    <li><strong>Commands</strong> - Lists all commands which can be performed on
        the web application. Only those commands which can be performed will be
        listed as a link which can be submitted. No commands can be performed on
        the manager web application itself. The following commands can be
        performed:
        <ul>
          <li><strong>Start</strong> - Start a web application which had been
              stopped.</li>
          <li><strong>Stop</strong> - Stop a web application which is currently
              running and make it unavailable.</li>
          <li><strong>Reload</strong> - Reload the web application so that new
              ".jar" files in <code>/WEB-INF/lib/</code> or new classes in
              <code>/WEB-INF/classes/</code> can be used.</li>
          <li><strong>Remove</strong> - Stop and then remove this web
               application from the server.</li>
        </ul>
    </li>
  </ul>
  </p>
  
  <subsection name="Start">
  
  <p>Signal a stopped application to restart, and make itself available again.
  Stopping and starting is useful, for example, if the database required by
  your application becomes temporarily unavailable.  It is usually better to
  stop the web application that relies on this database, rather than letting
  users continuously encounter database exceptions.</p>
  
  <p>If this command succeeds, you will see a Message like this:</p>
  <source>
  OK - Started application at context path /examples
  </source>
  
  <p>Otherwise, the Message will start with <code>FAIL</code> and include an
  error message.  Possible causes for problems include:
  <ul>
  <li><em>Encountered exception</em>
      <blockquote>             
      <p>An exception was encountered trying to start the web application.
      Check the Tomcat 4 logs for the details.</p>
      </blockquote></li>       
  <li><em>Invalid context path was specified</em>
      <blockquote>             
      <p>The context path must start with a slash character, unless you are
      referencing the ROOT web application -- in which case the context path
      must be a zero-length string.</p>
      </blockquote></li>       
  <li><em>No context exists for path /foo</em>
      <blockquote>             
      <p>There is no deployed or installed application on the context path
      that you specified.</p>  
      </blockquote></li>       
  <li><em>No context path was specified</em>
      <blockquote>             
      The <code>path</code> parameter is required.
      </blockquote></li>       
  </ul>
  </p>
  
  </subsection>
  
  <subsection name="Stop">
  
  <p>Signal an existing application to make itself unavailable, but leave it
  deployed or installed.  Any request that comes in while an application is
  stopped will see an HTTP error 404, and this application will show as
  "stopped" on a list applications command.</p>
                               
  <p>If this command succeeds, you will see a Message like this:</p>
  <source>                     
  OK - Stopped application at context path /examples
  </source>                    
                               
  <p>Otherwise, the Message will start with <code>FAIL</code> and include an
  error message.  Possible causes for problems include:
  <ul>                         
  <li><em>Encountered exception</em>
      <blockquote>             
      <p>An exception was encountered trying to stop the web application.
      Check the Tomcat 4 logs for the details.</p>
      </blockquote></li>       
  <li><em>Invalid context path was specified</em>
      <blockquote>             
      <p>The context path must start with a slash character, unless you are
      referencing the ROOT web application -- in which case the context path
      must be a zero-length string.</p>
      </blockquote></li>       
  <li><em>No context exists for path /foo</em>
      <blockquote>             
      <p>There is no deployed or installed application on the context path
      that you specified.</p>  
      </blockquote></li>       
  <li><em>No context path was specified</em>
      <blockquote>             
      The <code>path</code> parameter is required.
      </blockquote></li>       
  </ul>
  </p>
  
  </subsection>
  
  <subsection name="Reload">
  
  <p>Signal an existing application to shut itself down and reload.  This can
  be useful when the web application context is not reloadable and you have
  updated classes or property files in the <code>/WEB-INF/classes</code>
  directory or when you have added or updated jar files in the
  <code>/WEB-INF/lib</code> directory.
  </p>
  <p><strong>NOTE:</strong> The <code>/WEB-INF/web.xml</code>
  web application configuration file is not reread on a reload.
  If you have made changes to your web.xml file you must stop
  then start the web application.
  </p>
  
  <p>If this command succeeds, you will see a Message like this:</p>
  <source>
  OK - Reloaded application at context path /examples
  </source>
  
  <p>Otherwise, the Message will start with <code>FAIL</code> and include an
  error message.  Possible causes for problems include:
  <ul>
  <li><em>Encountered exception</em>
      <blockquote>             
      <p>An exception was encountered trying to restart the web application.
      Check the Tomcat 4 logs for the details.</p>
      </blockquote></li>       
  <li><em>Invalid context path was specified</em>
      <blockquote>             
      <p>The context path must start with a slash character, unless you are
      referencing the ROOT web application -- in which case the context path
      must be a zero-length string.</p>
      </blockquote></li>       
  <li><em>No context exists for path /foo</em>
      <blockquote>             
      <p>There is no deployed or installed application on the context path
      that you specified.</p>  
      </blockquote></li>       
  <li><em>No context path was specified</em>
      <blockquote>             
      The <code>path</code> parameter is required.
      </blockquote></li>       
  <li><em>Reload not supported on WAR deployed at path /foo</em>
      <blockquote>             
      Currently, application reloading (to pick up changes to the classes or
      <code>web.xml</code> file) is not supported when a web application is
      installed directly from a WAR file.  It only works when the web application
      is installed from an unpacked directory.  If you are using a WAR file,
      you should <code>remove</code> and then <code>install</code> the
      application again to pick up your changes.
      </blockquote></li>       
  </ul>
  </p>
  
  </subsection>
  
  <subsection name="Remove">
  
  <p><strong><font color="red">WARNING</font> - This command will delete the
  contents of the web application directory and/or ".war fileif it exists within
  the <code>appBase</code> directory (typically "webapps") for this virtual host
  </strong>.  The web application temporary work directory is also deleted.  If
  you simply want to take an application out of service, you should use the
  <code>/stop</code> command instead.</p>
                               
  <p>Signal an existing application to gracefully shut itself down, and then
  remove it from Tomcat (which also makes this context path available for
  reuse later).  This command is the logical opposite of the
  <code>/install</code> command.</p>
                               
  <p>If this command succeeds, you will see a Message like this:</p>
  <source>                     
  OK - Removed application at context path /examples
  </source>                    
                               
  <p>Otherwise, the Message will start with <code>FAIL</code> and include an
  error message.  Possible causes for problems include:
  <ul>                         
  <li><em>Encountered exception</em>
      <blockquote>             
      <p>An exception was encountered trying to remove the web application.
      Check the Tomcat 4 logs for the details.</p>
      </blockquote></li>       
  <li><em>Invalid context path was specified</em>
      <blockquote>             
      <p>The context path must start with a slash character, unless you are
      referencing the ROOT web application -- in which case the context path
      must be a zero-length string.</p>
      </blockquote></li>       
  <li><em>No context exists for path /foo</em>
      <blockquote>             
      <p>There is no deployed or installed application on the context path
      that you specified.</p>  
      </blockquote></li>       
  <li><em>No context path was specified</em>
      <blockquote>             
      The <code>path</code> parameter is required.
      </blockquote></li>       
  </ul>
  </p>
  
  </subsection>
  
  </section>
  
  <section name="Install">
  
  <p>Web applications can be installed using files or directories located
  on the Tomcat server or you can upload a web application archive (WAR)
  file to the server.</p>
  
  <p>To install an application fill in the appropriate fields for the type
  of install you want to do and then submit it using the <i>Install</i>
  button.</p>
  
  <subsection name="Install directory or WAR file located on server">
  
  <p>Install and start a new web application, attached to the specified <i>Context
  Path:</i> (which must not be in use by any other web application).
  This command is the logical opposite of the <em>Remove</em> command.</p>
  
  <p>There are a number of different ways the install command can be used.</p>
  
  <h3>Install a Directory or WAR by URL</h3>
  
  <p>Install a web application directory or ".war" file located on the Tomcat
  server. If no <i>Context Path:</i> is specified the directory name or the
  war file name without the ".war" extension is used as the path. The
  <i>WAR or Directory URL:</i> specifies a URL (including the <code>file:</code>
  scheme) for either a directory or a web application archive (WAR) file. The
  supported syntax for a URL referring to a WAR file is described on the Javadocs
  page for the <code>java.net.JarURLConnection</code> class.  Use only URLs that
  refer to the entire WAR file.</p>
  
  <p>In this example the web application located in the directory
  <code>/path/to/foo</code> on the Tomcat server is installed as the
  web application context named <code>/footoo</code>.
  <source>
  Context Path: /footoo
  WAR or Directory URL: file:/path/to/foo
  </source>
  </p>
  
  <p>In this example the ".war" file <code>/path/to/bar.war</code> on the
  Tomcat server is installed as the web application context named
  <code>/bar</code>. Notice that there is no <code>path</code> parameter
  so the context path defaults to the name of the web application archive
  file without the ".war" extension.
  <source>
  WAR or Directory URL: jar:file:/path/to/bar.war!/
  </source>
  </p>
  
  <h3>Install a Directory or War from the Host appBase</h3>
  
  <p>Install a web application directory or ".war" file located in your Host
  appBase directory. If no <i>Context Path:</i> is specified the directory name
  or the war file name without the ".war" extension is used as the path.</p>
  
  <p>In this example the web application located in a sub directory named
  <code>foo</code> in the Host appBase directory of the Tomcat server is
  installed as the web application context named <code>/foo</code>. Notice
  that there is no <code>path</code> parameter so the context path defaults
  to the name of the web application directory.
  <source>
  WAR or Directory URL: foo
  </source>
  </p>
  
  <p>In this example the ".war" file <code>bar.war</code> located in your
  Host appBase directory on the Tomcat server is installed as the web
  application context named <code>/bartoo</code>.
  <source>
  Context Path: /bartoo
  WAR or Directory URL: bar.war
  </source>
  </p>
  
  <h3>Install using a Context configuration ".xml" file</h3>
  
  <p>If the Host deployXML flag is set to true you can install a web
  application using a Context configuration ".xml" file and an optional
  ".war" file or web application directory. The <i>Context Path:</i>
  is not used when installing a web application using a context ".xml"
  configuration file.</p>
  
  <p>A Context configuration ".xml" file can contain valid XML for a
  web application Context just as if it were configured in your
  Tomcat <code>server.xml</code> configuration file. Here is an
  example:
  <source>
  &lt;Context path="/foobar" docBase="/path/to/application/foobar"
           debug="0"&gt;
  
    &lt;!-- Link to the user database we will get roles from --&gt;
    &lt;ResourceLink name="users" global="UserDatabase"
                  type="org.apache.catalina.UserDatabase"/&gt;
  
  &lt;/Context&gt;
  </source>
  </p>
  
  <p>Use of the <i>WAR or Directory URL:</i> is optional. When used
  to select a web application ".war" file or directory it overrides any
  docBase configured in the context configuration ".xml" file.</p>
  
  <p>Here is an example of installing an application using a Context
  configuration ".xml" file.
  <source>
  XML Configuration file URL: file:/path/to/context.xml
  </source>
  </p>
  
  <p>Here is an example of installing an application using a Context
  configuration ".xml" file and a web application ".war" file located
  on the server.
  <source>
  XML Configuration file URL: file:/path/to/context.xml
  WAR or Directory URL: jar:file:/path/to/bar.war!/
  </source>
  </p>
  
  </subsection>
  
  <subsection name="Upload a WAR file to install">
  
  <p>Upload a WAR file from your local system and install it into the
  appBase for your Host. The name of the WAR file without the ".war"
  extension is used as the context path name.</p>
  
  <p>Use the <i>Browse</i> button to select a WAR file to upload to the
  server from your local desktop system.</p>
  
  <p>Upload of a WAR file could fail for the following reasons:</p>
  <ul>
  <li><em>File uploaded must be a .war</em>
      <blockquote>
      <p>The upload install will only accept files which have the filename
      extension of ".war".</p>
      </blockquote></li>
  <li><em>War file already exists on server</em>
      <blockquote>
      <p>If a war file of the same name already exists in your Host's
      appBase the upload will fail. Either remove the existing war file
      from your Host's appBase or upload the new war file using a different
      name.</p>
      </blockquote></li>
  <li><em>File upload failed, no file</em>
      <blockquote>
      <p>The file upload failed, no file was received by the server.</p>
      </blockquote></li>
  <li><em>Install Upload Failed, Exception:</em>
      <blockquote>
      <p>The war file upload or install failed with a Java Exception.
      The exception message will be listed.</p>
      </blockquote></li>
  </ul>
  
  </subsection>
  
  <subsection name="Installation Notes">
  
  <p>If the Host is configured with unpackWARs=true and you install a war
  file, the war will be unpacked into a directory in your Host appBase
  directory.</p>
  
  <p>If the application war or directory is installed in your Host appBase
  directory and either the Host is configured with autoDeploy=true or
  liveDeploy=true, the Context path must match the directory name or
  war file name without the ".war" extension.</p>
  
  <p>For security when untrusted users can manage web applications the
  Host deployXML flag can be set to false.  This prevents untrusted users
  from installing web applications using a configuration XML file and
  also prevents them from installing application directories or ".war"
  files located outside of their Host appBase.</p>
  
  </subsection>
  
  <subsection name="Install Message">
  
  <p>If installation and startup is successful, you will receive a Message
  like this:</p>
  <source>
  OK - Installed application at context path /foo
  </source>
  
  <p>Otherwise, the Message will start with <code>FAIL</code> and include an
  error message.  Possible causes for problems include:</p>
  <ul>
  <li><em>Application already exists at path /foo</em>
      <blockquote>
      <p>The context paths for all currently running web applications must be
      unique.  Therefore, you must either remove or undeploy the existing web
      application using this context path, or choose a different context path
      for the new one.</p>
      </blockquote></li>
  <li><em>Document base does not exist or is not a readable directory</em>
      <blockquote>
      <p>The URL specified by the <i>WAR or Directory URL:</i> field must
      identify a directory on this server that contains the "unpacked" version
      of a web application, or the absolute URL of a web application archive
      (WAR) file that contains this application.  Correct the value entered for
      the <i>WAR or Directory URL:</i> field.</p>
      </blockquote></li>
  <li><em>Encountered exception</em>
      <blockquote>
      <p>An exception was encountered trying to start the new web application.
      Check the Tomcat 4 logs for the details, but likely explanations include
      problems parsing your <code>/WEB-INF/web.xml</code> file, or missing
      classes encountered when initializing application event listeners and
      filters.</p>
      </blockquote></li>
  <li><em>Invalid application URL was specified</em>
      <blockquote>
      <p>The URL for the <i>WAR or Directory URL:</i> field that you specified
      was not valid.  Such URLs must start with <code>file:</code>, and URLs
      for a WAR file must end in ".war".</p>
      </blockquote></li>
  <li><em>Invalid context path was specified</em>
      <blockquote>
      <p>The context path must start with a slash character, unless you are
      referencing the ROOT web application -- in which case the context path
      must be a "/" string.</p>
      </blockquote></li>
  <li><em>Context path must match the directory or WAR file name:</em>
      <blockquote>
      If the application war or directory is installed in your Host appBase
      directory and either the Host is configured with autoDeploy=true or
      liveDeploy=true, the Context path must match the directory name or
      war file name without the ".war" extension.
      </blockquote></li>
  <li><em>Only web applications in the Host web application directory can
       be installed</em>
       <blockquote>
       If the Host deployXML flag is set to false this error will happen
       if an attempt is made to install a web application directory or
        ".war" file outside of the Host appBase directory.
       </blockquote></li>
  </ul>
  
  </subsection>
  </section>
  
  <section name="Server Information">
  
  <p>This section displays information about Tomcat, the operating system of
  the server Tomcat is hosted on, and the Java Virtual Machine Tomcat is
  running in.</p>
  
  </section>
  
  </body>
  
  </document>
  
  
  
  1.14      +7 -5      jakarta-tomcat-4.0/webapps/tomcat-docs/config/host.xml
  
  Index: host.xml
  ===================================================================
  RCS file: /home/cvs/jakarta-tomcat-4.0/webapps/tomcat-docs/config/host.xml,v
  retrieving revision 1.13
  retrieving revision 1.14
  diff -u -r1.13 -r1.14
  --- host.xml	2 Dec 2002 15:09:09 -0000	1.13
  +++ host.xml	10 Jan 2003 15:52:19 -0000	1.14
  @@ -117,11 +117,13 @@
   
         <attribute name="deployXML" required="false">
           <p>Set to <code>false</code> if you want to disable deploying
  -        applications using a Context XML config file. Applications are
  -        deployed with the security permissions of catalina, for security
  -        this may need to be set to <code>false</code> if untrusted users
  -        can manage web applications.  The flag's value defaults to
  -        <code>true</code>.</p>
  +        applications using a Context XML config file. This also disables
  +        the ability to install web application directories or ".war" files
  +        with the manager app which are not located in the Host appBase
  +        directory. Applications are deployed with the security permissions
  +        of catalina, for security this may need to be set to <code>false</code>
  +        if untrusted users can manage web applications.  The flag's value
  +        defaults to <code>true</code>.</p>
         </attribute>
   
         <attribute name="errorReportValveClass" required="false">
  
  
  

--
To unsubscribe, e-mail:   <mailto:tomcat-dev-unsubscribe@jakarta.apache.org>
For additional commands, e-mail: <mailto:tomcat-dev-help@jakarta.apache.org>


Mime
View raw message