diff --git a/webapps/ROOT/WEB-INF/web.xml b/webapps/ROOT/WEB-INF/web.xml new file mode 100644 index 000000000000..9540110aff20 --- /dev/null +++ b/webapps/ROOT/WEB-INF/web.xml @@ -0,0 +1,31 @@ + + + + + + Welcome to Tomcat + + Welcome to Tomcat + + + diff --git a/webapps/ROOT/asf-logo-wide.gif b/webapps/ROOT/asf-logo-wide.gif new file mode 100644 index 000000000000..b2403286d552 Binary files /dev/null and b/webapps/ROOT/asf-logo-wide.gif differ diff --git a/webapps/ROOT/build.xml b/webapps/ROOT/build.xml new file mode 100644 index 000000000000..bcb2c2d106d7 --- /dev/null +++ b/webapps/ROOT/build.xml @@ -0,0 +1,93 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/webapps/ROOT/favicon.ico b/webapps/ROOT/favicon.ico new file mode 100644 index 000000000000..6c5bd2c63b38 Binary files /dev/null and b/webapps/ROOT/favicon.ico differ diff --git a/webapps/ROOT/index.jsp b/webapps/ROOT/index.jsp new file mode 100644 index 000000000000..1841c681e109 --- /dev/null +++ b/webapps/ROOT/index.jsp @@ -0,0 +1,176 @@ + + + + + + Apache Tomcat + + + + + + + + +
+
+
+

Administration

+

Status

+

Tomcat Manager

+

Host Manager

+
+ + + +
+
+

If you're seeing this page via a web browser, it means you've setup Tomcat successfully. Congratulations!

+

Now join the Tomcat Announce mailing list, which is a low volume mailing list for releases, security vulnerabilities and other project announcements.

+ +

As you may have guessed by now, this is the default Tomcat home page. It can be found on the local filesystem at: + $CATALINA_HOME/webapps/ROOT/index.html

+

where "$CATALINA_HOME" is the root of the Tomcat installation directory. If you're seeing this page, and you don't think you should be, then you're either a user who has arrived at new installation of Tomcat, or you're an administrator who hasn't got his/her setup quite right. Providing the latter is the case, please refer to the Tomcat Documentation for more detailed setup and administration information than is found in the INSTALL file.

+

NOTE: For security reasons, using the manager webapp is restricted to users with role "manager-gui". + Users are defined in: $CATALINA_HOME/conf/tomcat-users.xml

+

Included with this release are a host of sample Servlets and JSPs (with associated source code), extensive documentation, and an introductory guide to developing web applications.

+

Tomcat mailing lists are available at the Tomcat project web site:

+ +

Thanks for using Tomcat!

+ +
+ +
+ + diff --git a/webapps/ROOT/tomcat-power.gif b/webapps/ROOT/tomcat-power.gif new file mode 100644 index 000000000000..c1a74049c974 Binary files /dev/null and b/webapps/ROOT/tomcat-power.gif differ diff --git a/webapps/ROOT/tomcat.gif b/webapps/ROOT/tomcat.gif new file mode 100644 index 000000000000..61756736b823 Binary files /dev/null and b/webapps/ROOT/tomcat.gif differ diff --git a/webapps/ROOT/tomcat.svg b/webapps/ROOT/tomcat.svg new file mode 100644 index 000000000000..cfa87dba9f27 --- /dev/null +++ b/webapps/ROOT/tomcat.svg @@ -0,0 +1,589 @@ + + + + + + + + + + + + + + +]> + + + + + + + + + + + + + + + + + + + + + + + 2006-05-09T08:17:21Z + 2006-05-09T08:37:38Z + Illustrator + + + + JPEG + 256 + 184 + /9j/4AAQSkZJRgABAgEASABIAAD/7QAsUGhvdG9zaG9wIDMuMAA4QklNA+0AAAAAABAASAAAAAEA AQBIAAAAAQAB/+4ADkFkb2JlAGTAAAAAAf/bAIQABgQEBAUEBgUFBgkGBQYJCwgGBggLDAoKCwoK DBAMDAwMDAwQDA4PEA8ODBMTFBQTExwbGxscHx8fHx8fHx8fHwEHBwcNDA0YEBAYGhURFRofHx8f Hx8fHx8fHx8fHx8fHx8fHx8fHx8fHx8fHx8fHx8fHx8fHx8fHx8fHx8fHx8f/8AAEQgAuAEAAwER AAIRAQMRAf/EAaIAAAAHAQEBAQEAAAAAAAAAAAQFAwIGAQAHCAkKCwEAAgIDAQEBAQEAAAAAAAAA AQACAwQFBgcICQoLEAACAQMDAgQCBgcDBAIGAnMBAgMRBAAFIRIxQVEGE2EicYEUMpGhBxWxQiPB UtHhMxZi8CRygvElQzRTkqKyY3PCNUQnk6OzNhdUZHTD0uIIJoMJChgZhJRFRqS0VtNVKBry4/PE 1OT0ZXWFlaW1xdXl9WZ2hpamtsbW5vY3R1dnd4eXp7fH1+f3OEhYaHiImKi4yNjo+Ck5SVlpeYmZ qbnJ2en5KjpKWmp6ipqqusra6voRAAICAQIDBQUEBQYECAMDbQEAAhEDBCESMUEFURNhIgZxgZEy obHwFMHR4SNCFVJicvEzJDRDghaSUyWiY7LCB3PSNeJEgxdUkwgJChgZJjZFGidkdFU38qOzwygp 0+PzhJSktMTU5PRldYWVpbXF1eX1RlZmdoaWprbG1ub2R1dnd4eXp7fH1+f3OEhYaHiImKi4yNjo +DlJWWl5iZmpucnZ6fkqOkpaanqKmqq6ytrq+v/aAAwDAQACEQMRAD8A9U4q7FXYq7FXYq7FXYq7 FXYq7FXYq7FXYq7FXYq7FXhH/OYHnWfQ/wAurfRLSUxXXmK49GQqaN9VtwJJqH3cxqfYnFXhP5Y/ 85O+f/JU0enaw769okbBJLS8ZvrUKg0IhnarDj/I9R2HHFX2F+Xn5neT/P8ApP6R8u3glKAfW7KS iXNuzdFljqaezCqnsTirK8VdirsVdirsVdirsVdirC/zM/Nvyd+XemC71255Xcqk2WmQUa5nI2+F CRxUd3ag+nbFXx1+Zf8Azkn+YvneaW1tLh9C0NgwXTrB2V3Sm/rzji8m3UDitP2cVfV//OOfmabz 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 + + + + + + + image/svg+xml + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + 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 +/Dn4G1vgFa2715u9zrn+L1T7Dxc= + + + diff --git a/webapps/docs/META-INF/context.xml b/webapps/docs/META-INF/context.xml new file mode 100644 index 000000000000..28ae2ddce02d --- /dev/null +++ b/webapps/docs/META-INF/context.xml @@ -0,0 +1,18 @@ + + + diff --git a/webapps/docs/WEB-INF/web.xml b/webapps/docs/WEB-INF/web.xml new file mode 100644 index 000000000000..d57b326cff56 --- /dev/null +++ b/webapps/docs/WEB-INF/web.xml @@ -0,0 +1,29 @@ + + + + + Tomcat Documentation + + Tomcat Documentation. + + diff --git a/webapps/docs/aio.xml b/webapps/docs/aio.xml new file mode 100644 index 000000000000..cc0a4ea68efc --- /dev/null +++ b/webapps/docs/aio.xml @@ -0,0 +1,352 @@ + + + +]> + + + &project; + + + Advanced IO and Tomcat + Remy Maucherat + + + + +
+ +
+ +
+ +

+ With usage of APR or NIO APIs as the basis of its connectors, Tomcat is + able to provide a number of extensions over the regular blocking IO + as provided with support for the Servlet API. +

+ +

+ IMPORTANT NOTE: Usage of these features requires using the APR or NIO + HTTP connectors. The classic java.io HTTP connector and the AJP connectors + do not support them. +

+ +
+ +
+ +

+ Comet support allows a servlet to process IO asynchronously, receiving + events when data is available for reading on the connection (rather than + always using a blocking read), and writing data back on connections + asynchronously (most likely responding to some event raised from some + other source). +

+ + + +

+ Servlets which implement the org.apache.catalina.comet.CometProcessor + interface will have their event method invoked rather than the usual service + method, according to the event which occurred. The event object gives + access to the usual request and response objects, which may be used in the + usual way. The main difference is that those objects remain valid and fully + functional at any time between processing of the BEGIN event until processing + an END or ERROR event. + The following event types exist: +

+ +
    +
  • EventType.BEGIN: will be called at the beginning + of the processing of the connection. It can be used to initialize any relevant + fields using the request and response objects. Between the end of the processing + of this event, and the beginning of the processing of the end or error events, + it is possible to use the response object to write data on the open connection. + Note that the response object and dependent OutputStream and Writer are still + not synchronized, so when they are accessed by multiple threads, + synchronization is mandatory. After processing the initial event, the request + is considered to be committed.
  • +
  • EventType.READ: This indicates that input data is available, and that one read can be made + without blocking. The available and ready methods of the InputStream or + Reader may be used to determine if there is a risk of blocking: the servlet + should read while data is reported available, and can make one additional read + should read while data is reported available. When encountering a read error, + the servlet should report it by propagating the exception properly. Throwing + an exception will cause the error event to be invoked, and the connection + will be closed. + Alternately, it is also possible to catch any exception, perform clean up + on any data structure the servlet may be using, and using the close method + of the event. It is not allowed to attempt reading data from the request + object outside of the execution of this method.
    + On some platforms, like Windows, a client disconnect is indicated by a READ event. + Reading from the stream may result in -1, an IOException or an EOFException. + Make sure you properly handle all these three cases. + If you don't catch the IOException, Tomcat will instantly invoke your event chain with an ERROR as + it catches the error for you, and you will be notified of the error at that time. +
  • +
  • EventType.END: End may be called to end the processing of the request. Fields that have + been initialized in the begin method should be reset. After this event has + been processed, the request and response objects, as well as all their dependent + objects will be recycled and used to process other requests. End will also be + called when data is available and the end of file is reached on the request input + (this usually indicates the client has pipelined a request).
  • +
  • EventType.ERROR: Error will be called by the container in the case where an IO exception + or a similar unrecoverable error occurs on the connection. Fields that have + been initialized in the begin method should be reset. After this event has + been processed, the request and response objects, as well as all their dependent + objects will be recycled and used to process other requests.
  • +
+ +

+ There are some event subtypes which allow finer processing of events (note: some of these + events require usage of the org.apache.catalina.valves.CometConnectionManagerValve valve): +

+ +
    +
  • EventSubType.TIMEOUT: The connection timed out (sub type of ERROR); note that this ERROR + type is not fatal, and the connection will not be closed unless the servlet uses the close + method of the event. +
  • +
  • EventSubType.CLIENT_DISCONNECT: The client connection was closed (sub type of ERROR). + method of the event. +
  • +
  • EventSubType.IOEXCEPTION: An IO exception occurred, such as invalid content, for example, + an invalid chunk block (sub type of ERROR). +
  • +
  • EventSubType.WEBAPP_RELOAD: The web application is being reloaded (sub type of END). +
  • +
  • EventSubType.SESSION_END: The servlet ended the session (sub type of END). +
  • +
+ +

+ As described above, the typical lifecycle of a Comet request will consist in a series of + events such as: BEGIN -> READ -> READ -> READ -> ERROR/TIMEOUT. At any time, the servlet + may end processing of the request by using the close method of the event object. +

+ +
+ + + +

+ Similar to regular filters, a filter chain is invoked when comet events are processed. + These filters should implement the CometFilter interface (which works in the same way as + the regular Filter interface), and should be declared and mapped in the deployment + descriptor in the same way as a regular filter. The filter chain when processing an event + will only include filters which match all the usual mapping rules, and also implement + the CometFiler interface. +

+ +
+ + + +

+ The following pseudo code servlet implements asynchronous chat functionality using the API + described above: +

+ + +public class ChatServlet + extends HttpServlet implements CometProcessor { + + protected ArrayList<HttpServletResponse> connections = + new ArrayList<HttpServletResponse>(); + protected MessageSender messageSender = null; + + public void init() throws ServletException { + messageSender = new MessageSender(); + Thread messageSenderThread = + new Thread(messageSender, "MessageSender[" + getServletContext().getContextPath() + "]"); + messageSenderThread.setDaemon(true); + messageSenderThread.start(); + } + + public void destroy() { + connections.clear(); + messageSender.stop(); + messageSender = null; + } + + /** + * Process the given Comet event. + * + * @param event The Comet event that will be processed + * @throws IOException + * @throws ServletException + */ + public void event(CometEvent event) + throws IOException, ServletException { + HttpServletRequest request = event.getHttpServletRequest(); + HttpServletResponse response = event.getHttpServletResponse(); + if (event.getEventType() == CometEvent.EventType.BEGIN) { + log("Begin for session: " + request.getSession(true).getId()); + PrintWriter writer = response.getWriter(); + writer.println("<!doctype html public \"-//w3c//dtd html 4.0 transitional//en\">"); + writer.println("<head><title>JSP Chat</title></head><body bgcolor=\"#FFFFFF\">"); + writer.flush(); + synchronized(connections) { + connections.add(response); + } + } else if (event.getEventType() == CometEvent.EventType.ERROR) { + log("Error for session: " + request.getSession(true).getId()); + synchronized(connections) { + connections.remove(response); + } + event.close(); + } else if (event.getEventType() == CometEvent.EventType.END) { + log("End for session: " + request.getSession(true).getId()); + synchronized(connections) { + connections.remove(response); + } + PrintWriter writer = response.getWriter(); + writer.println("</body></html>"); + event.close(); + } else if (event.getEventType() == CometEvent.EventType.READ) { + InputStream is = request.getInputStream(); + byte[] buf = new byte[512]; + do { + int n = is.read(buf); //can throw an IOException + if (n > 0) { + log("Read " + n + " bytes: " + new String(buf, 0, n) + + " for session: " + request.getSession(true).getId()); + } else if (n < 0) { + error(event, request, response); + return; + } + } while (is.available() > 0); + } + } + + public class MessageSender implements Runnable { + + protected boolean running = true; + protected ArrayList<String> messages = new ArrayList<String>(); + + public MessageSender() { + } + + public void stop() { + running = false; + } + + /** + * Add message for sending. + */ + public void send(String user, String message) { + synchronized (messages) { + messages.add("[" + user + "]: " + message); + messages.notify(); + } + } + + public void run() { + + while (running) { + + if (messages.size() == 0) { + try { + synchronized (messages) { + messages.wait(); + } + } catch (InterruptedException e) { + // Ignore + } + } + + synchronized (connections) { + String[] pendingMessages = null; + synchronized (messages) { + pendingMessages = messages.toArray(new String[0]); + messages.clear(); + } + // Send any pending message on all the open connections + for (int i = 0; i < connections.size(); i++) { + try { + PrintWriter writer = connections.get(i).getWriter(); + for (int j = 0; j < pendingMessages.length; j++) { + writer.println(pendingMessages[j] + "<br>"); + } + writer.flush(); + } catch (IOException e) { + log("IOExeption sending message", e); + } + } + } + + } + + } + + } + +} + + +
+ +

If you are using the NIO connector, you can set individual timeouts for your different comet connections. + To set a timeout, simply set a request attribute like the following code shows: + CometEvent event.... event.setTimeout(30*1000); or + event.getHttpServletRequest().setAttribute("org.apache.tomcat.comet.timeout", new Integer(30 * 1000)); + This sets the timeout to 30 seconds. + Important note, in order to set this timeout, it has to be done on the BEGIN event. + The default value is soTimeout +

+

If you are using the APR connector, all Comet connections will have the same timeout value. It is soTimeout*50 +

+
+ +
+ +
+ +

+ When APR or NIO is enabled, Tomcat supports using sendfile to send large static files. + These writes, as soon as the system load increases, will be performed + asynchronously in the most efficient way. Instead of sending a large response using + blocking writes, it is possible to write content to a static file, and write it + using a sendfile code. A caching valve could take advantage of this to cache the + response data in a file rather than store it in memory. Sendfile support is + available if the request attribute org.apache.tomcat.sendfile.support + is set to Boolean.TRUE. +

+ +

+ Any servlet can instruct Tomcat to perform a sendfile call by setting the appropriate + request attributes. It is also necessary to correctly set the content length + for the response. When using sendfile, it is best to ensure that neither the + request or response have been wrapped, since as the response body will be sent later + by the connector itself, it cannot be filtered. Other than setting the 3 needed + request attributes, the servlet should not send any response data, but it may use + any method which will result in modifying the response header (like setting cookies). +

+ +
    +
  • org.apache.tomcat.sendfile.filename: Canonical filename of the file which will be sent as + a String
  • +
  • org.apache.tomcat.sendfile.start: Start offset as a Long
  • +
  • org.apache.tomcat.sendfile.end: End offset as a Long
  • +
+ +
+ + +
diff --git a/webapps/docs/api/index.html b/webapps/docs/api/index.html new file mode 100644 index 000000000000..9c125b917042 --- /dev/null +++ b/webapps/docs/api/index.html @@ -0,0 +1,34 @@ + + + + + + API docs + + + + +Tomcat's internal javadoc is not installed by default. Download and install +the "fulldocs" package to get it. + +You can also access the javadoc online in the Tomcat + +documentation bundle. + + + diff --git a/webapps/docs/appdev/build.xml.txt b/webapps/docs/appdev/build.xml.txt new file mode 100644 index 000000000000..d074939a07f6 --- /dev/null +++ b/webapps/docs/appdev/build.xml.txt @@ -0,0 +1,514 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/webapps/docs/appdev/deployment.xml b/webapps/docs/appdev/deployment.xml new file mode 100644 index 000000000000..a11d0870fb7d --- /dev/null +++ b/webapps/docs/appdev/deployment.xml @@ -0,0 +1,253 @@ + + + +]> + + + &project; + + + Craig R. McClanahan + Deployment + + + + +
+ +
+ +
+ +

Before describing how to organize your source code directories, +it is useful to examine the runtime organization of a web application. +Prior to the Servlet API Specification, version 2.2, there was little +consistency between server platforms. However, servers that conform +to the 2.2 (or later) specification are required to accept a +Web Application Archive in a standard format, which is discussed +further below.

+ +

A web application is defined as a hierarchy of directories and files +in a standard layout. Such a hierarchy can be accessed in its "unpacked" +form, where each directory and file exists in the filesystem separately, +or in a "packed" form known as a Web ARchive, or WAR file. The former format +is more useful during development, while the latter is used when you +distribute your application to be installed.

+ +

The top-level directory of your web application hierarchy is also the +document root of your application. Here, you will place the HTML +files and JSP pages that comprise your application's user interface. When the +system administrator deploys your application into a particular server, he +or she assigns a context path to your application (a later section +of this manual describes deployment on Tomcat). Thus, if the +system administrator assigns your application to the context path +/catalog, then a request URI referring to +/catalog/index.html will retrieve the index.html +file from your document root.

+ +
+ + +
+ +

To facilitate creation of a Web Application Archive file in the required +format, it is convenient to arrange the "executable" files of your web +application (that is, the files that Tomcat actually uses when executing +your app) in the same organization as required by the WAR format itself. +To do this, you will end up with the following contents in your +application's "document root" directory:

+
    +
  • *.html, *.jsp, etc. - The HTML and JSP pages, along + with other files that must be visible to the client browser (such as + JavaScript, stylesheet files, and images) for your application. + In larger applications you may choose to divide these files into + a subdirectory hierarchy, but for smaller apps, it is generally + much simpler to maintain only a single directory for these files. +

  • +
  • /WEB-INF/web.xml - The Web Application Deployment + Descriptor for your application. This is an XML file describing + the servlets and other components that make up your application, + along with any initialization parameters and container-managed + security constraints that you want the server to enforce for you. + This file is discussed in more detail in the following subsection. +

  • +
  • /WEB-INF/classes/ - This directory contains any Java + class files (and associated resources) required for your application, + including both servlet and non-servlet classes, that are not combined + into JAR files. If your classes are organized into Java packages, + you must reflect this in the directory hierarchy under + /WEB-INF/classes/. For example, a Java class named + com.mycompany.mypackage.MyServlet + would need to be stored in a file named + /WEB-INF/classes/com/mycompany/mypackage/MyServlet.class. +

  • +
  • /WEB-INF/lib/ - This directory contains JAR files that + contain Java class files (and associated resources) required for your + application, such as third party class libraries or JDBC drivers.
  • +
+ +

When you install an application into Tomcat (or any other +2.2/2.3-compatible server), the classes in the WEB-INF/classes/ +directory, as well as all classes in JAR files found in the +WEB-INF/lib/ directory, are made visible to other classes +within your particular web application. Thus, if +you include all of the required library classes in one of these places (be +sure to check licenses for redistribution rights for any third party libraries +you utilize), you will simplify the installation of your web application -- +no adjustment to the system class path (or installation of global library +files in your server) will be necessary.

+ +

Much of this information was extracted from Chapter 9 of the Servlet +API Specification, version 2.3, which you should consult for more details.

+ +
+ + +
+ +

Like most servlet containers, Tomcat also supports mechanisms to install +library JAR files (or unpacked classes) once, and make them visible to all +installed web applications (without having to be included inside the web +application itself. The details of how Tomcat locates and shares such +classes are described in the +Class Loader HOW-TO documentation. +The location commonly used within a Tomcat installation for shared code is +$CATALINA_HOME/lib. JAR files placed here are visible both to +web applications and internal Tomcat code. This is a good place to put JDBC +drivers that are required for both your application or internal Tomcat use +(such as for a JDBCRealm).

+ +

Out of the box, a standard Tomcat installation includes a variety +of pre-installed shared library files, including:

+
    +
  • The Servlet 3.0 and JSP 2.1 APIs that are fundamental + to writing servlets and JavaServer Pages.

  • +
  • An XML Parser compliant with the JAXP (version 1.2) APIs, so + your application can perform DOM-based or SAX-based processing of + XML documents.

  • +
+ +
+ + +
+ +

As mentioned above, the /WEB-INF/web.xml file contains the +Web Application Deployment Descriptor for your application. As the filename +extension implies, this file is an XML document, and defines everything about +your application that a server needs to know (except the context path, +which is assigned by the system administrator when the application is +deployed).

+ +

The complete syntax and semantics for the deployment descriptor is defined +in Chapter 13 of the Servlet API Specification, version 2.3. Over time, it +is expected that development tools will be provided that create and edit the +deployment descriptor for you. In the meantime, to provide a starting point, +a basic web.xml file +is provided. This file includes comments that describe the purpose of each +included element.

+ +

NOTE - The Servlet Specification includes a Document +Type Descriptor (DTD) for the web application deployment descriptor, and +Tomcat enforces the rules defined here when processing your application's +/WEB-INF/web.xml file. In particular, you must +enter your descriptor elements (such as <filter>, +<servlet>, and <servlet-mapping> in +the order defined by the DTD (see Section 13.3).

+ +
+ + +
+ +

A /META-INF/context.xml file can be used to define Tomcat specific +configuration options, such as loggers, data sources, session manager +configuration and more. This XML file must contain one Context element, which +will be considered as if it was the child of the Host element corresponding +to the Host to which the The Tomcat configuration documentation contains +information on the Context element.

+ +
+ + +
+ +
+

The description below uses the variable name $CATALINA_BASE to refer the + base directory against which most relative paths are resolved. If you have + not configured Tomcat for multiple instances by setting a CATALINA_BASE + directory, then $CATALINA_BASE will be set to the value of $CATALINA_HOME, + the directory into which you have installed Tomcat.

+
+ +

In order to be executed, a web application must be deployed on +a servlet container. This is true even during development. +We will describe using Tomcat to provide the execution environment. +A web application can be deployed in Tomcat by one of the following +approaches:

+
    +
  • Copy unpacked directory hierarchy into a subdirectory in directory + $CATALINA_BASE/webapps/. Tomcat will assign a + context path to your application based on the subdirectory name you + choose. We will use this technique in the build.xml + file that we construct, because it is the quickest and easiest approach + during development. Be sure to restart Tomcat after installing or + updating your application. +

  • +
  • Copy the web application archive file into directory + $CATALINA_BASE/webapps/. When Tomcat is started, it will + automatically expand the web application archive file into its unpacked + form, and execute the application that way. This approach would typically + be used to install an additional application, provided by a third party + vendor or by your internal development staff, into an existing + Tomcat installation. NOTE - If you use this approach, + and wish to update your application later, you must both replace the + web application archive file AND delete the expanded + directory that Tomcat created, and then restart Tomcat, in order to reflect + your changes. +

  • +
  • Use the Tomcat "Manager" web application to deploy and undeploy + web applications. Tomcat includes a web application, deployed + by default on context path /manager, that allows you to + deploy and undeploy applications on a running Tomcat server without + restarting it. See the administrator documentation (TODO: hyperlink) + for more information on using the Manager web application.

  • +
  • Use "Manager" Ant Tasks In Your Build Script. Tomcat + includes a set of custom task definitions for the Ant + build tool that allow you to automate the execution of commands to the + "Manager" web application. These tasks are used in the Tomcat deployer. +

  • +
  • Use the Tomcat Deployer. Tomcat includes a packaged tool + bundling the Ant tasks, and can be used to automatically precompile JSPs + which are part of the web application before deployment to the server. +

  • +
+ +

Deploying your app on other servlet containers will be specific to each +container, but all containers compatible with the Servlet API Specification +(version 2.2 or later) are required to accept a web application archive file. +Note that other containers are NOT required to accept an +unpacked directory structure (as Tomcat does), or to provide mechanisms for +shared library files, but these features are commonly available.

+ +
+ + + +
diff --git a/webapps/docs/appdev/index.xml b/webapps/docs/appdev/index.xml new file mode 100644 index 000000000000..c1456cb1548f --- /dev/null +++ b/webapps/docs/appdev/index.xml @@ -0,0 +1,79 @@ + + + +]> + + + &project; + + + Craig R. McClanahan + Table of Contents + + + + + +
+ +

This manual includes contributions from many members of the Tomcat Project +developer community. The following authors have provided significant content: +

+ + +
+ + +
+ +

The information presented is divided into the following sections:

+
    +
  • Introduction - + Briefly describes the information covered here, with + links and references to other sources of information.
  • +
  • Installation - + Covers acquiring and installing the required software + components to use Tomcat for web application development.
  • +
  • Deployment Organization - + Discusses the standard directory layout for a web application + (defined in the Servlet API Specification), the Web Application + Deployment Descriptor, and options for integration with Tomcat + in your development environment.
  • +
  • Source Organization - + Describes a useful approach to organizing the source code + directories for your project, and introduces the + build.xml used by Ant to manage compilation.
  • +
  • Development Processes - + Provides brief descriptions of typical development processes + utilizing the recommended deployment and source organizations.
  • +
  • Example Application - + This directory contains a very simple, but functionally complete, + "Hello, World" application built according to the principles + described in this manual. You can use this application to + practice using the described techniques.
  • +
+ +
+ + + +
diff --git a/webapps/docs/appdev/installation.xml b/webapps/docs/appdev/installation.xml new file mode 100644 index 000000000000..206745caed6f --- /dev/null +++ b/webapps/docs/appdev/installation.xml @@ -0,0 +1,105 @@ + + + +]> + + + &project; + + + Craig R. McClanahan + Yoav Shapira + Installation + + + + + +
+ +

In order to use Tomcat for developing web applications, you must first +install it (and the software it depends on). The required steps are outlined +in the following subsections.

+ + + +

Tomcat 7.0 was designed to run on J2SE 6.0. +

+ +

Compatible JDKs for many platforms (or links to where they can be found) +are available at +http://www.oracle.com/technetwork/java/javase/downloads/index.html/.

+ +
+ + + +

Binary downloads of the Tomcat server are available from +http://tomcat.apache.org/download-60.cgi. +This manual assumes you are using the most recent release +of Tomcat 7. Detailed instructions for downloading and installing +Tomcat are available here.

+ +

In the remainder of this manual, example shell scripts assume that you have +set an environment variable CATALINA_HOME that contains the +pathname to the directory in which Tomcat has been installed. Optionally, if +Tomcat has been configured for multiple instances, each instance will have its +own CATALINA_BASE configured.

+ +
+ + + + +

Binary downloads of the Ant build tool are available from +http://ant.apache.org/bindownload.cgi. +This manual assumes you are using Ant 1.4 or later. The instructions should +also be compatible with later versions, but this has not been tested.

+ +

Download and install Ant from the distribution directory mentioned above. +Then, add the bin directory of the Ant distribution to your +PATH environment variable, following the standard practices for +your operating system platform. Once you have done this, you will be able to +execute the ant shell command directly.

+ +
+ + + + +

Besides the required tools described above, you are strongly encouraged +to download and install a source code control system, such as the +Concurrent Version System (CVS), to maintain historical +versions of the source files that make up your web application. Besides +the server, you will also need appropriate client +tools to check out source code files, and check in modified versions.

+ +

Detailed instructions for installing and using source code control +applications is beyond the scope of this manual. However, CVS server and +client tools for many platforms (along with documentation) can be downloaded +from http://www.cvshome.org.

+ +
+ + +
+ + + +
diff --git a/webapps/docs/appdev/introduction.xml b/webapps/docs/appdev/introduction.xml new file mode 100644 index 000000000000..0048d6147dd0 --- /dev/null +++ b/webapps/docs/appdev/introduction.xml @@ -0,0 +1,100 @@ + + + +]> + + + &project; + + + Craig R. McClanahan + Introduction + + + + + +
+ +

Congratulations! You've decided to (or been told to) learn how to +build web applications using servlets and JSP pages, and picked the +Tomcat server to use for your learning and development. But now what +do you do?

+ +

This manual is a primer covering the basic steps of using Tomcat to +set up a development environment, organize your source code, and then +build and test your application. It does not discuss architectures or +recommended coding practices for web application development, +or provide in depth instructions on operating the development +tools that are discussed. References to sources of additional information +are included in the following subsections.

+ +

The discussion in this manual is aimed at developers who will be using +a text editor along with command line tools to develop and debug their +applications. As such, the recommendations are fairly generic -- but you +should easily be able to apply them in either a Windows-based or Unix-based +development environment. If you are utilizing an Interactive Development +Environment (IDE) tool, you will need to adapt the advice given here to +the details of your particular environment.

+ +
+ + +
+ +

The following links provide access to selected sources of online +information, documentation, and software that is useful in developing +web applications with Tomcat.

+
    +
  • http://java.sun.com/products/jsp/ - + JavaServer Pages (JSP) Specification, Version 2.0. Describes + the programming environment provided by standard implementations + of the JavaServer Pages (JSP) technology. In conjunction with + the Servlet API Specification (see below), this document describes + what a portable API page is allowed to contain. Specific + information on scripting (Chapter 6), tag extensions (Chapter 7), + and packaging JSP pages (Appendix A) is useful. The Javadoc + API Documentation is included in the specification, and with the + Tomcat download.

  • +
  • http://java.sun.com/products/servlet/download.html - + Servlet API Specification, Version 3.0. Describes the + programming environment that must be provided by all servlet + containers conforming to this specification. In particular, you + will need this document to understand the web application + directory structure and deployment file (Chapter 9), methods of + mapping request URIs to servlets (Chapter 11), container managed + security (Chapter 12), and the syntax of the web.xml + Web Application Deployment Descriptor (Chapter 13). The Javadoc + API Documentation is included in the specification, and with the + Tomcat download.

  • +
  • http://java.sun.com/j2ee/blueprints/ - + Sun BluePrints (tm) Design Guidelines for J2EE. Comprehensive + advice and examples on application design for the Java2 Enterprise + Edition (J2EE) platform, which includes servlets and JSP pages. The + chapters on servlet and JSP design are useful even when your application + does not require other J2EE platform components. +

  • +
  • TODO -- Add more entries here!
  • +
+ +
+ + + +
diff --git a/webapps/docs/appdev/processes.xml b/webapps/docs/appdev/processes.xml new file mode 100644 index 000000000000..4c4cd4edc94a --- /dev/null +++ b/webapps/docs/appdev/processes.xml @@ -0,0 +1,318 @@ + + + +]> + + + &project; + + + Craig R. McClanahan + Development Processes + + + + +
+ +
+ +
+ +

Although application development can take many forms, this manual proposes +a fairly generic process for creating web applications using Tomcat. The +following sections highlight the commands and tasks that you, as the developer +of the code, will perform. The same basic approach works when you have +multiple programmers involved, as long as you have an appropriate source code +control system and internal team rules about who is working on what parts +of the application at any given time.

+ +

The task descriptions below assume that you will be using CVS for source +code control, and that you have already configured access to the appropriate +CVS repository. Instructions for doing this are beyond the scope of this +manual. If you are using a different source code control environment, you +will need to figure out the corresponding commands for your system.

+ + + + +

In order to take advantage of the special Ant tasks that interact with the +Manager web application, you need to perform the following tasks +once (no matter how many web applications you plan to develop).

+
    +
  • Configure the Ant custom tasks. The implementation code for the + Ant custom tasks is in a JAR file named + $CATALINA_HOME/lib/catalina-ant.jar, which must be + copied in to the lib directory of your Ant installation. +

  • +
  • Define one or more Tomcat users. The Manager web + application runs under a security constraint that requires a user to be + logged in, and have the security role manager assigned to + him or her. How such users are defined depends on which Realm you have + configured in Tomcat's conf/server.xml file -- see the + Realm Configuration HOW-TO for more + information. You may define any number of users (with any username + and password that you like) with the manager role. +

  • +
+ +
+ + + + +

The first step is to create a new project source directory, and customize +the build.xml and build.properties files you will +be using. The directory structure is described in the +previous section, or you can use the +sample application as a starting point.

+ +

Create your project source directory, and define it within your CVS +repository. This might be done by a series of commands like this, where +{project} is the name under which your project should be +stored in the CVS repository, and {username} is your login username:

+ +cd {my home directory} +mkdir myapp <-- Assumed "project source directory" +cd myapp +mkdir docs +mkdir src +mkdir web +mkdir web/WEB-INF +cvs import -m "Initial Project Creation" {project} \ + {username} start + + +

Now, to verify that it was created correctly in CVS, we will perform a +checkout of the new project:

+ +cd .. +mv myapp myapp.bu +cvs checkout {project} + + +

Next, you will need to create and check in an initial version of the +build.xml script to be used for development. For getting +started quickly and easily, base your build.xml on the +basic build.xml file, included with this manual, +or code it from scratch.

+ +cd {my home directory} +cd myapp +emacs build.xml <-- if you want a real editor :-) +cvs add build.xml +cvs commit + + +

Until you perform the CVS commit, your changes are local to your own +development directory. Committing makes those changes visible to other +developers on your team that are sharing the same CVS repository.

+ +

The next step is to customize the Ant properties that are +named in the build.xml script. This is done by creating a +file named build.properties in your project's top-level +directory. The supported properties are listed in the comments inside +the sample build.xml script. At a minimum, you will generally +need to define the catalina.home property defining where +Tomcat is installed, and the manager application username and password. +You might end up with something like this:

+ +# Context path to install this application on +app.path=/hello + +# Tomcat 7 installation directory +catalina.home=/usr/local/apache-tomcat-7.0 + +# Manager webapp username and password +manager.username=myusername +manager.password=mypassword + + +

In general, you will not want to check the +build.properties file in to the CVS repository, because it +is unique to each developer's environment.

+ +

Now, create the initial version of the web application deployment +descriptor. You can base web.xml on the +basic web.xml file, or code it from scratch.

+ +cd {my home directory} +cd myapp/web/WEB-INF +emacs web.xml +cvs add web.xml +cvs commit + + +Note that this is only an example web.xml file. The full definition +of the deployment descriptor file is in the +Servlet Specification. + +
+ + + + +

The edit/build/test tasks will generally be your most common activities +during development and maintenance. The following general principles apply. +As described in Source Organization, newly created +source files should be located in the appropriate subdirectory, under your +project source directory.

+ +

Whenever you wish to refresh your development directory to reflect the +work performed by other developers, you will ask CVS to do it for you:

+ +cd {my home directory} +cd myapp +cvs update -dP + + +

To create a new file, go to the appropriate directory, create the file, +and register it with CVS. When you are satisfied with it's contents (after +building and testing is successful), commit the new file to the repository. +For example, to create a new JSP page:

+ +cd {my home directory} +cd myapp/web <-- Ultimate destination is document root +emacs mypage.jsp +cvs add mypage.jsp +... build and test the application ... +cvs commit + + +

Java source code that is defined in packages must be organized in a +directory hierarchy (under the src/ subdirectory) that +matches the package names. For example, a Java class named +com.mycompany.mypackage.MyClass.java should be stored in file +src/com/mycompany/mypackage/MyClass.java. +Whenever you create a new subdirectory, don't forget to +register it with CVS.

+ +

To edit an existing source file, you will generally just start editing +and testing, then commit the changed file when everything works. Although +CVS can be configured to required you to "check out" or "lock" a file you +are going to be modifying, this is generally not used.

+ +
+ + + + +

When you are ready to compile the application, issue the following +commands (generally, you will want a shell window open that is set to +the project source directory, so that only the last command is needed):

+ +cd {my home directory} +cd myapp <-- Normally leave a window open here +ant + + +

The Ant tool will be execute the default "compile" target in your +build.xml file, which will compile any new or updated Java +code. If this is the first time you compile after a "build clean", +it will cause everything to be recompiled.

+ +

To force the recompilation of your entire application, do this instead:

+ +cd {my home directory} +cd myapp +ant all + + +

This is a very good habit immediately before checking in changes, to +make sure that you have not introduced any subtle problems that Javac's +conditional checking did not catch.

+ +
+ + + + +

To test your application, you will want to install it under Tomcat. The +quickest way to do that is to use the custom Ant tasks that are included in +the sample build.xml script. Using these commands might follow +a pattern like this:

+
    +
  • Start Tomcat if needed. If Tomcat is not already running, + you will need to start it in the usual way. +

  • +
  • Compile your application. Use the ant compile + command (or just ant, since this is the default). Make + sure that there are no compilation errors. +

  • +
  • Install the application. Use the ant install + command. This tells Tomcat to immediately start running your app on + the context path defined in the app.path build property. + Tomcat does NOT have to be restarted for this to + take effect.

  • +
  • Test the application. Using your browser or other testing + tools, test the functionality of your application. +

  • +
  • Modify and rebuild as needed. As you discover that changes + are required, make those changes in the original source + files, not in the output build directory, and re-issue the + ant compile command. This ensures that your changes will + be available to be saved (via cvs commit) later on -- + the output build directory is deleted and recreated as necessary. +

  • +
  • Reload the application. Tomcat will recognize changes in + JSP pages automatically, but it will continue to use the old versions + of any servlet or JavaBean classes until the application is reloaded. + You can trigger this by executing the ant reload command. +

  • +
  • Remove the application when you re done. When you are through + working on this application, you can remove it from live execution by + running the ant remove command.
  • +
+ +

Do not forget to commit your changes to the source code repository when +you have completed your testing!

+ +
+ + + + +

When you are through adding new functionality, and you've tested everything +(you DO test, don't you :-), it is time to create the distributable version +of your web application that can be deployed on the production server. The +following general steps are required:

+
    +
  • Issue the command ant all from the project source + directory, to rebuild everything from scratch one last time. +

  • +
  • Use the cvs tag command to create an identifier for + all of the source files utilized to create this release. This allows + you to reliably reconstruct a release (from sources) at a later + time.
  • +
  • Issue the command ant dist to create a distributable + web application archive (WAR) file, as well as a JAR file containing + the corresponding source code. +

  • +
  • Package the contents of the dist directory using the + tar or zip utility, according to + the standard release procedures used by your organization.
  • +
+ +
+ + +
+ + +
diff --git a/webapps/docs/appdev/project.xml b/webapps/docs/appdev/project.xml new file mode 100644 index 000000000000..cf9c20d7f1c6 --- /dev/null +++ b/webapps/docs/appdev/project.xml @@ -0,0 +1,45 @@ + + + + + Application Developer's Guide + + + The Apache Tomcat Servlet/JSP Container + + + + + + + + + + + + + + + + + + + + + diff --git a/webapps/docs/appdev/sample/docs/README.txt b/webapps/docs/appdev/sample/docs/README.txt new file mode 100644 index 000000000000..f146b0e0702f --- /dev/null +++ b/webapps/docs/appdev/sample/docs/README.txt @@ -0,0 +1,17 @@ + Licensed to the Apache Software Foundation (ASF) under one or more + contributor license agreements. See the NOTICE file distributed with + this work for additional information regarding copyright ownership. + The ASF licenses this file to You under the Apache License, Version 2.0 + (the "License"); you may not use this file except in compliance with + the License. You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + + Unless required by applicable law or agreed to in writing, software + distributed under the License is distributed on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + See the License for the specific language governing permissions and + limitations under the License. + +This is a dummy README file for the sample +web application. diff --git a/webapps/docs/appdev/sample/index.html b/webapps/docs/appdev/sample/index.html new file mode 100644 index 000000000000..294b8f9d81d4 --- /dev/null +++ b/webapps/docs/appdev/sample/index.html @@ -0,0 +1,46 @@ + + + + +Sample Application + + +

Sample Application

+

+ The example app has been packaged as a war file and can be downloaded + here (Note: make sure your browser doesn't + change file extension or append a new one). +

+

+ The easiest way to run this application is simply to move the war file + to your CATALINA_HOME/webapps directory. Tomcat will automatically + expand and deploy the application for you. You can view it with the + following URL (assuming that you're running tomcat on port 8080 + as is the default): +
+ http://localhost:8080/sample +

+

+ If you just want to browse the contents, you can unpack the war file + with the jar command. +

+
+        jar -xvf sample.war
+      
+ + \ No newline at end of file diff --git a/webapps/docs/appdev/sample/sample.war b/webapps/docs/appdev/sample/sample.war new file mode 100644 index 000000000000..0a127e6bd1f6 Binary files /dev/null and b/webapps/docs/appdev/sample/sample.war differ diff --git a/webapps/docs/appdev/sample/src/mypackage/Hello.java b/webapps/docs/appdev/sample/src/mypackage/Hello.java new file mode 100644 index 000000000000..2ee495763528 --- /dev/null +++ b/webapps/docs/appdev/sample/src/mypackage/Hello.java @@ -0,0 +1,83 @@ +/* + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed with + * this work for additional information regarding copyright ownership. + * The ASF licenses this file to You under the Apache License, Version 2.0 + * (the "License"); you may not use this file except in compliance with + * the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +package mypackage; + +import java.io.IOException; +import java.io.PrintWriter; +import java.util.Enumeration; + +import javax.servlet.ServletException; +import javax.servlet.http.HttpServlet; +import javax.servlet.http.HttpServletRequest; +import javax.servlet.http.HttpServletResponse; + + +/** + * Simple servlet to validate that the Hello, World example can + * execute servlets. In the web application deployment descriptor, + * this servlet must be mapped to correspond to the link in the + * "index.html" file. + * + * @author Craig R. McClanahan + */ + +public final class Hello extends HttpServlet { + + + /** + * Respond to a GET request for the content produced by + * this servlet. + * + * @param request The servlet request we are processing + * @param response The servlet response we are producing + * + * @exception IOException if an input/output error occurs + * @exception ServletException if a servlet error occurs + */ + public void doGet(HttpServletRequest request, + HttpServletResponse response) + throws IOException, ServletException { + + response.setContentType("text/html"); + PrintWriter writer = response.getWriter(); + + writer.println(""); + writer.println(""); + writer.println("Sample Application Servlet Page"); + writer.println(""); + writer.println(""); + + writer.println(""); + writer.println(""); + writer.println(""); + writer.println(""); + writer.println(""); + writer.println("
"); + writer.println(""); + writer.println(""); + writer.println("

Sample Application Servlet

"); + writer.println("This is the output of a servlet that is part of"); + writer.println("the Hello, World application."); + writer.println("
"); + + writer.println(""); + writer.println(""); + + } + + +} diff --git a/webapps/docs/appdev/sample/web/WEB-INF/web.xml b/webapps/docs/appdev/sample/web/WEB-INF/web.xml new file mode 100644 index 000000000000..08b70537743a --- /dev/null +++ b/webapps/docs/appdev/sample/web/WEB-INF/web.xml @@ -0,0 +1,39 @@ + + + + + Hello, World Application + + This is a simple web application with a source code organization + based on the recommendations of the Application Developer's Guide. + + + + HelloServlet + mypackage.Hello + + + + HelloServlet + /hello + + + diff --git a/webapps/docs/appdev/sample/web/hello.jsp b/webapps/docs/appdev/sample/web/hello.jsp new file mode 100644 index 000000000000..0f23637fff71 --- /dev/null +++ b/webapps/docs/appdev/sample/web/hello.jsp @@ -0,0 +1,39 @@ + + + +Sample Application JSP Page + + + + + + + + +
+ + +

Sample Application JSP Page

+This is the output of a JSP page that is part of the Hello, World +application. +
+ +<%= new String("Hello!") %> + + + diff --git a/webapps/docs/appdev/sample/web/images/tomcat.gif b/webapps/docs/appdev/sample/web/images/tomcat.gif new file mode 100644 index 000000000000..32f7d809fbf7 Binary files /dev/null and b/webapps/docs/appdev/sample/web/images/tomcat.gif differ diff --git a/webapps/docs/appdev/sample/web/index.html b/webapps/docs/appdev/sample/web/index.html new file mode 100644 index 000000000000..bbb9997af87c --- /dev/null +++ b/webapps/docs/appdev/sample/web/index.html @@ -0,0 +1,44 @@ + + + +Sample "Hello, World" Application + + + + + + + + +
+ + +

Sample "Hello, World" Application

+

This is the home page for a sample application used to illustrate the +source directory organization of a web application utilizing the principles +outlined in the Application Developer's Guide. +

+ +

To prove that they work, you can execute either of the following links:

+ + + + diff --git a/webapps/docs/appdev/source.xml b/webapps/docs/appdev/source.xml new file mode 100644 index 000000000000..ac21beb32225 --- /dev/null +++ b/webapps/docs/appdev/source.xml @@ -0,0 +1,323 @@ + + + +]> + + + &project; + + + Craig R. McClanahan + Source Organization + + + + +
+ +
+ +
+ +
+

The description below uses the variable name $CATALINA_BASE to refer the + base directory against which most relative paths are resolved. If you have + not configured Tomcat for multiple instances by setting a CATALINA_BASE + directory, then $CATALINA_BASE will be set to the value of $CATALINA_HOME, + the directory into which you have installed Tomcat.

+
+ +

A key recommendation of this manual is to separate the directory +hierarchy containing your source code (described in this section) from +the directory hierarchy containing your deployable application +(described in the preceding section). Maintaining this separation has +the following advantages:

+
    +
  • The contents of the source directories can be more easily administered, + moved, and backed up if the "executable" version of the application + is not intermixed. +

  • +
  • Source code control is easier to manage on directories that contain + only source files. +

  • +
  • The files that make up an installable distribution of your + application are much easier to select when the deployment + hierarchy is separate.
  • +
+ +

As we will see, the ant development tool makes the creation +and processing of such directory hierarchies nearly painless.

+ +

The actual directory and file hierarchy used to contain the source code +of an application can be pretty much anything you like. However, the +following organization has proven to be quite generally applicable, and is +expected by the example build.xml configuration file that +is discussed below. All of these components exist under a top level +project source directory for your application:

+
    +
  • docs/ - Documentation for your application, in whatever + format your development team is using.

  • +
  • src/ - Java source files that generate the servlets, + beans, and other Java classes that are unique to your application. + If your source code is organized in packages (highly + recommended), the package hierarchy should be reflected as a directory + structure underneath this directory.

  • +
  • web/ - The static content of your web site (HTML pages, + JSP pages, JavaScript files, CSS stylesheet files, and images) that will + be accessible to application clients. This directory will be the + document root of your web application, and any subdirectory + structure found here will be reflected in the request URIs required to + access those files.

  • +
  • web/WEB-INF/ - The special configuration files required + for your application, including the web application deployment descriptor + (web.xml, defined in the + Servlet Specification), + tag library descriptors for custom tag libraries + you have created, and other resource files you wish to include within + your web application. Even though this directory appears to be a + subdirectory of your document root, the Servlet Specification + prohibits serving the contents of this directory (or any file it contains) + directly to a client request. Therefore, this is a good place to store + configuration information that is sensitive (such as database connection + usernames and passwords), but is required for your application to + operate successfully.
  • +
+ +

During the development process, two additional directories will be +created on a temporary basis:

+
    +
  • build/ - When you execute a default build + (ant), this directory will contain an exact image + of the files in the web application archive for this application. + Tomcat allows you to deploy an application in an unpacked + directory like this, either by copying it to the + $CATALINA_BASE/webapps directory, or by installing + it via the "Manager" web application. The latter approach is very + useful during development, and will be illustrated below. +

  • +
  • dist/ - When you execute the ant dist + target, this directory will be created. It will create an exact image + of the binary distribution for your web application, including an license + information, documentation, and README files that you have prepared.
  • +
+ +

Note that these two directories should NOT be archived in +your source code control system, because they are deleted and recreated (from +scratch) as needed during development. For that reason, you should not edit +any source files in these directories if you want to maintain a permanent +record of the changes, because the changes will be lost the next time that a +build is performed.

+ + + +

What do you do if your application requires JAR files (or other + resources) from external projects or packages? A common example is that + you need to include a JDBC driver in your web application, in order to + operate.

+ +

Different developers take different approaches to this problem. + Some will encourage checking a copy of the JAR files you depend on into + the source code control archives for every application that requires those + JAR files. However, this can cause significant management issues when you + use the same JAR in many applications - particular when faced with a need + to upgrade to a different version of that JAR file.

+ +

Therefore, this manual recommends that you NOT store + a copy of the packages you depend on inside the source control archives + of your applications. Instead, the external dependencies should be + integrated as part of the process of building your + application. In that way, you can always pick up the appropriate version + of the JAR files from wherever your development system administrator has + installed them, without having to worry about updating your application + every time the version of the dependent JAR file is changed.

+ +

In the example Ant build.xml file, we will demonstrate + how to define build properties that let you configure the locations + of the files to be copied, without having to modify build.xml + when these files change. The build properties used by a particular + developer can be customized on a per-application basis, or defaulted to + "standard" build properties stored in the developer's home directory.

+ +

In many cases, your development system administrator will have already + installed the required JAR files into the lib directory of Tomcat. + If this has been done, you need + to take no actions at all - the example build.xml file + automatically constructs a compile classpath that includes these files.

+ +
+ +
+ + +
+ +

As mentioned earlier, it is highly recommended that you place all of the +source files that comprise your application under the management of a +source code control system like the Concurrent Version System (CVS). If you +elect to do this, every directory and file in the source hierarchy should be +registered and saved -- but none of the generated files. If you register +binary format files (such as images or JAR libraries), be sure to indicate +this to your source code control system.

+ +

We recommended (in the previous section) that you should not store the +contents of the build/ and dist/ directories +created by your development process in the source code control system. An +easy way to tell CVS to ignore these directories is to create a file named +.cvsignore (note the leading period) in your top-level source +directory, with the following contents:

+ +build +dist +build.properties + + +

The reason for mentioning build.properties here will be +explained in the Processes section.

+ +

Detailed instructions for your source code control environment are beyond +the scope of this manual. However, the following steps are followed when +using a command-line CVS client:

+
    +
  • To refresh the state of your source code to that stored in the + the source repository, go to your project source directory, and + execute cvs update -dP. +

  • +
  • When you create a new subdirectory in the source code hierarchy, register + it in CVS with a command like cvs add {subdirname}. +

  • +
  • When you first create a new source code file, navigate to the directory + that contains it, and register the new file with a command like + cvs add {filename}. +

  • +
  • If you no longer need a particular source code file, navigate to the + containing directory and remove the file. Then, deregister it in CVS + with a command like cvs remove {filename}. +

  • +
  • While you are creating, modifying, and deleting source files, changes + are not yet reflected in the server repository. To save your changes in + their current state, go to the project source directory + and execute cvs commit. You will be asked to write a brief + description of the changes you have just completed, which will be stored + with the new version of any updated source file.
  • +
+ +

CVS, like other source code control systems, has many additional features +(such as the ability to tag the files that made up a particular release, and +support for multiple development branches that can later be merged). See the +links and references in the Introduction for +more information.

+ +
+ + +
+ +

We will be using the ant tool to manage the compilation of +our Java source code files, and creation of the deployment hierarchy. Ant +operates under the control of a build file, normally called +build.xml, that defines the processing steps required. This +file is stored in the top-level directory of your source code hierarchy, and +should be checked in to your source code control system.

+ +

Like a Makefile, the build.xml file provides several +"targets" that support optional development activities (such as creating +the associated Javadoc documentation, erasing the deployment home directory +so you can build your project from scratch, or creating the web application +archive file so you can distribute your application. A well-constructed +build.xml file will contain internal documentation describing +the targets that are designed for use by the developer, versus those targets +used internally. To ask Ant to display the project documentation, change to +the directory containing the build.xml file and type:

+ +ant -projecthelp + + +

To give you a head start, a basic build.xml file +is provided that you can customize and install in the project source directory +for your application. This file includes comments that describe the various +targets that can be executed. Briefly, the following targets are generally +provided:

+
    +
  • clean - This target deletes any existing + build and dist directories, so that they + can be reconstructed from scratch. This allows you to guarantee that + you have not made source code modifications that will result in + problems at runtime due to not recompiling all affected classes. +

  • +
  • compile - This target is used to compile any source code + that has been changed since the last time compilation took place. The + resulting class files are created in the WEB-INF/classes + subdirectory of your build directory, exactly where the + structure of a web application requires them to be. Because + this command is executed so often during development, it is normally + made the "default" target so that a simple ant command will + execute it. +

  • +
  • all - This target is a short cut for running the + clean target, followed by the compile target. + Thus, it guarantees that you will recompile the entire application, to + ensure that you have not unknowingly introduced any incompatible changes. +

  • +
  • javadoc - This target creates Javadoc API documentation + for the Java classes in this web application. The example + build.xml file assumes you want to include the API + documentation with your app distribution, so it generates the docs + in a subdirectory of the dist directory. Because you normally + do not need to generate the Javadocs on every compilation, this target is + usually a dependency of the dist target, but not of the + compile target. +

  • +
  • dist - This target creates a distribution directory for + your application, including any required documentation, the Javadocs for + your Java classes, and a web application archive (WAR) file that will be + delivered to system administrators who wish to install your application. + Because this target also depends on the deploy target, the + web application archive will have also picked up any external dependencies + that were included at deployment time.
  • +
+ +

For interactive development and testing of your web application using +Tomcat, the following additional targets are defined:

+
    +
  • install - Tell the currently running Tomcat to make + the application you are developing immediately available for execution + and testing. This action does not require Tomcat to be restarted, but + it is also not remembered after Tomcat is restarted the next time. +

  • +
  • reload - Once the application is installed, you can + continue to make changes and recompile using the compile + target. Tomcat will automatically recognize changes made to JSP pages, + but not to servlet or JavaBean classes - this command will tell Tomcat + to restart the currently installed application so that such changes are + recognized. +

  • +
  • remove - When you have completed your development and + testing activities, you can optionally tell Tomcat to remove this + application from service. +
  • +
+ +

Using the development and testing targets requires some additional +one-time setup that is described on the next page.

+ +
+ + + +
diff --git a/webapps/docs/appdev/web.xml.txt b/webapps/docs/appdev/web.xml.txt new file mode 100644 index 000000000000..b54c61a2df73 --- /dev/null +++ b/webapps/docs/appdev/web.xml.txt @@ -0,0 +1,166 @@ + + + + + + + + + + + My Web Application + + This is version X.X of an application to perform + a wild and wonderful task, based on servlets and + JSP pages. It was written by Dave Developer + (dave@mycompany.com), who should be contacted for + more information. + + + + + + + webmaster + myaddress@mycompany.com + + The EMAIL address of the administrator to whom questions + and comments about this application should be addressed. + + + + + + + + controller + + This servlet plays the "controller" role in the MVC architecture + used in this application. It is generally mapped to the ".do" + filename extension with a servlet-mapping element, and all form + submits in the app will be submitted to a request URI like + "saveCustomer.do", which will therefore be mapped to this servlet. + + The initialization parameter names for this servlet are the + "servlet path" that will be received by this servlet (after the + filename extension is removed). The corresponding value is the + name of the action class that will be used to process this request. + + com.mycompany.mypackage.ControllerServlet + + listOrders + com.mycompany.myactions.ListOrdersAction + + + saveCustomer + com.mycompany.myactions.SaveCustomerAction + + + 5 + + + + graph + + This servlet produces GIF images that are dynamically generated + graphs, based on the input parameters included on the request. + It is generally mapped to a specific request URI like "/graph". + + + + + + + + controller + *.do + + + + graph + /graph + + + + + + + 30 + + + + diff --git a/webapps/docs/apr.xml b/webapps/docs/apr.xml new file mode 100644 index 000000000000..51a8f7d545ad --- /dev/null +++ b/webapps/docs/apr.xml @@ -0,0 +1,185 @@ + + + +]> + + + &project; + + + Apache Portable Runtime (APR) based Native library for Tomcat + Remy Maucherat + + + + +
+ +
+ +
+ +

+ Tomcat can use the Apache Portable Runtime to + provide superior scalability, performance, and better integration with native server + technologies. The Apache Portable Runtime is a highly portable library that is at + the heart of Apache HTTP Server 2.x. APR has many uses, including access to advanced IO + functionality (such as sendfile, epoll and OpenSSL), OS level functionality (random number + generation, system status, etc), and native process handling (shared memory, NT + pipes and Unix sockets). +

+ +

+ These features allows making Tomcat a general purpose webserver, will enable much better + integration with other native web technologies, and overall make Java much more viable as + a full fledged webserver platform rather than simply a backend focused technology. +

+ +
+ +
+ +

+ APR support requires three main native components to be installed: +

    +
  • APR library
  • +
  • JNI wrappers for APR used by Tomcat (libtcnative)
  • +
  • OpenSSL libraries
  • +
+

+ + + +

+ Windows binaries are provided for tcnative-1, which is a statically compiled .dll which includes + OpenSSL and APR. It can be downloaded from here + as 32bit or AMD x86-64 binaries. + In security conscious production environments, it is recommended to use separate shared dlls + for OpenSSL, APR, and libtcnative-1, and update them as needed according to security bulletins. + Windows OpenSSL binaries are linked from the Official OpenSSL + website (see related/binaries). +

+ +
+ + + +

+ Most Linux distributions will ship packages for APR and OpenSSL. The JNI wrapper (libtcnative) will + then have to be compiled. It depends on APR, OpenSSL, and the Java headers. +

+ +

+ Requirements: +

    +
  • APR 1.2+ development headers (libapr1-dev package)
  • +
  • OpenSSL 0.9.7+ development headers (libssl-dev package)
  • +
  • JNI headers from Java compatible JDK 1.4+
  • +
  • GNU development environment (gcc, make)
  • +
+

+ +

+ The wrapper library sources are located in the Tomcat binary bundle, in the + bin/tomcat-native.tar.gz archive. + Once the build environment is installed and the source archive is extracted, the wrapper library + can be compiled using (from the folder containing the configure script): + ./configure && make && make install +

+ +
+ +
+ +
+ +

+ Once the libraries are properly installed and available to Java (if loading fails, the library path + will be displayed), the Tomcat connectors will automatically use APR. Configuration of the connectors + is similar to the regular connectors, but have a few extra attributes which are used to configure + APR components. Note that the defaults should be well tuned for most use cases, and additional + tweaking shouldn't be required. +

+ +

+ When APR is enabled, the following features are also enabled in Tomcat: +

    +
  • Secure session ID generation by default on all platforms (platforms other than Linux required + random number generation using a configured entropy)
  • +
  • OS level statistics on memory usage and CPU usage by the Tomcat process are displayed by + the status servlet
  • +
+

+ +
+ +
+ + +

+ Name of the SSLEngine to use. off: Do not use SSL, on: Use SSL but no specific ENGINE. + The default value is on. + This initializes the native SSL engine, then enable the use of this engine in the connector + using the SSLEnabled attribute. Example: + +<Listener className="org.apache.catalina.core.AprLifecycleListener" SSLEngine="on" /> + +

+

See the Official OpenSSL + website for more details on SSL hardware engines and manufacturers. +

+
+
+
+ +
+ + + +

For HTTP configuration, see the HTTP + connector configuration documentation.

+ +

For HTTPS configuration, see the + HTTPS connector configuration + documentation.

+ +

An example SSL Connector declaration is: + + <Connector port="443" maxHttpHeaderSize="8192" + maxThreads="150" + enableLookups="false" disableUploadTimeout="true" + acceptCount="100" scheme="https" secure="true" + SSLEnabled="true" + SSLCertificateFile="${catalina.base}/conf/localhost.crt" + SSLCertificateKeyFile="${catalina.base}/conf/localhost.key" /> +

+ +
+ + + +

For AJP configuration, see the AJP + connector configuration documentation.

+ +
+ +
+ + +
diff --git a/webapps/docs/architecture/index.xml b/webapps/docs/architecture/index.xml new file mode 100644 index 000000000000..922c03409068 --- /dev/null +++ b/webapps/docs/architecture/index.xml @@ -0,0 +1,69 @@ + + + +]> + + + &project; + + + Yoav Shapira + Table of Contents + + + + + +
+ +

This section of the Tomcat documentation attempts to explain +the architecture and design of the Tomcat server. It includes significant +contributions from several tomcat developers: +

+ + +
+ + +
+ +

The information presented is divided into the following sections:

+
    +
  • Overview - + An overview of the Tomcat server architecture with key terms + and concepts.
  • +
  • Server Startup - + A detailed description, with sequence diagrams, of how the Tomcat + server starts up.
  • +
  • Request Process Flow - + A detailed description of how Tomcat handles a request.
  • +
+ +
+ + + +
diff --git a/webapps/docs/architecture/overview.xml b/webapps/docs/architecture/overview.xml new file mode 100644 index 000000000000..13d03ae48597 --- /dev/null +++ b/webapps/docs/architecture/overview.xml @@ -0,0 +1,138 @@ + + + +]> + + + &project; + + + Yoav Shapira + Architecture Overview + + + + + +
+

+This page provides an overview of the Tomcat server architecture. +

+
+ +
+ + +

+In the Tomcat world, a +Server represents the whole container. +Tomcat provides a default implementation of the +Server interface +which is rarely customized by users. +

+
+ + +

+A Service is an intermediate component +which lives inside a Server and ties one or more Connectors to exactly one +Engine. The Service element is rarely customized by users, as the default +implementation is simple and sufficient: +Service interface. +

+
+ + +

+An +Engine represents request processing +pipeline for a specific Service. As a Service may have multiple Connectors, +the Engine received and processes all requests from these connectors, handing +the response back to the appropriate connector for transmission to the client. +The Engine interface +may be implemented to supply custom Engines, though this is uncommon. +

+

+Note that the Engine may be used for Tomcat server clustering via the +jvmRoute parameter. Read the Clustering documentation for more information. +

+
+ + +

+A Host is an association of a network name, +e.g. www.yourcompany.com, to the Tomcat server. An Engine may contain +multiple hosts, and the Host element also supports network aliases such as +yourcompany.com and abc.yourcompany.com. Users rarely create custom +Hosts +because the +StandardHost +implementation provides significant additional functionality. +

+
+ + +

+A Connector handles communications with the client. There are multiple +connectors available with Tomcat. These include the +HTTP connector which is used for +most HTTP traffic, especially when running Tomcat as a standalone server, +and the AJP connector which implements +the AJP procotol used when connecting Tomcat to a web server such as +Apache HTTPD server. Creating a customized connector is a significant +effort. +

+
+ + +

+A +Context +represents a web application. A Host may contain multiple +contexts, each with a unique path. The +Context +interface may be implemented to create custom Contexts, but +this is rarely the case because the + +StandardContext provides significant additional functionality. +

+
+
+ +
+

+Tomcat is designed to be a fast and efficient implementation of the +Servlet Specification. Tomcat came about as the reference implementation +of this specification, and has remained rigorous in adhering to the +specification. At the same time, significant attention has been paid +to Tomcat's performance and it is now on par with other servlet containers, +including commercial ones. +

+

+In recent releases of Tomcat, mostly starting with Tomcat 5, +we have begun efforts to make more aspects of Tomcat manageable via +JMX. In addition, the Manager and Admin webapps have been greatly +enhanced and improved. Manageability is a primary area of concern +for us as the product matures and the specification becomes more +stable. +

+
+ + +
diff --git a/webapps/docs/architecture/project.xml b/webapps/docs/architecture/project.xml new file mode 100644 index 000000000000..db658364311b --- /dev/null +++ b/webapps/docs/architecture/project.xml @@ -0,0 +1,42 @@ + + + + + Apache Tomcat 7 Architecture + + + The Apache Tomcat Servlet/JSP Container + + + + + + + + + + + + + + + + + + diff --git a/webapps/docs/architecture/requestProcess.xml b/webapps/docs/architecture/requestProcess.xml new file mode 100644 index 000000000000..ee96a1b4c872 --- /dev/null +++ b/webapps/docs/architecture/requestProcess.xml @@ -0,0 +1,69 @@ + + + +]> + + + &project; + + + Yoav Shapira + Request Process Flow + + + + + +
+ +

+This page describes the process used by Tomcat to handle +an incoming request. This process is largely defined by +the Servlet Specification, which outlines the order +of events that must take place. +

+ + +

+TODO +

+
+ + +

+A UML sequence diagram of the request process is available +here. +

+
+ + +

+The Servlet Specification provides many opportunities for +listening in (using Listeners) or modifying (using Filters) +the request handling process even before the request arrives +at the servlet that will handle it. +

+ +
+ +
+ + + +
diff --git a/webapps/docs/architecture/requestProcess/requestProcess.pdf b/webapps/docs/architecture/requestProcess/requestProcess.pdf new file mode 100644 index 000000000000..6a171de8708d Binary files /dev/null and b/webapps/docs/architecture/requestProcess/requestProcess.pdf differ diff --git a/webapps/docs/architecture/requestProcess/roseModel.mdl b/webapps/docs/architecture/requestProcess/roseModel.mdl new file mode 100644 index 000000000000..159c2eeac0d4 --- /dev/null +++ b/webapps/docs/architecture/requestProcess/roseModel.mdl @@ -0,0 +1,12921 @@ + +(object Petal + version 45 + _written "Rose 7.6.0109.2314" + charSet 0) + +(object Design "Logical View" + is_unit TRUE + is_loaded TRUE + quid "3DFDF6CE0337" + defaults (object defaults + rightMargin 0.250000 + leftMargin 0.250000 + topMargin 0.250000 + bottomMargin 0.500000 + pageOverlap 0.250000 + clipIconLabels TRUE + autoResize TRUE + snapToGrid TRUE + gridX 16 + gridY 16 + defaultFont (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + showMessageNum 1 + showClassOfObject TRUE + notation "Unified") + root_usecase_package (object Class_Category "Use Case View" + quid "3DFDF6CE0369" + exportControl "Public" + global TRUE + logical_models (list unit_reference_list) + logical_presentations (list unit_reference_list + (object UseCaseDiagram "Main" + quid "3DFDF6D201FE" + title "Main" + zoom 100 + max_height 28350 + max_width 21600 + origin_x 0 + origin_y 0 + items (list diagram_item_list)))) + root_category (object Class_Category "Logical View" + quid "3DFDF6CE0338" + exportControl "Public" + global TRUE + subsystem "Component View" + quidu "3DFDF6CE036A" + logical_models (list unit_reference_list + (object Class_Category "org.apache.catalina" + quid "3E42DE8D0082" + visible_categories (list visibility_relationship_list + (object Visibility_Relationship + quid "3E42DEF601EB" + supplier "Logical View::org.apache.tomcat.util" + quidu "3E42DEDF01F2") + (object Visibility_Relationship + quid "3E42DF700060" + supplier "Logical View::org.apache.coyote" + quidu "3E42DE9F0132") + (object Visibility_Relationship + quid "3E43D165039C" + supplier "Logical View::org.apache.naming" + quidu "3E43D1580339")) + exportControl "Public" + logical_models (list unit_reference_list + (object Class_Category "ant" + quid "3E42DFBB037F" + visible_categories (list visibility_relationship_list + (object Visibility_Relationship + quid "3E43CFF7020F" + supplier "Logical View::org.apache.catalina::util" + quidu "3E42E0260184")) + exportControl "Public" + logical_models (list unit_reference_list) + logical_presentations (list unit_reference_list)) + (object Class_Category "authenticator" + quid "3E42DFC702B4" + visible_categories (list visibility_relationship_list + (object Visibility_Relationship + quid "3E43D03C0395" + supplier "Logical View::org.apache.catalina::deploy" + quidu "3E42DFDC0340") + (object Visibility_Relationship + quid "3E43D03F01C2" + supplier "Logical View::org.apache.catalina::util" + quidu "3E42E0260184") + (object Visibility_Relationship + quid "3E43D043024A" + supplier "Logical View::org.apache.catalina::valves" + quidu "3E42E02D035B")) + exportControl "Public" + logical_models (list unit_reference_list) + logical_presentations (list unit_reference_list)) + (object Class_Category "connector" + quid "3E42DFCF036A" + visible_categories (list visibility_relationship_list + (object Visibility_Relationship + quid "3E43D07E017D" + supplier "Logical View::org.apache.catalina::session" + quidu "3E42E00C026D")) + exportControl "Public" + logical_models (list unit_reference_list) + logical_presentations (list unit_reference_list)) + (object Class_Category "core" + quid "3E42DFD603BA" + visible_categories (list visibility_relationship_list + (object Visibility_Relationship + quid "3E43D19E01A9" + supplier "Logical View::org.apache.catalina::deploy" + quidu "3E42DFDC0340") + (object Visibility_Relationship + quid "3E43D1A10185" + supplier "Logical View::org.apache.catalina::util" + quidu "3E42E0260184") + (object Visibility_Relationship + quid "3E43D1CE007C" + supplier "Logical View::org.apache.catalina::connector" + quidu "3E42DFCF036A") + (object Visibility_Relationship + quid "3E43D1D800D0" + supplier "Logical View::org.apache.catalina::security" + quidu "3E42E00100D7") + (object Visibility_Relationship + quid "3E43D25C031F" + supplier "Logical View::org.apache.catalina::mbean" + quidu "3E42DFF10188") + (object Visibility_Relationship + quid "3E43D260028E" + supplier "Logical View::org.apache.catalina::startup" + quidu "3E42E01E00EC") + (object Visibility_Relationship + quid "3E43D26A015C" + supplier "Logical View::org.apache.catalina::session" + quidu "3E42E00C026D") + (object Visibility_Relationship + quid "3E43D2830271" + supplier "Logical View::org.apache.catalina::valves" + quidu "3E42E02D035B") + (object Visibility_Relationship + quid "3E43D2C80248" + supplier "Logical View::org.apache.catalina::net" + quidu "3E42DFF70227") + (object Visibility_Relationship + quid "3E43D2D6002B" + supplier "Logical View::org.apache.catalina::loader" + quidu "3E43D2D002D6") + (object Visibility_Relationship + quid "3E43D3D300F7" + supplier "Logical View::org.apache.naming" + quidu "3E43D1580339")) + exportControl "Public" + logical_models (list unit_reference_list) + logical_presentations (list unit_reference_list)) + (object Class_Category "deploy" + quid "3E42DFDC0340" + visible_categories (list visibility_relationship_list + (object Visibility_Relationship + quid "3E43D32001B8" + supplier "Logical View::org.apache.catalina::util" + quidu "3E42E0260184")) + exportControl "Public" + logical_models (list unit_reference_list) + logical_presentations (list unit_reference_list)) + (object Class_Category "launcher" + quid "3E42DFE2033F" + exportControl "Public" + logical_models (list unit_reference_list) + logical_presentations (list unit_reference_list)) + (object Class_Category "logger" + quid "3E42DFEC0285" + exportControl "Public" + logical_models (list unit_reference_list) + logical_presentations (list unit_reference_list)) + (object Class_Category "mbean" + quid "3E42DFF10188" + visible_categories (list visibility_relationship_list + (object Visibility_Relationship + quid "3E43D49101A5" + supplier "Logical View::org.apache.catalina::deploy" + quidu "3E42DFDC0340") + (object Visibility_Relationship + quid "3E43D4C6027D" + supplier "Logical View::org.apache.catalina::core" + quidu "3E42DFD603BA") + (object Visibility_Relationship + quid "3E43D4FB008F" + supplier "Logical View::org.apache.catalina::session" + quidu "3E42E00C026D") + (object Visibility_Relationship + quid "3E43D50000BE" + supplier "Logical View::org.apache.catalina::valves" + quidu "3E42E02D035B") + (object Visibility_Relationship + quid "3E43D5080278" + supplier "Logical View::org.apache.catalina::realm" + quidu "3E42DFFA00AE") + (object Visibility_Relationship + quid "3E43D55A0258" + supplier "Logical View::org.apache.catalina::logger" + quidu "3E42DFEC0285") + (object Visibility_Relationship + quid "3E43D56000D0" + supplier "Logical View::org.apache.catalina::authenticator" + quidu "3E42DFC702B4")) + exportControl "Public" + logical_models (list unit_reference_list) + logical_presentations (list unit_reference_list)) + (object Class_Category "net" + quid "3E42DFF70227" + visible_categories (list visibility_relationship_list + (object Visibility_Relationship + quid "3E43D6390371" + supplier "Logical View::org.apache.catalina::util" + quidu "3E42E0260184")) + exportControl "Public" + logical_models (list unit_reference_list) + logical_presentations (list unit_reference_list)) + (object Class_Category "realm" + quid "3E42DFFA00AE" + visible_categories (list visibility_relationship_list + (object Visibility_Relationship + quid "3E43D69F0133" + supplier "Logical View::org.apache.catalina::core" + quidu "3E42DFD603BA") + (object Visibility_Relationship + quid "3E43D6A10353" + supplier "Logical View::org.apache.catalina::util" + quidu "3E42E0260184") + (object Visibility_Relationship + quid "3E43D70E00E2" + supplier "Logical View::org.apache.naming" + quidu "3E43D1580339") + (object Visibility_Relationship + quid "3E43D72302D7" + supplier "Logical View::org.apache.catalina::deploy" + quidu "3E42DFDC0340")) + exportControl "Public" + logical_models (list unit_reference_list) + logical_presentations (list unit_reference_list)) + (object Class_Category "security" + quid "3E42E00100D7" + visible_categories (list visibility_relationship_list + (object Visibility_Relationship + quid "3E43D74D007F" + supplier "Logical View::org.apache.catalina::startup" + quidu "3E42E01E00EC") + (object Visibility_Relationship + quid "3E43D76B0371" + supplier "Logical View::org.apache.catalina::util" + quidu "3E42E0260184")) + exportControl "Public" + logical_models (list unit_reference_list) + logical_presentations (list unit_reference_list)) + (object Class_Category "servlets" + quid "3E42E00502DB" + visible_categories (list visibility_relationship_list + (object Visibility_Relationship + quid "3E43D82702E5" + supplier "Logical View::org.apache.tomcat.util" + quidu "3E42DEDF01F2") + (object Visibility_Relationship + quid "3E43D82A02CC" + supplier "Logical View::org.apache.catalina::util" + quidu "3E42E0260184") + (object Visibility_Relationship + quid "3E43D82D0244" + supplier "Logical View::org.apache.naming" + quidu "3E43D1580339")) + exportControl "Public" + logical_models (list unit_reference_list) + logical_presentations (list unit_reference_list)) + (object Class_Category "session" + quid "3E42E00C026D" + visible_categories (list visibility_relationship_list + (object Visibility_Relationship + quid "3E43D8770344" + supplier "Logical View::org.apache.catalina::util" + quidu "3E42E0260184")) + exportControl "Public" + logical_models (list unit_reference_list) + logical_presentations (list unit_reference_list)) + (object Class_Category "ssi" + quid "3E42E01002C3" + visible_categories (list visibility_relationship_list + (object Visibility_Relationship + quid "3E43D8F902B5" + supplier "Logical View::org.apache.catalina::util" + quidu "3E42E0260184")) + exportControl "Public" + logical_models (list unit_reference_list) + logical_presentations (list unit_reference_list)) + (object Class_Category "startup" + quid "3E42E01E00EC" + visible_categories (list visibility_relationship_list + (object Visibility_Relationship + quid "3E43D9150251" + supplier "Logical View::org.apache.catalina::logger" + quidu "3E42DFEC0285") + (object Visibility_Relationship + quid "3E43D919018F" + supplier "Logical View::org.apache.catalina::security" + quidu "3E42E00100D7") + (object Visibility_Relationship + quid "3E43D946000D" + supplier "Logical View::org.apache.catalina::core" + quidu "3E42DFD603BA") + (object Visibility_Relationship + quid "3E43D95E012A" + supplier "Logical View::org.apache.catalina::loader" + quidu "3E43D2D002D6") + (object Visibility_Relationship + quid "3E43D9960315" + supplier "Logical View::org.apache.catalina::util" + quidu "3E42E0260184") + (object Visibility_Relationship + quid "3E43D99902BF" + supplier "Logical View::org.apache.catalina::valves" + quidu "3E42E02D035B") + (object Visibility_Relationship + quid "3E43D99C0147" + supplier "Logical View::org.apache.catalina::deploy" + quidu "3E42DFDC0340") + (object Visibility_Relationship + quid "3E43D9DA0114" + supplier "Logical View::org.apache.catalina::net" + quidu "3E42DFF70227") + (object Visibility_Relationship + quid "3E43D9F402F2" + supplier "Logical View::org.apache.catalina::realm" + quidu "3E42DFFA00AE")) + exportControl "Public" + logical_models (list unit_reference_list) + logical_presentations (list unit_reference_list)) + (object Class_Category "user" + quid "3E42E0220174" + visible_categories (list visibility_relationship_list + (object Visibility_Relationship + quid "3E43DB240227" + supplier "Logical View::org.apache.catalina::util" + quidu "3E42E0260184") + (object Visibility_Relationship + quid "3E43DB31009F" + supplier "Logical View::org.apache.naming" + quidu "3E43D1580339")) + exportControl "Public" + logical_models (list unit_reference_list) + logical_presentations (list unit_reference_list)) + (object Class_Category "util" + quid "3E42E0260184" + visible_categories (list visibility_relationship_list + (object Visibility_Relationship + quid "3E43DB85017C" + supplier "Logical View::org.apache.catalina::core" + quidu "3E42DFD603BA") + (object Visibility_Relationship + quid "3E43DB88016C" + supplier "Logical View::org.apache.naming" + quidu "3E43D1580339")) + exportControl "Public" + logical_models (list unit_reference_list) + logical_presentations (list unit_reference_list)) + (object Class_Category "valves" + quid "3E42E02D035B" + visible_categories (list visibility_relationship_list + (object Visibility_Relationship + quid "3E43DC2B0257" + supplier "Logical View::org.apache.catalina::util" + quidu "3E42E0260184") + (object Visibility_Relationship + quid "3E43DD3E0271" + supplier "Logical View::org.apache.catalina::deploy" + quidu "3E42DFDC0340") + (object Visibility_Relationship + quid "3E43DD4102CF" + supplier "Logical View::org.apache.catalina::connector" + quidu "3E42DFCF036A") + (object Visibility_Relationship + quid "3E43DDDE00B8" + supplier "Logical View::org.apache.catalina::core" + quidu "3E42DFD603BA")) + exportControl "Public" + logical_models (list unit_reference_list) + logical_presentations (list unit_reference_list)) + (object Class_Category "loader" + quid "3E43D2D002D6" + visible_categories (list visibility_relationship_list + (object Visibility_Relationship + quid "3E43D3CF00F2" + supplier "Logical View::org.apache.naming" + quidu "3E43D1580339")) + exportControl "Public" + logical_models (list unit_reference_list) + logical_presentations (list unit_reference_list))) + logical_presentations (list unit_reference_list + (object ClassDiagram "Main" + quid "3E42DFB6010B" + title "Main" + zoom 100 + max_height 28350 + max_width 21600 + origin_x 0 + origin_y 0 + items (list diagram_item_list + (object CategoryView "Logical View::org.apache.catalina::ant" @1 + location (2208, 1504) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @1 + location (2064, 1420) + fill_color 13434879 + nlines 2 + max_width 288 + justify 0 + label "ant") + icon_style "Icon" + line_color 3342489 + fill_color 13434879 + quidu "3E42DFBB037F" + width 300 + height 180) + (object CategoryView "Logical View::org.apache.catalina::authenticator" @2 + location (192, 2000) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @2 + location (48, 1916) + fill_color 13434879 + nlines 2 + max_width 288 + justify 0 + label "authenticator") + icon_style "Icon" + line_color 3342489 + fill_color 13434879 + quidu "3E42DFC702B4" + width 300 + height 180) + (object CategoryView "Logical View::org.apache.catalina::connector" @3 + location (464, 1328) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @3 + location (320, 1244) + fill_color 13434879 + nlines 2 + max_width 288 + justify 0 + label "connector") + icon_style "Icon" + line_color 3342489 + fill_color 13434879 + quidu "3E42DFCF036A" + width 300 + height 180) + (object CategoryView "Logical View::org.apache.catalina::core" @4 + location (2224, 800) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @4 + location (2080, 716) + fill_color 13434879 + nlines 2 + max_width 288 + justify 0 + label "core") + icon_style "Icon" + line_color 3342489 + fill_color 13434879 + quidu "3E42DFD603BA" + width 300 + height 180) + (object CategoryView "Logical View::org.apache.catalina::deploy" @5 + location (240, 160) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @5 + location (96, 76) + fill_color 13434879 + nlines 2 + max_width 288 + justify 0 + label "deploy") + icon_style "Icon" + line_color 3342489 + fill_color 13434879 + quidu "3E42DFDC0340" + width 300 + height 180) + (object CategoryView "Logical View::org.apache.catalina::launcher" @6 + location (1776, 2480) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @6 + location (1632, 2396) + fill_color 13434879 + nlines 2 + max_width 288 + justify 0 + label "launcher") + icon_style "Icon" + line_color 3342489 + fill_color 13434879 + quidu "3E42DFE2033F" + width 300 + height 180) + (object CategoryView "Logical View::org.apache.catalina::logger" @7 + location (752, 128) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @7 + location (608, 44) + fill_color 13434879 + nlines 2 + max_width 288 + justify 0 + label "logger") + icon_style "Icon" + line_color 3342489 + fill_color 13434879 + quidu "3E42DFEC0285" + width 300 + height 180) + (object CategoryView "Logical View::org.apache.catalina::mbean" @8 + location (2208, 1216) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @8 + location (2064, 1132) + fill_color 13434879 + nlines 2 + max_width 288 + justify 0 + label "mbean") + icon_style "Icon" + line_color 3342489 + fill_color 13434879 + quidu "3E42DFF10188" + width 300 + height 180) + (object CategoryView "Logical View::org.apache.catalina::net" @9 + location (1056, 2496) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @9 + location (912, 2412) + fill_color 13434879 + nlines 2 + max_width 288 + justify 0 + label "net") + icon_style "Icon" + line_color 3342489 + fill_color 13434879 + quidu "3E42DFF70227" + width 300 + height 180) + (object CategoryView "Logical View::org.apache.catalina::realm" @10 + location (1248, 112) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @10 + location (1104, 28) + fill_color 13434879 + nlines 2 + max_width 288 + justify 0 + label "realm") + icon_style "Icon" + line_color 3342489 + fill_color 13434879 + quidu "3E42DFFA00AE" + width 300 + height 180) + (object CategoryView "Logical View::org.apache.catalina::security" @11 + location (304, 2496) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @11 + location (160, 2412) + fill_color 13434879 + nlines 2 + max_width 288 + justify 0 + label "security") + icon_style "Icon" + line_color 3342489 + fill_color 13434879 + quidu "3E42E00100D7" + width 300 + height 180) + (object CategoryView "Logical View::org.apache.catalina::servlets" @12 + location (2096, 1888) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @12 + location (1952, 1804) + fill_color 13434879 + nlines 2 + max_width 288 + justify 0 + label "servlets") + icon_style "Icon" + line_color 3342489 + fill_color 13434879 + quidu "3E42E00502DB" + width 300 + height 180) + (object CategoryView "Logical View::org.apache.catalina::session" @13 + location (432, 1696) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @13 + location (288, 1612) + fill_color 13434879 + nlines 2 + max_width 288 + justify 0 + label "session") + icon_style "Icon" + line_color 3342489 + fill_color 13434879 + quidu "3E42E00C026D" + width 300 + height 180) + (object CategoryView "Logical View::org.apache.catalina::ssi" @14 + location (672, 2480) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @14 + location (528, 2393) + fill_color 13434879 + nlines 2 + max_width 288 + justify 0 + label "ssi") + icon_style "Icon" + line_color 3342489 + fill_color 13434879 + quidu "3E42E01002C3" + width 301 + height 187) + (object CategoryView "Logical View::org.apache.catalina::startup" @15 + location (1088, 832) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @15 + location (944, 748) + fill_color 13434879 + nlines 2 + max_width 288 + justify 0 + label "startup") + icon_style "Icon" + line_color 3342489 + fill_color 13434879 + quidu "3E42E01E00EC" + width 300 + height 180) + (object CategoryView "Logical View::org.apache.catalina::user" @16 + location (1424, 2496) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @16 + location (1280, 2412) + fill_color 13434879 + nlines 2 + max_width 288 + justify 0 + label "user") + icon_style "Icon" + line_color 3342489 + fill_color 13434879 + quidu "3E42E0220174" + width 300 + height 180) + (object CategoryView "Logical View::org.apache.catalina::util" @17 + location (1312, 1872) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @17 + location (1168, 1788) + fill_color 13434879 + nlines 2 + max_width 288 + justify 0 + label "util") + icon_style "Icon" + line_color 3342489 + fill_color 13434879 + quidu "3E42E0260184" + width 300 + height 180) + (object CategoryView "Logical View::org.apache.catalina::valves" @18 + location (304, 704) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @18 + location (160, 620) + fill_color 13434879 + nlines 2 + max_width 288 + justify 0 + label "valves") + icon_style "Icon" + line_color 3342489 + fill_color 13434879 + quidu "3E42E02D035B" + width 300 + height 180) + (object ImportView "" @19 + stereotype TRUE + line_color 3342489 + quidu "3E43CFF7020F" + client @1 + supplier @17 + line_style 0) + (object ImportView "" @20 + stereotype TRUE + line_color 3342489 + quidu "3E43D07E017D" + client @3 + supplier @13 + line_style 0) + (object CategoryView "Logical View::org.apache.catalina::loader" @21 + location (2240, 416) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @21 + location (2096, 332) + fill_color 13434879 + nlines 2 + max_width 288 + justify 0 + label "loader") + icon_style "Icon" + line_color 3342489 + fill_color 13434879 + quidu "3E43D2D002D6" + width 300 + height 180) + (object ImportView "" @22 + stereotype TRUE + line_color 3342489 + quidu "3E43D32001B8" + client @5 + supplier @17 + line_style 0) + (object CategoryView "Logical View::org.apache.naming" @23 + location (1872, 96) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @23 + location (1699, 12) + fill_color 13434879 + nlines 2 + max_width 346 + justify 0 + label "org.apache.naming") + icon_style "Icon" + line_color 3342489 + fill_color 13434879 + quidu "3E43D1580339" + width 358 + height 180) + (object ImportView "" @24 + stereotype TRUE + line_color 3342489 + quidu "3E43D3CF00F2" + client @21 + supplier @23 + line_style 0) + (object ImportView "" @25 + stereotype TRUE + line_color 3342489 + quidu "3E43D6390371" + client @9 + supplier @17 + line_style 0) + (object ImportView "" @26 + stereotype TRUE + line_color 3342489 + quidu "3E43D69F0133" + client @10 + supplier @4 + line_style 0) + (object ImportView "" @27 + stereotype TRUE + line_color 3342489 + quidu "3E43D6A10353" + client @10 + supplier @17 + line_style 0) + (object ImportView "" @28 + stereotype TRUE + line_color 3342489 + quidu "3E43D70E00E2" + client @10 + supplier @23 + line_style 0) + (object ImportView "" @29 + stereotype TRUE + line_color 3342489 + quidu "3E43D72302D7" + client @10 + supplier @5 + line_style 0) + (object ImportView "" @30 + stereotype TRUE + line_color 3342489 + quidu "3E43D69F0133" + client @10 + supplier @4 + line_style 0) + (object ImportView "" @31 + stereotype TRUE + line_color 3342489 + quidu "3E43D74D007F" + client @11 + supplier @15 + line_style 0) + (object ImportView "" @32 + stereotype TRUE + line_color 3342489 + quidu "3E43D76B0371" + client @11 + supplier @17 + line_style 0) + (object CategoryView "Logical View::org.apache.tomcat.util" @33 + location (2096, 2224) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @33 + location (1923, 2140) + fill_color 13434879 + nlines 2 + max_width 346 + justify 0 + label "org.apache.tomcat.util") + icon_style "Icon" + line_color 3342489 + fill_color 13434879 + quidu "3E42DEDF01F2" + width 358 + height 180) + (object ImportView "" @34 + stereotype TRUE + line_color 3342489 + quidu "3E43D8770344" + client @13 + supplier @17 + line_style 0) + (object ImportView "" @35 + stereotype TRUE + line_color 3342489 + quidu "3E43D8F902B5" + client @14 + supplier @17 + line_style 0) + (object ImportView "" @36 + stereotype TRUE + line_color 3342489 + quidu "3E43DB240227" + client @16 + supplier @17 + line_style 0) + (object ImportView "" @37 + stereotype TRUE + line_color 3342489 + quidu "3E43DB31009F" + client @16 + supplier @23 + line_style 0) + (object ImportView "" @38 + stereotype TRUE + line_color 3342489 + quidu "3E43DB85017C" + client @17 + supplier @4 + line_style 0) + (object ImportView "" @39 + stereotype TRUE + line_color 3342489 + quidu "3E43DB88016C" + client @17 + supplier @23 + line_style 0) + (object ImportView "" @40 + stereotype TRUE + line_color 3342489 + quidu "3E43D82702E5" + client @12 + supplier @33 + line_style 0) + (object ImportView "" @41 + stereotype TRUE + line_color 3342489 + quidu "3E43D82A02CC" + client @12 + supplier @17 + line_style 0) + (object ImportView "" @42 + stereotype TRUE + line_color 3342489 + quidu "3E43D82D0244" + client @12 + supplier @23 + vertices (list Points + (2060, 1743) + (1746, 447) + (1838, 186)) + line_style 0) + (object ImportView "" @43 + stereotype TRUE + line_color 3342489 + quidu "3E43D919018F" + client @15 + supplier @11 + line_style 0) + (object ImportView "" @44 + stereotype TRUE + line_color 3342489 + quidu "3E43D946000D" + client @15 + supplier @4 + line_style 0) + (object ImportView "" @45 + stereotype TRUE + line_color 3342489 + quidu "3E43D95E012A" + client @15 + supplier @21 + line_style 0) + (object ImportView "" @46 + stereotype TRUE + line_color 3342489 + quidu "3E43D95E012A" + client @15 + supplier @21 + line_style 0) + (object ImportView "" @47 + stereotype TRUE + line_color 3342489 + quidu "3E43D9960315" + client @15 + supplier @17 + line_style 0) + (object ImportView "" @48 + stereotype TRUE + line_color 3342489 + quidu "3E43D99902BF" + client @15 + supplier @18 + line_style 0) + (object ImportView "" @49 + stereotype TRUE + line_color 3342489 + quidu "3E43D99C0147" + client @15 + supplier @5 + line_style 0) + (object ImportView "" @50 + stereotype TRUE + line_color 3342489 + quidu "3E43D946000D" + client @15 + supplier @4 + line_style 0) + (object ImportView "" @51 + stereotype TRUE + line_color 3342489 + quidu "3E43D9150251" + client @15 + supplier @7 + line_style 0) + (object ImportView "" @52 + stereotype TRUE + line_color 3342489 + quidu "3E43D9DA0114" + client @15 + supplier @9 + line_style 0) + (object ImportView "" @53 + stereotype TRUE + line_color 3342489 + quidu "3E43D9F402F2" + client @15 + supplier @10 + line_style 0) + (object ImportView "" @54 + stereotype TRUE + line_color 3342489 + quidu "3E43D9960315" + client @15 + supplier @17 + line_style 0) + (object ImportView "" @55 + stereotype TRUE + line_color 3342489 + quidu "3E43D946000D" + client @15 + supplier @4 + line_style 0) + (object ImportView "" @56 + stereotype TRUE + line_color 3342489 + quidu "3E43D99C0147" + client @15 + supplier @5 + line_style 0) + (object ImportView "" @57 + stereotype TRUE + line_color 3342489 + quidu "3E43D49101A5" + client @8 + supplier @5 + line_style 0) + (object ImportView "" @58 + stereotype TRUE + line_color 3342489 + quidu "3E43D4C6027D" + client @8 + supplier @4 + line_style 0) + (object ImportView "" @59 + stereotype TRUE + line_color 3342489 + quidu "3E43D4FB008F" + client @8 + supplier @13 + line_style 0) + (object ImportView "" @60 + stereotype TRUE + line_color 3342489 + quidu "3E43D50000BE" + client @8 + supplier @18 + vertices (list Points + (2057, 1216) + (1278, 1216) + (454, 783)) + line_style 0) + (object ImportView "" @61 + stereotype TRUE + line_color 3342489 + quidu "3E43D5080278" + client @8 + supplier @10 + line_style 0) + (object ImportView "" @62 + stereotype TRUE + line_color 3342489 + quidu "3E43D55A0258" + client @8 + supplier @7 + line_style 0) + (object ImportView "" @63 + stereotype TRUE + line_color 3342489 + quidu "3E43D56000D0" + client @8 + supplier @2 + line_style 0) + (object ImportView "" @64 + stereotype TRUE + line_color 3342489 + quidu "3E43D19E01A9" + client @4 + supplier @5 + line_style 0) + (object ImportView "" @65 + stereotype TRUE + line_color 3342489 + quidu "3E43D1A10185" + client @4 + supplier @17 + line_style 0) + (object ImportView "" @66 + stereotype TRUE + line_color 3342489 + quidu "3E43D1CE007C" + client @4 + supplier @3 + line_style 0) + (object ImportView "" @67 + stereotype TRUE + line_color 3342489 + quidu "3E43D1D800D0" + client @4 + supplier @11 + vertices (list Points + (2081, 890) + (959, 1616) + (409, 2351)) + line_style 0) + (object ImportView "" @68 + stereotype TRUE + line_color 3342489 + quidu "3E43D25C031F" + client @4 + supplier @8 + line_style 0) + (object ImportView "" @69 + stereotype TRUE + line_color 3342489 + quidu "3E43D260028E" + client @4 + supplier @15 + line_style 0) + (object ImportView "" @70 + stereotype TRUE + line_color 3342489 + quidu "3E43D26A015C" + client @4 + supplier @13 + line_style 0) + (object ImportView "" @71 + stereotype TRUE + line_color 3342489 + quidu "3E43D2830271" + client @4 + supplier @18 + line_style 0) + (object ImportView "" @72 + stereotype TRUE + line_color 3342489 + quidu "3E43D2C80248" + client @4 + supplier @9 + line_style 0) + (object ImportView "" @73 + stereotype TRUE + line_color 3342489 + quidu "3E43D2D6002B" + client @4 + supplier @21 + line_style 0) + (object ImportView "" @74 + stereotype TRUE + line_color 3342489 + quidu "3E43D3D300F7" + client @4 + supplier @23 + line_style 0) + (object ImportView "" @75 + stereotype TRUE + line_color 3342489 + quidu "3E43D03C0395" + client @2 + supplier @5 + vertices (list Points + (171, 1855) + (16, 766) + (205, 250)) + line_style 0) + (object ImportView "" @76 + stereotype TRUE + line_color 3342489 + quidu "3E43D03F01C2" + client @2 + supplier @17 + line_style 0) + (object ImportView "" @77 + stereotype TRUE + line_color 3342489 + quidu "3E43D043024A" + client @2 + supplier @18 + line_style 0) + (object ImportView "" @78 + stereotype TRUE + line_color 3342489 + quidu "3E43DC2B0257" + client @18 + supplier @17 + line_style 0) + (object ImportView "" @79 + stereotype TRUE + line_color 3342489 + quidu "3E43DD3E0271" + client @18 + supplier @5 + line_style 0) + (object ImportView "" @80 + stereotype TRUE + line_color 3342489 + quidu "3E43DD4102CF" + client @18 + supplier @3 + line_style 0) + (object ImportView "" @81 + stereotype TRUE + line_color 3342489 + quidu "3E43DDDE00B8" + client @18 + supplier @4 + vertices (list Points + (454, 654) + (1293, 381) + (2073, 731)) + line_style 0))))) + (object Class_Category "org.apache.coyote" + quid "3E42DE9F0132" + visible_categories (list visibility_relationship_list + (object Visibility_Relationship + quid "3E42DEFC00B3" + supplier "Logical View::org.apache.tomcat.util" + quidu "3E42DEDF01F2")) + exportControl "Public" + logical_models (list unit_reference_list) + logical_presentations (list unit_reference_list)) + (object Class_Category "org.apache.tomcat.util" + quid "3E42DEDF01F2" + exportControl "Public" + logical_models (list unit_reference_list) + logical_presentations (list unit_reference_list)) + (object Class_Category "org.apache.jasper" + quid "3E42DEFF0270" + exportControl "Public" + logical_models (list unit_reference_list) + logical_presentations (list unit_reference_list)) + (object Class_Category "org.apache.naming" + quid "3E43D1580339" + exportControl "Public" + logical_models (list unit_reference_list) + logical_presentations (list unit_reference_list)) + (object Mechanism @82 + logical_models (list unit_reference_list + (object Object "Bootstrap" + quid "3DFDF8FD0345" + collaborators (list link_list + (object Link + quid "3DFDF9210008" + supplier "Bootstrap" + quidu "3DFDF8FD0345" + messages (list Messages + (object Message "initClassLoaders()" + quid "3DFDF9210009" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "1" + ordinal 0 + quidu "000000000000" + creation FALSE))) + (object Link + quid "3DFDF91A010C" + supplier "Catalina" + quidu "3DFDF90A0330" + messages (list Messages + (object Message "newInstance()" + quid "3DFDF91A010D" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "2" + ordinal 1 + quidu "000000000000" + creation FALSE) + (object Message "setParentClassLoader()" + quid "3DFDF97900C2" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "3" + ordinal 2 + quidu "000000000000" + creation FALSE) + (object Message "load()" + quid "3DFDFA3402F2" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "4" + ordinal 3 + quidu "000000000000" + creation FALSE)))) + persistence "Transient" + creationObj FALSE + multi FALSE) + (object Object "Digester" + quid "3DFDFAF201A1" + collaborators (list link_list + (object Link + quid "3DFDFB8400A6" + supplier "ServerLifecycleListener" + quidu "3DFDFB4B0217" + messages (list Messages + (object Message "newInstance()" + quid "3DFDFB8400A7" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "9.1" + ordinal 9 + quidu "000000000000" + creation FALSE))) + (object Link + quid "3DFDFB920147" + supplier "GlobalResourcesLifecycleListener" + quidu "3DFDFB7A02AB" + messages (list Messages + (object Message "newInstance()" + quid "3DFDFB920148" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "9.2" + ordinal 10 + quidu "000000000000" + creation FALSE)))) + persistence "Transient" + creationObj FALSE + multi FALSE) + (object Object "ServerLifecycleListener" + quid "3DFDFB4B0217" + persistence "Transient" + creationObj FALSE + multi FALSE) + (object Object "GlobalResourcesLifecycleListener" + quid "3DFDFB7A02AB" + persistence "Transient" + creationObj FALSE + multi FALSE) + (object Object "SecurityConfig" + quid "3DFDFBD802BA" + persistence "Transient" + creationObj FALSE + multi FALSE) + (object Object "Catalina" + quid "3DFDF90A0330" + collaborators (list link_list + (object Link + quid "3DFDFA8001D9" + supplier "Catalina" + quidu "3DFDF90A0330" + messages (list Messages + (object Message "initDirs()" + quid "3DFDFA8001DA" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "5" + ordinal 4 + quidu "000000000000" + creation FALSE) + (object Message "initNaming()" + quid "3DFDFA8B0347" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "6" + ordinal 5 + quidu "000000000000" + creation FALSE) + (object Message "initialize()" + quid "3DFDFAAD01AC" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "7" + ordinal 6 + quidu "000000000000" + creation FALSE))) + (object Link + quid "3DFDFAF800C3" + supplier "Digester" + quidu "3DFDFAF201A1" + messages (list Messages + (object Message "createDigester()" + quid "3DFDFAF800C4" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "8" + ordinal 7 + quidu "000000000000" + creation FALSE) + (object Message "parse()" + quid "3DFDFB0100B2" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "9" + ordinal 8 + quidu "000000000000" + creation FALSE))) + (object Link + quid "3DFDFBEA00C1" + supplier "SecurityConfig" + quidu "3DFDFBD802BA" + messages (list Messages + (object Message "newInstance()" + quid "3DFDFBEA00C2" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "10" + ordinal 11 + quidu "000000000000" + creation FALSE) + (object Message "setPackageDefinition()" + quid "3DFDFBF401F2" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "11" + ordinal 12 + Operation "setPackageDefinition" + quidu "000000000000" + creation FALSE) + (object Message "setPackageAccess()" + quid "3DFDFC1203C2" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "12" + ordinal 13 + Operation "setPackageAccess" + quidu "000000000000" + creation FALSE)))) + persistence "Transient" + creationObj FALSE + multi FALSE))) + (object Mechanism @83 + logical_models (list unit_reference_list + (object Object "Catalina" + quid "3DFDFC8F015F" + collaborators (list link_list + (object Link + quid "3DFDFD1F0075" + supplier "StandardServer" + quidu "3DFDFCCB006B" + messages (list Messages + (object Message "initialize()" + quid "3DFDFD1F0076" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "1" + ordinal 0 + quidu "000000000000" + creation FALSE)))) + persistence "Transient" + creationObj FALSE + multi FALSE) + (object Object "StandardServer" + quid "3DFDFCCB006B" + collaborators (list link_list + (object Link + quid "3DFDFD3D01C3" + supplier "StandardService" + quidu "3DFDFD370020" + messages (list Messages + (object Message "initialize()" + quid "3DFDFD3D01C4" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "2" + ordinal 1 + quidu "000000000000" + creation FALSE)))) + persistence "Transient" + creationObj FALSE + multi FALSE) + (object Object "StandardService" + quid "3DFDFD370020" + collaborators (list link_list + (object Link + quid "3DFDFE990304" + supplier "CoyoteConnector" + quidu "3DFDFE810313" + messages (list Messages + (object Message "initialize()" + quid "3DFDFE990305" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "2.1" + ordinal 2 + quidu "000000000000" + creation FALSE)))) + persistence "Transient" + creationObj FALSE + multi FALSE) + (object Object "CoyoteConnector" + quid "3DFDFE810313" + collaborators (list link_list + (object Link + quid "3DFE013D0216" + supplier "CoyoteAdapter" + quidu "3DFDFFA00226" + messages (list Messages + (object Message "new()" + quid "3DFE013D0217" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "2.1.1" + ordinal 3 + quidu "000000000000" + creation FALSE))) + (object Link + quid "3DFE0183032F" + supplier "Http11Protocol" + quidu "3DFE016601A6" + messages (list Messages + (object Message "new()" + quid "3DFE01830330" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "2.1.2" + ordinal 4 + quidu "000000000000" + creation FALSE) + (object Message "init()" + quid "3DFE0188032C" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "2.1.3" + ordinal 5 + quidu "000000000000" + creation FALSE))) + (object Link + quid "3DFE01BC038B" + supplier "JkCoyoteAdapter" + quidu "3DFE01AD01A8" + messages (list Messages + (object Message "new()" + quid "3DFE01BC038C" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "2.1.4" + ordinal 6 + quidu "000000000000" + creation FALSE) + (object Message "init()" + quid "3DFE01C30164" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "2.1.5" + ordinal 7 + quidu "000000000000" + creation FALSE)))) + persistence "Transient" + creationObj FALSE + multi FALSE) + (object Object "CoyoteAdapter" + quid "3DFDFFA00226" + persistence "Transient" + creationObj FALSE + multi FALSE) + (object Object "Http11Protocol" + quid "3DFE016601A6" + persistence "Transient" + creationObj FALSE + multi FALSE) + (object Object "JkCoyoteAdapter" + quid "3DFE01AD01A8" + persistence "Transient" + creationObj FALSE + multi FALSE))) + (object Mechanism @84 + logical_models (list unit_reference_list + (object Object "Bootstrap" + quid "3DFE027700F5" + collaborators (list link_list + (object Link + quid "3DFE02830373" + supplier "Catalina" + quidu "3DFE027D0067" + messages (list Messages + (object Message "start()" + quid "3DFE02830374" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "1" + ordinal 0 + quidu "000000000000" + creation FALSE)))) + persistence "Transient" + creationObj FALSE + multi FALSE) + (object Object "Catalina" + quid "3DFE027D0067" + collaborators (list link_list + (object Link + quid "3DFE02BA0187" + supplier "StandardServer" + quidu "3DFE02B30015" + messages (list Messages + (object Message "start()" + quid "3DFE02BA0188" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "1.1" + ordinal 1 + quidu "000000000000" + creation FALSE)))) + persistence "Transient" + creationObj FALSE + multi FALSE) + (object Object "StandardServer" + quid "3DFE02B30015" + collaborators (list link_list + (object Link + quid "3DFE02D3006B" + supplier "StandardServer" + quidu "3DFE02B30015" + messages (list Messages + (object Message "fireLifecycleEvent(BEFORE_START_EVENT)" + quid "3DFE02D3006C" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "1.1.1" + ordinal 2 + quidu "000000000000" + creation FALSE) + (object Message "fireLifecycleEvent(START_EVENT)" + quid "3DFE02DF02DF" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "1.1.2" + ordinal 3 + quidu "000000000000" + creation FALSE))) + (object Link + quid "3DFE030C02B2" + supplier "StandardService" + quidu "3DFE030400E3" + messages (list Messages + (object Message "start()" + quid "3DFE030C02B3" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "1.1.3" + ordinal 4 + quidu "000000000000" + creation FALSE)))) + persistence "Transient" + creationObj FALSE + multi FALSE) + (object Object "StandardService" + quid "3DFE030400E3" + collaborators (list link_list + (object Link + quid "3DFE031D0021" + supplier "StandardService" + quidu "3DFE030400E3" + messages (list Messages + (object Message "fireLifecycleEvent(BEFORE_START_EVENT)" + quid "3DFE031D0022" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "1.1.3.1" + ordinal 5 + quidu "000000000000" + creation FALSE) + (object Message "fireLifecycleEvent(START_EVENT)" + quid "3DFE0330019B" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "1.1.3.2" + ordinal 6 + quidu "000000000000" + creation FALSE))) + (object Link + quid "3DFE03700189" + supplier "StandardEngine" + quidu "3DFE034700C2" + messages (list Messages + (object Message "start()" + quid "3DFE0370018A" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "1.1.3.3" + ordinal 7 + quidu "000000000000" + creation FALSE)))) + persistence "Transient" + creationObj FALSE + multi FALSE) + (object Object "StandardEngine" + quid "3DFE034700C2" + collaborators (list link_list + (object Link + quid "3DFE03750050" + supplier "StandardEngine" + quidu "3DFE034700C2" + messages (list Messages + (object Message "fireLifecycleEvent(BEFORE_START_EVENT)" + quid "3DFE03750051" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "2" + ordinal 8 + quidu "000000000000" + creation FALSE) + (object Message "addDefaultMapper()" + quid "3DFE0389001C" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "3" + ordinal 9 + quidu "000000000000" + creation FALSE) + (object Message "logger.start()" + quid "3DFE03980281" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "4" + ordinal 10 + quidu "000000000000" + creation FALSE) + (object Message "realm.start()" + quid "3DFE03A80107" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "5" + ordinal 11 + quidu "000000000000" + creation FALSE) + (object Message "findMappers()" + quid "3DFE03BD000D" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "6" + ordinal 12 + quidu "000000000000" + creation FALSE) + (object Message "findChildren()" + quid "3DFE03E000A4" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "7" + ordinal 13 + quidu "000000000000" + creation FALSE))) + (object Link + quid "3DFE03FB0279" + supplier "StandardHost" + quidu "3DFE03F2035D" + messages (list Messages + (object Message "start()" + quid "3DFE03FB027A" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "8" + ordinal 14 + quidu "000000000000" + creation FALSE)))) + persistence "Transient" + creationObj FALSE + multi FALSE) + (object Object "StandardHost" + quid "3DFE03F2035D" + collaborators (list link_list + (object Link + quid "3DFE043B02AD" + supplier "StandardHost" + quidu "3DFE03F2035D" + messages (list Messages + (object Message "fireLifecycleEvent(BEFORE_START_EVENT)" + quid "3DFE043B02AE" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "8.1" + ordinal 15 + quidu "000000000000" + creation FALSE) + (object Message "addDefaultMapper()" + quid "3DFE045C021F" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "8.2" + ordinal 16 + quidu "000000000000" + creation FALSE) + (object Message "logger.start()" + quid "3DFE049B000C" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "8.3" + ordinal 17 + quidu "000000000000" + creation FALSE) + (object Message "findMapper()" + quid "3DFE04A303BB" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "8.4" + ordinal 18 + quidu "000000000000" + creation FALSE) + (object Message "findChildren()" + quid "3DFE04A90342" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "8.5" + ordinal 19 + Operation "findChildren" + quidu "000000000000" + creation FALSE))) + (object Link + quid "3DFE048E00B8" + supplier "StandardPipeline" + quidu "3DFE047D006D" + messages (list Messages + (object Message "start()" + quid "3DFE048E00B9" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "8.6" + ordinal 20 + quidu "000000000000" + creation FALSE)))) + persistence "Transient" + creationObj FALSE + multi FALSE) + (object Object "StandardPipeline" + quid "3DFE047D006D" + collaborators (list link_list + (object Link + quid "3DFE05780137" + supplier "StandardPipeline" + quidu "3DFE047D006D" + messages (list Messages + (object Message "fireLifecycleEvent(BEFORE_START_EVENT)" + quid "3DFE05780138" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "8.6.1" + ordinal 21 + Operation "fireLifecycleEvent(AFTER_START_EVENT)" + quidu "000000000000" + creation FALSE) + (object Message "fireLifecycleEvent(START_EVENT)" + quid "3DFE05A80398" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "8.6.2" + ordinal 22 + Operation "fireLifecycleEvent(BEFORE_START_EVENT)" + quidu "000000000000" + creation FALSE) + (object Message "fireLifecycleEvent(AFTER_EVENT)" + quid "3DFE05BA0196" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "8.6.3" + ordinal 23 + quidu "000000000000" + creation FALSE)))) + persistence "Transient" + creationObj FALSE + multi FALSE))) + (object Mechanism @85 + logical_models (list unit_reference_list + (object Object "StandardHost" + quid "3DFE0538017B" + collaborators (list link_list + (object Link + quid "3DFE066C0340" + supplier "StandardHost" + quidu "3DFE0538017B" + messages (list Messages + (object Message "fireLifecycleEvent(START_EVENT)" + quid "3DFE066C0341" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "1" + ordinal 0 + quidu "000000000000" + creation FALSE))) + (object Link + quid "3DFE06D20293" + supplier "HostConfig" + quidu "3DFE06A60131" + messages (list Messages + (object Message "interested[i].lifecycleEvent()" + quid "3DFE06D20294" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "2" + ordinal 1 + quidu "000000000000" + creation FALSE) + (object Message "install()" + quid "3DFE078B03BB" + frequency "Aperiodic" + synchronization "Simple" + dir "ToClientFromSupplier" + sequence "2.6" + ordinal 7 + quidu "000000000000" + creation FALSE) + (object Message "install()" + quid "3DFE132D0309" + frequency "Aperiodic" + synchronization "Simple" + dir "ToClientFromSupplier" + sequence "5" + ordinal 13 + quidu "000000000000" + creation FALSE))) + (object Link + quid "3DFE07B100BD" + supplier "StandardHostDeployer" + quidu "3DFE079A0055" + messages (list Messages + (object Message "install()" + quid "3DFE07B100BE" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "3" + ordinal 8 + quidu "000000000000" + creation FALSE) + (object Message "install() // same as above" + quid "3DFE133A036C" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "6" + ordinal 17 + Operation "install()" + quidu "000000000000" + creation FALSE)))) + persistence "Transient" + creationObj FALSE + multi FALSE) + (object Object "HostConfig" + quid "3DFE06A60131" + collaborators (list link_list + (object Link + quid "3DFE06E9028C" + supplier "HostConfig" + quidu "3DFE06A60131" + messages (list Messages + (object Message "setDeployXML()" + quid "3DFE06E9028D" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "2.1" + ordinal 2 + quidu "000000000000" + creation FALSE) + (object Message "setLiveDeploy()" + quid "3DFE06F300FF" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "2.2" + ordinal 3 + quidu "000000000000" + creation FALSE) + (object Message "setUnpacksWar()" + quid "3DFE06FB00D9" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "2.3" + ordinal 4 + quidu "000000000000" + creation FALSE) + (object Message "setXMLValidation()" + quid "3DFE070C0015" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "2.4" + ordinal 5 + quidu "000000000000" + creation FALSE) + (object Message "deployDescriptors()" + quid "3DFE073B0031" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "2.5" + ordinal 6 + quidu "000000000000" + creation FALSE) + (object Message "deployApps()" + quid "3DFE131F0327" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "4" + ordinal 12 + quidu "000000000000" + creation FALSE)))) + persistence "Transient" + creationObj FALSE + multi FALSE) + (object Object "StandardHostDeployer" + quid "3DFE079A0055" + collaborators (list link_list + (object Link + quid "3DFE07D200EC" + supplier "Digester" + quidu "3DFE07C9034C" + messages (list Messages + (object Message "create()" + quid "3DFE07D200ED" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "3.1" + ordinal 9 + quidu "000000000000" + creation FALSE) + (object Message "parse()" + quid "3DFE07D603D7" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "3.6" + ordinal 16 + quidu "000000000000" + creation FALSE) + (object Message "add(ContextRuleSet)" + quid "3DFE08FA003D" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "3.3" + ordinal 11 + quidu "000000000000" + creation FALSE))) + (object Link + quid "3DFE087D01E2" + supplier "StandardHostDeployer" + quidu "3DFE079A0055") + (object Link + quid "3DFE08DA029A" + supplier "ContextRuleSet" + quidu "3DFE0834016F" + messages (list Messages + (object Message "new()" + quid "3DFE08DA029B" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "3.2" + ordinal 10 + quidu "000000000000" + creation FALSE) + (object Message "add(NamingRuleSet())" + quid "3DFE0907015F" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "3.5" + ordinal 15 + quidu "000000000000" + creation FALSE))) + (object Link + quid "3DFE08E00090" + supplier "NamingRuleSet" + quidu "3DFE08D00173" + messages (list Messages + (object Message "new()" + quid "3DFE08E00091" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "3.4" + ordinal 14 + quidu "000000000000" + creation FALSE)))) + persistence "Transient" + creationObj FALSE + multi FALSE) + (object Object "Digester" + quid "3DFE07C9034C" + persistence "Transient" + creationObj FALSE + multi FALSE) + (object Object "ContextRuleSet" + quid "3DFE0834016F" + persistence "Transient" + creationObj FALSE + multi FALSE) + (object Object "NamingRuleSet" + quid "3DFE08D00173" + persistence "Transient" + creationObj FALSE + multi FALSE))) + (object Mechanism @86 + logical_models (list unit_reference_list + (object Object "Digester" + quid "3DFE095A0371" + collaborators (list link_list + (object Link + quid "3DFE0E7801DA" + supplier "Digester" + quidu "3DFE095A0371" + messages (list Messages + (object Message "parse" + quid "3DFE0E7801DB" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "1" + ordinal 0 + quidu "000000000000" + creation FALSE) + (object Message "startElement()" + quid "3DFE0F2F03D2" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "2" + ordinal 1 + quidu "000000000000" + creation FALSE))) + (object Link + quid "3DFE0F400213" + supplier "Rule" + quidu "3DFE0E7400D0" + messages (list Messages + (object Message "begin()" + quid "3DFE0F400214" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "3" + ordinal 2 + quidu "000000000000" + creation FALSE)))) + persistence "Transient" + creationObj FALSE + multi FALSE) + (object Object "Rule" + quid "3DFE0E7400D0" + collaborators (list link_list + (object Link + quid "3DFE0FD30265" + supplier "StandardContext" + quidu "3DFE0FC502A1" + messages (list Messages + (object Message "newInstance()" + quid "3DFE0FD30266" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "3.1" + ordinal 3 + quidu "000000000000" + creation FALSE))) + (object Link + quid "3DFE102002E8" + supplier "SetPropertiesRule" + quidu "3DFE100303A4" + messages (list Messages + (object Message "begin()" + quid "3DFE102002E9" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "3.2" + ordinal 6 + quidu "000000000000" + creation FALSE))) + (object Link + quid "3DFE127F0024" + supplier "Rule" + quidu "3DFE0E7400D0") + (object Link + quid "3DFE128501C7" + supplier "SetNextRule" + quidu "3DFE12690267" + messages (list Messages + (object Message "end()" + quid "3DFE128501C8" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "3.3" + ordinal 8 + quidu "000000000000" + creation FALSE)))) + persistence "Transient" + creationObj FALSE + multi FALSE) + (object Object "StandardContext" + quid "3DFE0FC502A1" + collaborators (list link_list + (object Link + quid "3DFE114A0192" + supplier "StandardPipeline" + quidu "3DFE112F003F" + messages (list Messages + (object Message "setBasic(StandardContextValve)" + quid "3DFE114A0193" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "3.1.2" + ordinal 5 + Operation "setBasic" + quidu "000000000000" + creation FALSE))) + (object Link + quid "3DFE115E001E" + supplier "StandardContextValve" + quidu "3DFE110D0375" + messages (list Messages + (object Message "new()" + quid "3DFE115E001F" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "3.1.1" + ordinal 4 + quidu "000000000000" + creation FALSE)))) + persistence "Transient" + creationObj FALSE + multi FALSE) + (object Object "SetPropertiesRule" + quid "3DFE100303A4" + collaborators (list link_list + (object Link + quid "3DFE11D50390" + supplier "StandardContext" + quidu "3DFE0FC502A1" + messages (list Messages + (object Message "//Using BeanUtil, set the object properties (from ex: admin.xml)" + quid "3DFE11D50391" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "3.2.1" + ordinal 7 + quidu "000000000000" + creation FALSE)))) + persistence "Transient" + creationObj FALSE + multi FALSE) + (object Object "StandardContextValve" + quid "3DFE110D0375" + persistence "Transient" + creationObj FALSE + multi FALSE) + (object Object "StandardPipeline" + quid "3DFE112F003F" + persistence "Transient" + creationObj FALSE + multi FALSE) + (object Object "SetNextRule" + quid "3DFE12690267" + persistence "Transient" + creationObj FALSE + multi FALSE))) + (object Mechanism @87 + logical_models (list unit_reference_list + (object Object "StandardContext" + quid "3DFE196D00D9" + collaborators (list link_list + (object Link + quid "3DFE200603BD" + supplier "WebappLoader" + quidu "3DFE1FFA0347" + messages (list Messages + (object Message "new" + quid "3DFE200603BE" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "3.1.1.1" + ordinal 5 + quidu "000000000000" + creation FALSE))) + (object Link + quid "3DFE200C0299" + supplier "StandardContext" + quidu "3DFE196D00D9" + messages (list Messages + (object Message "setLoader" + quid "3DFE200C029A" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "3.1.1.2" + ordinal 6 + quidu "000000000000" + creation FALSE) + (object Message "setManager" + quid "3DFE2032001C" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "3.1.1.4" + ordinal 8 + quidu "000000000000" + creation FALSE) + (object Message "fireLifecycleEvent(START_EVENT)" + quid "3DFE205B01A2" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "3.1.1.5" + ordinal 9 + quidu "000000000000" + creation FALSE))) + (object Link + quid "3DFE202C024F" + supplier "StandardManager" + quidu "3DFE201F0105" + messages (list Messages + (object Message "new" + quid "3DFE202C0250" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "3.1.1.3" + ordinal 7 + quidu "000000000000" + creation FALSE) + (object Message "start()" + quid "3DFE20B600E5" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "3.1.1.7" + ordinal 12 + quidu "000000000000" + creation FALSE))) + (object Link + quid "3DFE20960002" + supplier "ContextConfig" + quidu "3DFE2087028C" + messages (list Messages + (object Message " // Notify interested LifecycleListeners" + quid "3DFE20960003" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "3.1.1.6" + ordinal 10 + quidu "000000000000" + creation FALSE)))) + persistence "Transient" + creationObj FALSE + multi FALSE) + (object Object "StandardHostDeployer" + quid "3DFE1D8A02DC" + collaborators (list link_list + (object Link + quid "3DFE1FAF0014" + supplier "StandardHost" + quidu "3DFE1DF20141" + messages (list Messages + (object Message "addChild" + quid "3DFE1FB60277" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "3.1" + ordinal 3 + quidu "000000000000" + creation FALSE)))) + persistence "Transient" + creationObj FALSE + multi FALSE) + (object Object "StandardHost" + quid "3DFE1DF20141" + collaborators (list link_list + (object Link + quid "3DFE1FC40227" + supplier "StandardContext" + quidu "3DFE196D00D9" + messages (list Messages + (object Message "start()" + quid "3DFE1FC40228" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "3.1.1" + ordinal 4 + quidu "000000000000" + creation FALSE)))) + persistence "Transient" + creationObj FALSE + multi FALSE) + (object Object "WebappLoader" + quid "3DFE1FFA0347" + persistence "Transient" + creationObj FALSE + multi FALSE) + (object Object "StandardManager" + quid "3DFE201F0105" + persistence "Transient" + creationObj FALSE + multi FALSE) + (object Object "ContextConfig" + quid "3DFE2087028C" + collaborators (list link_list + (object Link + quid "3DFE20CF018B" + supplier "ContextConfig" + quidu "3DFE2087028C" + messages (list Messages + (object Message "start()" + quid "3DFE20CF018C" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "3.1.1.6.1" + ordinal 11 + quidu "000000000000" + creation FALSE) + (object Message "defaultConfig()" + quid "3DFE20E303E2" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "3.1.1.6.2" + ordinal 13 + quidu "000000000000" + creation FALSE) + (object Message "applicationConfig()" + quid "3DFE211D01A1" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "3.1.1.6.3" + ordinal 14 + Operation "applicationConfig" + quidu "000000000000" + creation FALSE))) + (object Link + quid "3DFE21B60287" + supplier "Digester" + quidu "3DFE13960364" + messages (list Messages + (object Message "create()" + quid "3DFE21B60288" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "3.1.1.6.3.1" + ordinal 15 + quidu "000000000000" + creation FALSE) + (object Message "createWarpper() // Invoked by a WebWrapperRule (not Directly by the Digester)" + quid "3DFE228B03BA" + frequency "Aperiodic" + synchronization "Simple" + dir "ToClientFromSupplier" + sequence "3.1.1.6.3.1.2" + ordinal 17 + Operation "createWarpper() // Invoked by a Rule (not Directly by the Digester)" + quidu "000000000000" + creation FALSE))) + (object Link + quid "3DFE22560061" + supplier "StandardWrapper" + quidu "3DFE220C0122" + messages (list Messages + (object Message "new" + quid "3DFE229A0004" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "3.1.1.6.3.1.2.1" + ordinal 18 + quidu "000000000000" + creation FALSE) + (object Message "addInstanceListener()" + quid "3DFE22A700C1" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "3.1.1.6.3.2" + ordinal 19 + Operation "addInstanceListener" + quidu "000000000000" + creation FALSE) + (object Message "addLifecycleListener()" + quid "3DFE22C701CC" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "3.1.1.6.3.3" + ordinal 20 + quidu "000000000000" + creation FALSE) + (object Message "addContainerListener()" + quid "3DFE22E80364" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "3.1.1.6.3.4" + ordinal 21 + quidu "000000000000" + creation FALSE)))) + persistence "Transient" + creationObj TRUE + multi FALSE) + (object Object "Digester" + quid "3DFE13960364" + collaborators (list link_list + (object Link + quid "3DFE19AE0064" + supplier "Digester" + quidu "3DFE13960364" + messages (list Messages + (object Message "parse" + quid "3DFE19AE0065" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "1" + ordinal 0 + quidu "000000000000" + creation FALSE) + (object Message "startElement()" + quid "3DFE19B102E9" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "2" + ordinal 1 + quidu "000000000000" + creation FALSE) + (object Message "// Process web.xml * tld.xml" + quid "3DFE21BE021B" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "3.1.1.6.3.1.1" + ordinal 16 + quidu "000000000000" + creation FALSE))) + (object Link + quid "3DFE1DFB0021" + supplier "StandardHostDeployer" + quidu "3DFE1D8A02DC" + messages (list Messages + (object Message "addChild" + quid "3DFE1DFB0022" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "3" + ordinal 2 + quidu "000000000000" + creation FALSE))) + (object Link + quid "3DFE22190225" + supplier "StandardWrapper" + quidu "3DFE220C0122")) + persistence "Transient" + creationObj FALSE + multi FALSE) + (object Object "StandardWrapper" + quid "3DFE220C0122" + persistence "Transient" + creationObj FALSE + multi FALSE))) + (object Mechanism @88 + logical_models (list unit_reference_list + (object Object "ThreadPool" + quid "3DFE402B02C5" + collaborators (list link_list + (object Link + quid "3DFE40E701AD" + supplier "TcpWorkerThread" + quidu "3DFE403200F8" + messages (list Messages + (object Message "runIt()" + quid "3DFE40E701AE" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "1" + ordinal 0 + quidu "000000000000" + creation FALSE)))) + persistence "Transient" + creationObj FALSE + multi FALSE) + (object Object "TcpWorkerThread" + quid "3DFE403200F8" + collaborators (list link_list + (object Link + quid "3DFE40FC010D" + supplier "Http11Protocol" + quidu "3DFE40750177" + messages (list Messages + (object Message "processConnection" + quid "3DFE40FC010E" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "1.1" + ordinal 1 + quidu "000000000000" + creation FALSE)))) + persistence "Transient" + creationObj FALSE + multi FALSE) + (object Object "Http11Protocol" + quid "3DFE40750177" + collaborators (list link_list + (object Link + quid "3DFE4111029E" + supplier "Http11Protocol" + quidu "3DFE40750177" + messages (list Messages + (object Message "process()" + quid "3DFE4111029F" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "1.1.1" + ordinal 2 + quidu "000000000000" + creation FALSE) + (object Message "parseHeaders()" + quid "3DFE415C0151" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "2" + ordinal 3 + quidu "000000000000" + creation FALSE) + (object Message "prepareRequest()" + quid "3DFE41A60161" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "3" + ordinal 4 + quidu "000000000000" + creation FALSE))) + (object Link + quid "3DFE41D60106" + supplier "CoyoteAdapter" + quidu "3DFE410600DF" + messages (list Messages + (object Message "service()" + quid "3DFE41D60107" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "4" + ordinal 5 + quidu "000000000000" + creation FALSE)))) + persistence "Transient" + creationObj FALSE + multi FALSE) + (object Object "CoyoteAdapter" + quid "3DFE410600DF" + collaborators (list link_list + (object Link + quid "3DFE422C01F0" + supplier "CoyoteAdapter" + quidu "3DFE410600DF" + messages (list Messages + (object Message "postParseRequest()" + quid "3DFE422C01F1" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "5" + ordinal 6 + quidu "000000000000" + creation FALSE))) + (object Link + quid "3DFE42800237" + supplier "StandardEngine" + quidu "3DFE424B0349" + messages (list Messages + (object Message "invoke()" + quid "3DFE42800238" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "6" + ordinal 7 + quidu "000000000000" + creation FALSE)))) + persistence "Transient" + creationObj FALSE + multi FALSE) + (object Object "StandardEngine" + quid "3DFE424B0349" + collaborators (list link_list + (object Link + quid "3DFE429A002C" + supplier "StandardPipeline" + quidu "3DFE42900045" + messages (list Messages + (object Message "invoke()" + quid "3DFE429A002D" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "6.1" + ordinal 8 + Operation "invoke" + quidu "000000000000" + creation FALSE)))) + persistence "Transient" + creationObj FALSE + multi FALSE) + (object Object "StandardPipeline" + quid "3DFE42900045" + collaborators (list link_list + (object Link + quid "3DFE42CE022F" + supplier "StandardValveContext" + quidu "3DFE42C002B1" + messages (list Messages + (object Message "invoke()" + quid "3DFE42CE0230" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "6.1.1" + ordinal 9 + quidu "000000000000" + creation FALSE)))) + persistence "Transient" + creationObj FALSE + multi FALSE) + (object Object "StandardValveContext" + quid "3DFE42C002B1" + persistence "Transient" + creationObj FALSE + multi FALSE))) + (object Mechanism @89 + logical_models (list unit_reference_list + (object Object "StandardContextValve" + quid "3DFE4307001E" + collaborators (list link_list + (object Link + quid "3DFE434C019A" + supplier "StandardEngineValve" + quidu "3DFE432801F3" + messages (list Messages + (object Message "invoke()" + quid "3DFE434C019B" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "1" + ordinal 0 + quidu "000000000000" + creation FALSE))) + (object Link + quid "3DFE43C203A3" + supplier "ErrorReportValve" + quidu "3DFE438C028D" + messages (list Messages + (object Message "invoke()" + quid "3DFE43C203A4" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "3" + ordinal 4 + quidu "000000000000" + creation FALSE) + (object Message "invokeNext()" + quid "3DFE46330293" + frequency "Aperiodic" + synchronization "Simple" + dir "ToClientFromSupplier" + sequence "3.2" + ordinal 6 + quidu "000000000000" + creation FALSE))) + (object Link + quid "3DFE46E70025" + supplier "ErrorDispatcherValve" + quidu "3DFE451F01EC" + messages (list Messages + (object Message "invoke()" + quid "3DFE46E70026" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "4" + ordinal 7 + quidu "000000000000" + creation FALSE) + (object Message "invokeNext" + quid "3DFE475D03A0" + frequency "Aperiodic" + synchronization "Simple" + dir "ToClientFromSupplier" + sequence "4.1" + ordinal 8 + quidu "000000000000" + creation FALSE))) + (object Link + quid "3DFE476503C9" + supplier "StandardHostValve" + quidu "3DFE47310130" + messages (list Messages + (object Message "invoke()" + quid "3DFE476503CA" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "5" + ordinal 9 + quidu "000000000000" + creation FALSE)))) + persistence "Transient" + creationObj FALSE + multi FALSE) + (object Object "StandardEngineValve" + quid "3DFE432801F3" + collaborators (list link_list + (object Link + quid "3DFE436C009C" + supplier "StandardHost" + quidu "3DFE436503BD" + messages (list Messages + (object Message "map()" + quid "3DFE436C009D" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "1.1" + ordinal 1 + quidu "000000000000" + creation FALSE) + (object Message "invoke()" + quid "3DFE43830063" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "1.2" + ordinal 2 + quidu "000000000000" + creation FALSE))) + (object Link + quid "3DFE437F0143" + supplier "StandardEngineValve" + quidu "3DFE432801F3")) + persistence "Transient" + creationObj FALSE + multi FALSE) + (object Object "StandardHost" + quid "3DFE436503BD" + collaborators (list link_list + (object Link + quid "3DFE43B903BE" + supplier "StandardContextValve" + quidu "3DFE4307001E" + messages (list Messages + (object Message "invoke()" + quid "3DFE43B903BF" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "2" + ordinal 3 + quidu "000000000000" + creation FALSE)))) + persistence "Transient" + creationObj FALSE + multi FALSE) + (object Object "ErrorReportValve" + quid "3DFE438C028D" + collaborators (list link_list + (object Link + quid "3DFE442501B0" + supplier "ErrorReportValve" + quidu "3DFE438C028D" + messages (list Messages + (object Message "report()" + quid "3DFE442501B1" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "3.1" + ordinal 5 + quidu "000000000000" + creation FALSE))) + (object Link + quid "3DFE452A00F7" + supplier "ErrorDispatcherValve" + quidu "3DFE451F01EC")) + persistence "Transient" + creationObj FALSE + multi FALSE) + (object Object "ErrorDispatcherValve" + quid "3DFE451F01EC" + collaborators (list link_list + (object Link + quid "3DFE47500148" + supplier "StandardHostValve" + quidu "3DFE47310130") + (object Link + quid "3DFE47580335" + supplier "ErrorDispatcherValve" + quidu "3DFE451F01EC")) + persistence "Transient" + creationObj FALSE + multi FALSE) + (object Object "StandardHostValve" + quid "3DFE47310130" + collaborators (list link_list + (object Link + quid "3DFE47CD0166" + supplier "StandardHostValve" + quidu "3DFE47310130" + messages (list Messages + (object Message "map() //Context" + quid "3DFE47CD0167" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "5.1" + ordinal 10 + quidu "000000000000" + creation FALSE))) + (object Link + quid "3DFE47D500B3" + supplier "StandardContext" + quidu "3DFE47C100F1" + messages (list Messages + (object Message "invoke()" + quid "3DFE47D500B4" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "5.2" + ordinal 11 + quidu "000000000000" + creation FALSE)))) + persistence "Transient" + creationObj FALSE + multi FALSE) + (object Object "StandardContext" + quid "3DFE47C100F1" + persistence "Transient" + creationObj FALSE + multi FALSE))) + (object Mechanism @90 + logical_models (list unit_reference_list + (object Object "StandardContext" + quid "3DFE48B001D1" + collaborators (list link_list + (object Link + quid "3DFE48BE0267" + supplier "StandardPipeline" + quidu "3DFE48B80088" + messages (list Messages + (object Message "invoke()" + quid "3DFE48BE0268" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "1" + ordinal 0 + quidu "000000000000" + creation FALSE)))) + persistence "Transient" + creationObj FALSE + multi FALSE) + (object Object "StandardPipeline" + quid "3DFE48B80088" + collaborators (list link_list + (object Link + quid "3DFE48EA0039" + supplier "StandardValveContext" + quidu "3DFE48D000DC" + messages (list Messages + (object Message "invoke()" + quid "3DFE48EA003A" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "1.1" + ordinal 1 + quidu "000000000000" + creation FALSE) + (object Message "invoke()" + quid "3DFE4976015D" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "1.2" + ordinal 6 + quidu "000000000000" + creation FALSE)))) + persistence "Transient" + creationObj FALSE + multi FALSE) + (object Object "StandardValveContext" + quid "3DFE48D000DC" + collaborators (list link_list + (object Link + quid "3DFE491102D5" + supplier "StandardContextValve" + quidu "3DFE490303A7" + messages (list Messages + (object Message "invoke()" + quid "3DFE491102D6" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "1.1.1" + ordinal 2 + quidu "000000000000" + creation FALSE))) + (object Link + quid "3DFE4993023B" + supplier "StandardWrapperValve" + quidu "3DFE49890056" + messages (list Messages + (object Message "invoke()" + quid "3DFE4993023C" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "1.2.1" + ordinal 7 + quidu "000000000000" + creation FALSE)))) + persistence "Transient" + creationObj FALSE + multi FALSE) + (object Object "StandardContextValve" + quid "3DFE490303A7" + collaborators (list link_list + (object Link + quid "3DFE492F033C" + supplier "StandardContextValve" + quidu "3DFE490303A7" + messages (list Messages + (object Message "map //return Wrapper" + quid "3DFE492F033D" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "1.1.1.1" + ordinal 3 + quidu "000000000000" + creation FALSE))) + (object Link + quid "3DFE494A0150" + supplier "StandardWrapper" + quidu "3DFE49370351" + messages (list Messages + (object Message "invoke()" + quid "3DFE494A0151" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "1.1.1.2" + ordinal 4 + Operation "invoke" + quidu "000000000000" + creation FALSE)))) + persistence "Transient" + creationObj FALSE + multi FALSE) + (object Object "StandardWrapper" + quid "3DFE49370351" + collaborators (list link_list + (object Link + quid "3DFE495F0287" + supplier "StandardPipeline" + quidu "3DFE48B80088" + messages (list Messages + (object Message "invoke()" + quid "3DFE495F0288" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "1.1.1.2.1" + ordinal 5 + quidu "000000000000" + creation FALSE)))) + persistence "Transient" + creationObj FALSE + multi FALSE) + (object Object "StandardWrapperValve" + quid "3DFE49890056" + collaborators (list link_list + (object Link + quid "3DFE49DB018A" + supplier "StandardWrapperValve" + quidu "3DFE49890056") + (object Link + quid "3DFE49EC004E" + supplier "StandardWrapper" + quidu "3DFE49370351" + messages (list Messages + (object Message "allocate()" + quid "3DFE49EC004F" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "1.2.1.1" + ordinal 8 + quidu "000000000000" + creation FALSE) + (object Message "return servlet" + quid "3DFE4A200067" + frequency "Aperiodic" + synchronization "Return" + dir "ToClientFromSupplier" + sequence "1.2.1.1.1" + ordinal 9 + quidu "000000000000" + creation FALSE))) + (object Link + quid "3DFE4A29027D" + supplier "ApplicationFilterChain" + quidu "3DFE4A1500B2" + messages (list Messages + (object Message "createFilterChain()" + quid "3DFE4A29027E" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "1.2.1.1.1.1" + ordinal 10 + quidu "000000000000" + creation FALSE) + (object Message "doFilter()" + quid "3DFE4A490283" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "1.2.1.2" + ordinal 11 + Operation "doFilter" + quidu "000000000000" + creation FALSE) + (object Message "return" + quid "3DFE4CB4025B" + frequency "Aperiodic" + synchronization "Return" + dir "ToClientFromSupplier" + sequence "1.2.1.2.3" + ordinal 14 + quidu "000000000000" + creation FALSE)))) + persistence "Transient" + creationObj FALSE + multi FALSE) + (object Object "ApplicationFilterChain" + quid "3DFE4A1500B2" + collaborators (list link_list + (object Link + quid "3DFE4C2701C2" + supplier "ApplicationFilterChain" + quidu "3DFE4A1500B2" + messages (list Messages + (object Message "internalDoFilter()" + quid "3DFE4C2701C3" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "1.2.1.2.1" + ordinal 12 + quidu "000000000000" + creation FALSE))) + (object Link + quid "3DFE4CA502BE" + supplier "$UNNAMED$0" + quidu "3DFE4BAE0056" + messages (list Messages + (object Message "service()" + quid "3DFE4CA502BF" + frequency "Aperiodic" + synchronization "Simple" + dir "FromClientToSupplier" + sequence "1.2.1.2.2" + ordinal 13 + quidu "000000000000" + creation FALSE)))) + persistence "Transient" + creationObj FALSE + multi FALSE) + (object Object "$UNNAMED$0" + quid "3DFE4BAE0056" + stereotype "Servlet" + persistence "Transient" + creationObj TRUE + multi FALSE)))) + logical_presentations (list unit_reference_list + (object ClassDiagram "Main" + quid "3DFDF6D2021B" + title "Main" + zoom 100 + max_height 28350 + max_width 21600 + origin_x 0 + origin_y 0 + items (list diagram_item_list)) + (object ClassDiagram "high level packaging" + quid "3E42DE75004B" + title "high level packaging" + zoom 100 + max_height 28350 + max_width 21600 + origin_x 0 + origin_y 0 + items (list diagram_item_list + (object CategoryView "Logical View::org.apache.catalina" @91 + location (1024, 752) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @91 + location (780, 668) + fill_color 13434879 + nlines 2 + max_width 488 + justify 0 + label "org.apache.catalina") + icon_style "Icon" + line_color 3342489 + fill_color 13434879 + quidu "3E42DE8D0082" + width 500 + height 181) + (object CategoryView "Logical View::org.apache.coyote" @92 + location (512, 1184) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @92 + location (237, 1090) + fill_color 13434879 + nlines 2 + max_width 550 + justify 0 + label "org.apache.coyote") + icon_style "Icon" + line_color 3342489 + fill_color 13434879 + quidu "3E42DE9F0132" + width 563 + height 200) + (object CategoryView "Logical View::org.apache.tomcat.util" @93 + location (1920, 1104) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @93 + location (1670, 1020) + fill_color 13434879 + nlines 2 + max_width 500 + justify 0 + label "org.apache.tomcat.util") + icon_style "Icon" + line_color 3342489 + fill_color 13434879 + quidu "3E42DEDF01F2" + width 512 + height 181) + (object ImportView "" @94 + stereotype TRUE + line_color 3342489 + quidu "3E42DEF601EB" + client @91 + supplier @93 + line_style 0) + (object ImportView "" @95 + stereotype TRUE + line_color 3342489 + quidu "3E42DEFC00B3" + client @92 + supplier @93 + line_style 0) + (object CategoryView "Logical View::org.apache.jasper" @96 + location (1728, 624) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @96 + location (1437, 540) + fill_color 13434879 + nlines 2 + max_width 582 + justify 0 + label "org.apache.jasper") + icon_style "Icon" + line_color 3342489 + fill_color 13434879 + quidu "3E42DEFF0270" + width 594 + height 181) + (object ImportView "" @97 + stereotype TRUE + line_color 3342489 + quidu "3E42DF700060" + client @91 + supplier @92 + line_style 0) + (object NoteView @98 + location (1200, 208) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @98 + location (847, 143) + fill_color 13434879 + nlines 2 + max_width 671 + label "High Level package dependencies") + line_color 3342489 + fill_color 13434879 + width 731 + height 143) + (object CategoryView "Logical View::org.apache.naming" @99 + location (352, 304) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @99 + location (83, 220) + fill_color 13434879 + nlines 2 + max_width 538 + justify 0 + label "org.apache.naming") + icon_style "Icon" + line_color 3342489 + fill_color 13434879 + quidu "3E43D1580339" + width 550 + height 181) + (object ImportView "" @100 + stereotype TRUE + line_color 3342489 + quidu "3E43D165039C" + client @91 + supplier @99 + line_style 0))) + (object InteractionDiagram "1. catalina_load" + mechanism_ref @82 + quid "3DFDF8EE0267" + title "1. catalina_load" + zoom 100 + max_height 28350 + max_width 21600 + origin_x 0 + origin_y 519 + items (list diagram_item_list + (object InterObjView "Bootstrap" @101 + location (224, 224) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline TRUE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @101 + location (224, 224) + fill_color 13434879 + anchor_loc 1 + nlines 2 + max_width 282 + justify 0 + label "Bootstrap") + icon_style "Icon" + line_color 3342489 + fill_color 13434879 + quidu "3DFDF8FD0345" + width 300 + height 1972 + icon_height 0 + icon_width 0 + icon_y_offset 0 + annotation 1 + Focus_Of_Control (object Focus_Of_Control "" @102 + location (224, 368) + line_color 3342489 + InterObjView @101 + height 1738 + y_coord 1678 + Nested FALSE) + Focus_Of_Control (object Focus_Of_Control "" @103 + location (224, 368) + line_color 3342489 + InterObjView @101 + height 60 + y_coord 0 + Nested TRUE)) + (object InterObjView "Digester" @104 + location (896, 224) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline TRUE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @104 + location (896, 224) + fill_color 13434879 + anchor_loc 1 + nlines 2 + max_width 282 + justify 0 + label "Digester") + icon_style "Icon" + line_color 3342489 + fill_color 13434879 + quidu "3DFDFAF201A1" + width 300 + height 1972 + icon_height 0 + icon_width 0 + icon_y_offset 0 + annotation 1 + Focus_Of_Control (object Focus_Of_Control "" @105 + location (896, 1232) + line_color 3342489 + InterObjView @104 + height 60 + y_coord 0 + Nested FALSE) + Focus_Of_Control (object Focus_Of_Control "" @106 + location (896, 1312) + line_color 3342489 + InterObjView @104 + height 264 + y_coord 204 + Nested FALSE)) + (object InterObjView "ServerLifecycleListener" @107 + location (1232, 224) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline TRUE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @107 + location (1232, 224) + fill_color 13434879 + anchor_loc 1 + nlines 2 + max_width 282 + justify 0 + label "ServerLifecycleListener") + icon_style "Icon" + line_color 3342489 + fill_color 13434879 + quidu "3DFDFB4B0217" + width 300 + height 1972 + icon_height 0 + icon_width 0 + icon_y_offset 0 + annotation 1 + Focus_Of_Control (object Focus_Of_Control "" @108 + location (1232, 1328) + line_color 3342489 + InterObjView @107 + height 60 + y_coord 0 + Nested FALSE)) + (object InterObjView "GlobalResourcesLifecycleListener" @109 + location (1568, 224) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline TRUE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @109 + location (1568, 224) + fill_color 13434879 + anchor_loc 1 + nlines 2 + max_width 322 + justify 0 + label "GlobalResourcesLifecycleListener") + icon_style "Icon" + line_color 3342489 + fill_color 13434879 + quidu "3DFDFB7A02AB" + width 340 + height 1972 + icon_height 0 + icon_width 0 + icon_y_offset 0 + annotation 1 + Focus_Of_Control (object Focus_Of_Control "" @110 + location (1568, 1456) + line_color 3342489 + InterObjView @109 + height 60 + y_coord 0 + Nested FALSE)) + (object InterObjView "SecurityConfig" @111 + location (1920, 224) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline TRUE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @111 + location (1920, 224) + fill_color 13434879 + anchor_loc 1 + nlines 2 + max_width 282 + justify 0 + label "SecurityConfig") + icon_style "Icon" + line_color 3342489 + fill_color 13434879 + quidu "3DFDFBD802BA" + width 300 + height 1972 + icon_height 0 + icon_width 0 + icon_y_offset 0 + annotation 1 + Focus_Of_Control (object Focus_Of_Control "" @112 + location (1920, 1600) + line_color 3342489 + InterObjView @111 + height 60 + y_coord 0 + Nested FALSE) + Focus_Of_Control (object Focus_Of_Control "" @113 + location (1920, 1680) + line_color 3342489 + InterObjView @111 + height 146 + y_coord 86 + Nested FALSE) + Focus_Of_Control (object Focus_Of_Control "" @114 + location (1920, 1760) + line_color 3342489 + InterObjView @111 + height 60 + y_coord 0 + Nested TRUE)) + (object SelfMessView "" @115 + location (16, 368) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @116 + Parent_View @115 + location (315, 324) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFDF9210009" + anchor_loc 1 + nlines 1 + max_width 340 + justify 0 + label "initClassLoaders()" + pctDist 0.500000 + height 45 + orientation 0) + line_color 3342489 + client @101 + supplier @101 + Focus_Src @102 + Focus_Entry @103 + origin (240, 368) + terminus (390, 368) + ordinal 0) + (object NoteView @117 + location (1152, 1072) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @117 + location (1014, 1012) + fill_color 13434879 + nlines 2 + max_width 240 + label "parse server.xml") + line_color 3342489 + fill_color 13434879 + width 300 + height 132) + (object NoteView @118 + location (1376, 80) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @118 + location (1238, 20) + fill_color 13434879 + nlines 2 + max_width 240 + label "MBeans") + line_color 3342489 + fill_color 13434879 + width 300 + height 132) + (object AttachView "" @119 + stereotype TRUE + line_color 3342489 + client @118 + supplier @107 + line_style 0) + (object AttachView "" @120 + stereotype TRUE + line_color 3342489 + client @109 + supplier @118 + line_style 0) + (object NoteView @121 + location (2160, 2176) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @121 + location (1947, 2113) + fill_color 13434879 + nlines 2 + max_width 390 + label "#1Catalina.load()") + line_color 3342489 + fill_color 13434879 + width 450 + height 138) + (object InterObjView "Catalina" @122 + location (560, 224) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline TRUE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @122 + location (560, 224) + fill_color 13434879 + anchor_loc 1 + nlines 2 + max_width 282 + justify 0 + label "Catalina") + icon_style "Icon" + line_color 3342489 + fill_color 13434879 + quidu "3DFDF90A0330" + width 300 + height 1972 + icon_height 0 + icon_width 0 + icon_y_offset 0 + annotation 1 + Focus_Of_Control (object Focus_Of_Control "" @123 + location (560, 464) + line_color 3342489 + InterObjView @122 + height 60 + y_coord 0 + Nested FALSE) + Focus_Of_Control (object Focus_Of_Control "" @124 + location (560, 608) + line_color 3342489 + InterObjView @122 + height 60 + y_coord 0 + Nested FALSE) + Focus_Of_Control (object Focus_Of_Control "" @125 + location (560, 720) + line_color 3342489 + InterObjView @122 + height 1326 + y_coord 1266 + Nested FALSE) + Focus_Of_Control (object Focus_Of_Control "" @126 + location (560, 896) + line_color 3342489 + InterObjView @122 + height 194 + y_coord 134 + Nested TRUE) + Focus_Of_Control (object Focus_Of_Control "" @127 + location (560, 896) + InterObjView @122 + height 60 + y_coord 0 + Nested TRUE) + Focus_Of_Control (object Focus_Of_Control "" @128 + location (560, 1024) + line_color 3342489 + InterObjView @122 + height 60 + y_coord 0 + Nested TRUE) + Focus_Of_Control (object Focus_Of_Control "" @129 + location (560, 1024) + InterObjView @122 + height 60 + y_coord 0 + Nested TRUE) + Focus_Of_Control (object Focus_Of_Control "" @130 + location (560, 1152) + line_color 3342489 + InterObjView @122 + height 60 + y_coord 0 + Nested TRUE) + Focus_Of_Control (object Focus_Of_Control "" @131 + location (560, 1152) + InterObjView @122 + height 60 + y_coord 0 + Nested TRUE)) + (object SelfMessView "" @132 + location (16, 896) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @133 + Parent_View @132 + location (651, 852) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFDFA8001DA" + anchor_loc 1 + nlines 1 + max_width 160 + justify 0 + label "initDirs()" + pctDist 0.500000 + height 45 + orientation 0) + line_color 3342489 + client @122 + supplier @122 + Focus_Src @127 + Focus_Entry @126 + origin (576, 896) + terminus (726, 896) + ordinal 4) + (object SelfMessView "" @134 + location (16, 1024) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @135 + Parent_View @134 + location (701, 981) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFDFA8B0347" + anchor_loc 1 + nlines 1 + max_width 228 + justify 0 + label "initNaming()" + pctDist 0.840000 + height 44 + orientation 0) + line_color 3342489 + client @122 + supplier @122 + Focus_Src @129 + Focus_Entry @128 + origin (576, 1024) + terminus (726, 1024) + ordinal 5) + (object SelfMessView "" @136 + location (16, 1152) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @137 + Parent_View @136 + location (686, 1109) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFDFAAD01AC" + anchor_loc 1 + nlines 1 + max_width 180 + justify 0 + label "initialize()" + pctDist 0.733333 + height 44 + orientation 0) + line_color 3342489 + client @122 + supplier @122 + Focus_Src @131 + Focus_Entry @130 + origin (576, 1152) + terminus (726, 1152) + ordinal 6) + (object InterMessView "" @138 + location (16, 464) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @139 + Parent_View @138 + location (389, 437) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFDF91A010D" + anchor_loc 1 + nlines 1 + max_width 265 + justify 0 + label "newInstance()" + pctDist 0.495082 + height 28 + orientation 0) + line_color 3342489 + client @101 + supplier @122 + Focus_Src @102 + Focus_Entry @123 + origin (239, 464) + terminus (544, 464) + ordinal 1) + (object InterMessView "" @140 + location (16, 608) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @141 + Parent_View @140 + location (456, 565) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFDF97900C2" + anchor_loc 1 + nlines 1 + max_width 445 + justify 0 + label "setParentClassLoader()" + pctDist 0.711475 + height 44 + orientation 0) + line_color 3342489 + client @101 + supplier @122 + Focus_Src @102 + Focus_Entry @124 + origin (239, 608) + terminus (544, 608) + ordinal 2) + (object InterMessView "" @142 + location (16, 720) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @143 + Parent_View @142 + location (391, 676) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFDFA3402F2" + anchor_loc 1 + nlines 1 + max_width 108 + justify 0 + label "load()" + pctDist 0.500000 + height 45 + orientation 0) + line_color 3342489 + client @101 + supplier @122 + Focus_Src @102 + Focus_Entry @125 + origin (239, 720) + terminus (544, 720) + ordinal 3) + (object InterMessView "" @144 + location (16, 1232) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @145 + Parent_View @144 + location (727, 1188) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFDFAF800C4" + anchor_loc 1 + nlines 1 + max_width 302 + justify 0 + label "createDigester()" + pctDist 0.500000 + height 45 + orientation 0) + line_color 3342489 + client @122 + supplier @104 + Focus_Src @125 + Focus_Entry @105 + origin (575, 1232) + terminus (880, 1232) + ordinal 7) + (object InterMessView "" @146 + location (16, 1312) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @147 + Parent_View @146 + location (727, 1268) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFDFB0100B2" + anchor_loc 1 + nlines 1 + max_width 136 + justify 0 + label "parse()" + pctDist 0.500000 + height 45 + orientation 0) + line_color 3342489 + client @122 + supplier @104 + Focus_Src @125 + Focus_Entry @106 + origin (575, 1312) + terminus (880, 1312) + ordinal 8) + (object AttachView "" @148 + stereotype TRUE + line_color 3342489 + client @147 + supplier @117 + line_style 0) + (object InterMessView "" @149 + location (16, 1328) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @150 + Parent_View @149 + location (1063, 1284) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFDFB8400A7" + anchor_loc 1 + nlines 1 + max_width 265 + justify 0 + label "newInstance()" + pctDist 0.500000 + height 45 + orientation 0) + line_color 3342489 + client @104 + supplier @107 + Focus_Src @106 + Focus_Entry @108 + origin (911, 1328) + terminus (1216, 1328) + ordinal 9) + (object InterMessView "" @151 + location (16, 1456) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @152 + Parent_View @151 + location (1231, 1412) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFDFB920148" + anchor_loc 1 + nlines 1 + max_width 265 + justify 0 + label "newInstance()" + pctDist 0.500000 + height 45 + orientation 0) + line_color 3342489 + client @104 + supplier @109 + Focus_Src @106 + Focus_Entry @110 + origin (911, 1456) + terminus (1552, 1456) + ordinal 10) + (object InterMessView "" @153 + location (16, 1600) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @154 + Parent_View @153 + location (1239, 1556) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFDFBEA00C2" + anchor_loc 1 + nlines 1 + max_width 265 + justify 0 + label "newInstance()" + pctDist 0.500000 + height 45 + orientation 0) + line_color 3342489 + client @122 + supplier @111 + Focus_Src @125 + Focus_Entry @112 + origin (575, 1600) + terminus (1904, 1600) + ordinal 11) + (object InterMessView "" @155 + location (16, 1680) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @156 + Parent_View @155 + location (1239, 1636) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFDFBF401F2" + anchor_loc 1 + nlines 1 + max_width 425 + justify 0 + label "setPackageDefinition()" + pctDist 0.500000 + height 45 + orientation 0) + line_color 3342489 + client @122 + supplier @111 + Focus_Src @125 + Focus_Entry @113 + origin (575, 1680) + terminus (1904, 1680) + ordinal 12) + (object InterMessView "" @157 + location (16, 1760) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @158 + Parent_View @157 + location (1239, 1716) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFDFC1203C2" + anchor_loc 1 + nlines 1 + max_width 386 + justify 0 + label "setPackageAccess()" + pctDist 0.500000 + height 45 + orientation 0) + line_color 3342489 + client @122 + supplier @111 + Focus_Src @125 + Focus_Entry @114 + origin (575, 1760) + terminus (1904, 1760) + ordinal 13))) + (object InteractionDiagram "2. catalina_initliaze" + mechanism_ref @83 + quid "3DFDFC44002A" + title "2. catalina_initliaze" + zoom 100 + max_height 28350 + max_width 21600 + origin_x 0 + origin_y 87 + items (list diagram_item_list + (object InterObjView "Catalina" @159 + location (176, 224) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline TRUE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @159 + location (176, 224) + fill_color 13434879 + anchor_loc 1 + nlines 2 + max_width 282 + justify 0 + label "Catalina") + icon_style "Icon" + line_color 3342489 + fill_color 13434879 + quidu "3DFDFC8F015F" + width 300 + height 1180 + icon_height 0 + icon_width 0 + icon_y_offset 0 + annotation 1 + Focus_Of_Control (object Focus_Of_Control "" @160 + location (176, 400) + line_color 3342489 + InterObjView @159 + height 914 + y_coord 854 + Nested FALSE)) + (object InterObjView "StandardServer" @161 + location (496, 224) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline TRUE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @161 + location (496, 224) + fill_color 13434879 + anchor_loc 1 + nlines 2 + max_width 282 + justify 0 + label "StandardServer") + icon_style "Icon" + line_color 3342489 + fill_color 13434879 + quidu "3DFDFCCB006B" + width 300 + height 1180 + icon_height 0 + icon_width 0 + icon_y_offset 0 + annotation 1 + Focus_Of_Control (object Focus_Of_Control "" @162 + location (496, 400) + line_color 3342489 + InterObjView @161 + height 854 + y_coord 794 + Nested FALSE) + Focus_Of_Control (object Focus_Of_Control "" @163 + location (496, 480) + line_color 3342489 + InterObjView @161 + height 768 + y_coord 708 + Nested TRUE)) + (object InterObjView "StandardService" @164 + location (832, 224) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline TRUE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @164 + location (832, 224) + fill_color 13434879 + anchor_loc 1 + nlines 2 + max_width 282 + justify 0 + label "StandardService") + icon_style "Icon" + line_color 3342489 + fill_color 13434879 + quidu "3DFDFD370020" + width 300 + height 1180 + icon_height 0 + icon_width 0 + icon_y_offset 0 + annotation 1 + Focus_Of_Control (object Focus_Of_Control "" @165 + location (832, 480) + line_color 3342489 + InterObjView @164 + height 708 + y_coord 648 + Nested FALSE)) + (object InterObjView "CoyoteConnector" @166 + location (1168, 224) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline TRUE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @166 + location (1168, 224) + fill_color 13434879 + anchor_loc 1 + nlines 2 + max_width 282 + justify 0 + label "CoyoteConnector") + icon_style "Icon" + line_color 3342489 + fill_color 13434879 + quidu "3DFDFE810313" + width 300 + height 1180 + icon_height 0 + icon_width 0 + icon_y_offset 0 + annotation 1 + Focus_Of_Control (object Focus_Of_Control "" @167 + location (1168, 528) + line_color 3342489 + InterObjView @166 + height 600 + y_coord 540 + Nested FALSE)) + (object InterObjView "CoyoteAdapter" @168 + location (1504, 224) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline TRUE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @168 + location (1504, 224) + fill_color 13434879 + anchor_loc 1 + nlines 2 + max_width 282 + justify 0 + label "CoyoteAdapter") + icon_style "Icon" + line_color 3342489 + fill_color 13434879 + quidu "3DFDFFA00226" + width 300 + height 1180 + icon_height 0 + icon_width 0 + icon_y_offset 0 + annotation 1 + Focus_Of_Control (object Focus_Of_Control "" @169 + location (1504, 576) + line_color 3342489 + InterObjView @168 + height 60 + y_coord 0 + Nested FALSE)) + (object InterObjView "Http11Protocol" @170 + location (1808, 224) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline TRUE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @170 + location (1808, 224) + fill_color 13434879 + anchor_loc 1 + nlines 2 + max_width 282 + justify 0 + label "Http11Protocol") + icon_style "Icon" + line_color 3342489 + fill_color 13434879 + quidu "3DFE016601A6" + width 300 + height 1180 + icon_height 0 + icon_width 0 + icon_y_offset 0 + annotation 1 + Focus_Of_Control (object Focus_Of_Control "" @171 + location (1808, 704) + line_color 3342489 + InterObjView @170 + height 60 + y_coord 0 + Nested FALSE) + Focus_Of_Control (object Focus_Of_Control "" @172 + location (1808, 832) + line_color 3342489 + InterObjView @170 + height 60 + y_coord 0 + Nested FALSE)) + (object InterObjView "JkCoyoteAdapter" @173 + location (2144, 224) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline TRUE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @173 + location (2144, 224) + fill_color 13434879 + anchor_loc 1 + nlines 2 + max_width 282 + justify 0 + label "JkCoyoteAdapter") + icon_style "Icon" + line_color 3342489 + fill_color 13434879 + quidu "3DFE01AD01A8" + width 300 + height 1180 + icon_height 0 + icon_width 0 + icon_y_offset 0 + annotation 1 + Focus_Of_Control (object Focus_Of_Control "" @174 + location (2144, 928) + line_color 3342489 + InterObjView @173 + height 60 + y_coord 0 + Nested FALSE) + Focus_Of_Control (object Focus_Of_Control "" @175 + location (2144, 1008) + line_color 3342489 + InterObjView @173 + height 60 + y_coord 0 + Nested FALSE)) + (object InterMessView "" @176 + location (16, 400) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @177 + Parent_View @176 + location (335, 356) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFDFD1F0076" + anchor_loc 1 + nlines 1 + max_width 180 + justify 0 + label "initialize()" + pctDist 0.500000 + height 45 + orientation 0) + line_color 3342489 + client @159 + supplier @161 + Focus_Src @160 + Focus_Entry @162 + origin (191, 400) + terminus (480, 400) + ordinal 0) + (object InterMessView "" @178 + location (16, 480) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @179 + Parent_View @178 + location (663, 436) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFDFD3D01C4" + anchor_loc 1 + nlines 1 + max_width 180 + justify 0 + label "initialize()" + pctDist 0.500000 + height 45 + orientation 0) + line_color 3342489 + client @161 + supplier @164 + Focus_Src @163 + Focus_Entry @165 + origin (511, 480) + terminus (816, 480) + ordinal 1) + (object InterMessView "" @180 + location (16, 528) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @181 + Parent_View @180 + location (999, 484) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFDFE990305" + anchor_loc 1 + nlines 1 + max_width 180 + justify 0 + label "initialize()" + pctDist 0.500000 + height 45 + orientation 0) + line_color 3342489 + client @164 + supplier @166 + Focus_Src @165 + Focus_Entry @167 + origin (847, 528) + terminus (1152, 528) + ordinal 2) + (object InterMessView "" @182 + location (16, 576) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @183 + Parent_View @182 + location (1335, 532) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE013D0217" + anchor_loc 1 + nlines 1 + max_width 106 + justify 0 + label "new()" + pctDist 0.500000 + height 45 + orientation 0) + line_color 3342489 + client @166 + supplier @168 + Focus_Src @167 + Focus_Entry @169 + origin (1183, 576) + terminus (1488, 576) + ordinal 3) + (object InterMessView "" @184 + location (1504, 704) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @185 + Parent_View @184 + location (1487, 660) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE01830330" + anchor_loc 1 + nlines 1 + max_width 106 + justify 0 + label "new()" + pctDist 0.500000 + height 45 + orientation 0) + line_color 3342489 + client @166 + supplier @170 + Focus_Src @167 + Focus_Entry @171 + origin (1183, 704) + terminus (1792, 704) + ordinal 4) + (object InterMessView "" @186 + location (1504, 832) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @187 + Parent_View @186 + location (1487, 788) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE0188032C" + anchor_loc 1 + nlines 1 + max_width 80 + justify 0 + label "init()" + pctDist 0.500000 + height 45 + orientation 0) + line_color 3342489 + client @166 + supplier @170 + Focus_Src @167 + Focus_Entry @172 + origin (1183, 832) + terminus (1792, 832) + ordinal 5) + (object InterMessView "" @188 + location (16, 928) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @189 + Parent_View @188 + location (1655, 884) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE01BC038C" + anchor_loc 1 + nlines 1 + max_width 106 + justify 0 + label "new()" + pctDist 0.500000 + height 45 + orientation 0) + line_color 3342489 + client @166 + supplier @173 + Focus_Src @167 + Focus_Entry @174 + origin (1183, 928) + terminus (2128, 928) + ordinal 6) + (object InterMessView "" @190 + location (16, 1008) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @191 + Parent_View @190 + location (1655, 964) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE01C30164" + anchor_loc 1 + nlines 1 + max_width 80 + justify 0 + label "init()" + pctDist 0.500000 + height 45 + orientation 0) + line_color 3342489 + client @166 + supplier @173 + Focus_Src @167 + Focus_Entry @175 + origin (1183, 1008) + terminus (2128, 1008) + ordinal 7) + (object NoteView @192 + location (2144, 2016) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @192 + location (1947, 1957) + fill_color 13434879 + nlines 2 + max_width 359 + label "#2 Catalina.initialize()") + line_color 3342489 + fill_color 13434879 + width 419 + height 131))) + (object InteractionDiagram "3. catalina_start" + mechanism_ref @84 + quid "3DFE026D02D1" + title "3. catalina_start" + zoom 100 + max_height 28350 + max_width 21600 + origin_x 0 + origin_y 2481 + items (list diagram_item_list + (object InterObjView "Bootstrap" @193 + location (192, 224) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline TRUE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @193 + location (192, 224) + fill_color 13434879 + anchor_loc 1 + nlines 2 + max_width 282 + justify 0 + label "Bootstrap") + icon_style "Icon" + line_color 3342489 + fill_color 13434879 + quidu "3DFE027700F5" + width 300 + height 2912 + icon_height 0 + icon_width 0 + icon_y_offset 0 + annotation 1 + Focus_Of_Control (object Focus_Of_Control "" @194 + location (192, 384) + line_color 3342489 + InterObjView @193 + height 2662 + y_coord 2602 + Nested FALSE)) + (object InterObjView "Catalina" @195 + location (480, 224) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline TRUE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @195 + location (480, 224) + fill_color 13434879 + anchor_loc 1 + nlines 2 + max_width 282 + justify 0 + label "Catalina") + icon_style "Icon" + line_color 3342489 + fill_color 13434879 + quidu "3DFE027D0067" + width 300 + height 2912 + icon_height 0 + icon_width 0 + icon_y_offset 0 + annotation 1 + Focus_Of_Control (object Focus_Of_Control "" @196 + location (480, 384) + line_color 3342489 + InterObjView @195 + height 2602 + y_coord 2542 + Nested FALSE)) + (object InterObjView "StandardServer" @197 + location (784, 224) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline TRUE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @197 + location (784, 224) + fill_color 13434879 + anchor_loc 1 + nlines 2 + max_width 282 + justify 0 + label "StandardServer") + icon_style "Icon" + line_color 3342489 + fill_color 13434879 + quidu "3DFE02B30015" + width 300 + height 2912 + icon_height 0 + icon_width 0 + icon_y_offset 0 + annotation 1 + Focus_Of_Control (object Focus_Of_Control "" @198 + location (784, 416) + line_color 3342489 + InterObjView @197 + height 2510 + y_coord 2450 + Nested FALSE) + Focus_Of_Control (object Focus_Of_Control "" @199 + location (784, 480) + line_color 3342489 + InterObjView @197 + height 60 + y_coord 0 + Nested TRUE) + Focus_Of_Control (object Focus_Of_Control "" @200 + location (784, 592) + line_color 3342489 + InterObjView @197 + height 60 + y_coord 0 + Nested TRUE)) + (object InterObjView "StandardService" @201 + location (1088, 224) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline TRUE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @201 + location (1088, 224) + fill_color 13434879 + anchor_loc 1 + nlines 2 + max_width 282 + justify 0 + label "StandardService") + icon_style "Icon" + line_color 3342489 + fill_color 13434879 + quidu "3DFE030400E3" + width 300 + height 2912 + icon_height 0 + icon_width 0 + icon_y_offset 0 + annotation 1 + Focus_Of_Control (object Focus_Of_Control "" @202 + location (1088, 704) + line_color 3342489 + InterObjView @201 + height 2162 + y_coord 2102 + Nested FALSE) + Focus_Of_Control (object Focus_Of_Control "" @203 + location (1088, 752) + line_color 3342489 + InterObjView @201 + height 60 + y_coord 0 + Nested TRUE) + Focus_Of_Control (object Focus_Of_Control "" @204 + location (1088, 864) + line_color 3342489 + InterObjView @201 + height 60 + y_coord 0 + Nested TRUE)) + (object InterObjView "StandardEngine" @205 + location (1424, 224) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline TRUE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @205 + location (1424, 224) + fill_color 13434879 + anchor_loc 1 + nlines 2 + max_width 332 + justify 0 + label "StandardEngine") + icon_style "Icon" + line_color 3342489 + fill_color 13434879 + quidu "3DFE034700C2" + width 350 + height 2912 + icon_height 0 + icon_width 0 + icon_y_offset 0 + annotation 1 + Focus_Of_Control (object Focus_Of_Control "" @206 + location (1424, 976) + line_color 3342489 + InterObjView @205 + height 1830 + y_coord 1770 + Nested FALSE) + Focus_Of_Control (object Focus_Of_Control "" @207 + location (1424, 1056) + line_color 3342489 + InterObjView @205 + height 1744 + y_coord 1684 + Nested TRUE) + Focus_Of_Control (object Focus_Of_Control "" @208 + location (1424, 1056) + line_color 3342489 + InterObjView @205 + height 60 + y_coord 0 + Nested TRUE) + Focus_Of_Control (object Focus_Of_Control "" @209 + location (1424, 1168) + line_color 3342489 + InterObjView @205 + height 60 + y_coord 0 + Nested TRUE) + Focus_Of_Control (object Focus_Of_Control "" @210 + location (1424, 1296) + line_color 3342489 + InterObjView @205 + height 60 + y_coord 0 + Nested TRUE) + Focus_Of_Control (object Focus_Of_Control "" @211 + location (1424, 1408) + line_color 3342489 + InterObjView @205 + height 60 + y_coord 0 + Nested TRUE) + Focus_Of_Control (object Focus_Of_Control "" @212 + location (1424, 1536) + line_color 3342489 + InterObjView @205 + height 60 + y_coord 0 + Nested TRUE) + Focus_Of_Control (object Focus_Of_Control "" @213 + location (1424, 1648) + line_color 3342489 + InterObjView @205 + height 60 + y_coord 0 + Nested TRUE)) + (object InterObjView "StandardHost" @214 + location (1760, 224) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline TRUE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @214 + location (1760, 224) + fill_color 13434879 + anchor_loc 1 + nlines 2 + max_width 282 + justify 0 + label "StandardHost") + icon_style "Icon" + line_color 3342489 + fill_color 13434879 + quidu "3DFE03F2035D" + width 300 + height 2912 + icon_height 0 + icon_width 0 + icon_y_offset 0 + annotation 1 + Focus_Of_Control (object Focus_Of_Control "" @215 + location (1760, 1760) + line_color 3342489 + InterObjView @214 + height 980 + y_coord 920 + Nested FALSE) + Focus_Of_Control (object Focus_Of_Control "" @216 + location (1760, 1808) + line_color 3342489 + InterObjView @214 + height 60 + y_coord 0 + Nested TRUE) + Focus_Of_Control (object Focus_Of_Control "" @217 + location (1760, 1920) + line_color 3342489 + InterObjView @214 + height 60 + y_coord 0 + Nested TRUE) + Focus_Of_Control (object Focus_Of_Control "" @218 + location (1760, 2032) + line_color 3342489 + InterObjView @214 + height 60 + y_coord 0 + Nested TRUE) + Focus_Of_Control (object Focus_Of_Control "" @219 + location (1760, 2144) + line_color 3342489 + InterObjView @214 + height 60 + y_coord 0 + Nested TRUE) + Focus_Of_Control (object Focus_Of_Control "" @220 + location (1760, 2256) + line_color 3342489 + InterObjView @214 + height 60 + y_coord 0 + Nested TRUE)) + (object InterObjView "StandardPipeline" @221 + location (2080, 224) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline TRUE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @221 + location (2080, 224) + fill_color 13434879 + anchor_loc 1 + nlines 2 + max_width 326 + justify 0 + label "StandardPipeline") + icon_style "Icon" + line_color 3342489 + fill_color 13434879 + quidu "3DFE047D006D" + width 344 + height 2912 + icon_height 0 + icon_width 0 + icon_y_offset 0 + annotation 1 + Focus_Of_Control (object Focus_Of_Control "" @222 + location (2080, 2368) + line_color 3342489 + InterObjView @221 + height 312 + y_coord 252 + Nested FALSE) + Focus_Of_Control (object Focus_Of_Control "" @223 + location (2080, 2416) + line_color 3342489 + InterObjView @221 + height 60 + y_coord 0 + Nested TRUE) + Focus_Of_Control (object Focus_Of_Control "" @224 + location (2080, 2480) + line_color 3342489 + InterObjView @221 + height 60 + y_coord 0 + Nested TRUE) + Focus_Of_Control (object Focus_Of_Control "" @225 + location (2080, 2560) + line_color 3342489 + InterObjView @221 + height 60 + y_coord 0 + Nested TRUE)) + (object InterMessView "" @226 + location (16, 384) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @227 + Parent_View @226 + location (335, 340) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE02830374" + anchor_loc 1 + nlines 1 + max_width 110 + justify 0 + label "start()" + pctDist 0.500000 + height 45 + orientation 0) + line_color 3342489 + client @193 + supplier @195 + Focus_Src @194 + Focus_Entry @196 + origin (207, 384) + terminus (464, 384) + ordinal 0) + (object InterMessView "" @228 + location (16, 416) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @229 + Parent_View @228 + location (631, 372) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE02BA0188" + anchor_loc 1 + nlines 1 + max_width 110 + justify 0 + label "start()" + pctDist 0.500000 + height 45 + orientation 0) + line_color 3342489 + client @195 + supplier @197 + Focus_Src @196 + Focus_Entry @198 + origin (495, 416) + terminus (768, 416) + ordinal 1) + (object SelfMessView "" @230 + location (16, 480) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @231 + Parent_View @230 + location (1244, 437) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE02D3006C" + anchor_loc 1 + nlines 1 + max_width 854 + justify 0 + label "fireLifecycleEvent(BEFORE_START_EVENT)" + pctDist 2.960000 + height 44 + orientation 0) + line_color 3342489 + client @197 + supplier @197 + Focus_Src @198 + Focus_Entry @199 + origin (800, 480) + terminus (950, 480) + ordinal 2) + (object SelfMessView "" @232 + location (16, 592) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @233 + Parent_View @232 + location (1146, 549) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE02DF02DF" + anchor_loc 1 + nlines 1 + max_width 658 + justify 0 + label "fireLifecycleEvent(START_EVENT)" + pctDist 2.313333 + height 44 + orientation 0) + line_color 3342489 + client @197 + supplier @197 + Focus_Src @198 + Focus_Entry @200 + origin (800, 592) + terminus (950, 592) + ordinal 3) + (object InterMessView "" @234 + location (16, 704) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @235 + Parent_View @234 + location (935, 660) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE030C02B3" + anchor_loc 1 + nlines 1 + max_width 110 + justify 0 + label "start()" + pctDist 0.500000 + height 45 + orientation 0) + line_color 3342489 + client @197 + supplier @201 + Focus_Src @198 + Focus_Entry @202 + origin (799, 704) + terminus (1072, 704) + ordinal 4) + (object SelfMessView "" @236 + location (16, 752) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @237 + Parent_View @236 + location (1531, 708) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE031D0022" + anchor_loc 1 + nlines 1 + max_width 854 + justify 0 + label "fireLifecycleEvent(BEFORE_START_EVENT)" + pctDist 2.853333 + height 45 + orientation 0) + line_color 3342489 + client @201 + supplier @201 + Focus_Src @202 + Focus_Entry @203 + origin (1104, 752) + terminus (1254, 752) + ordinal 5) + (object SelfMessView "" @238 + location (16, 864) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @239 + Parent_View @238 + location (1449, 821) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE0330019B" + anchor_loc 1 + nlines 1 + max_width 658 + justify 0 + label "fireLifecycleEvent(START_EVENT)" + pctDist 2.306667 + height 44 + orientation 0) + line_color 3342489 + client @201 + supplier @201 + Focus_Src @202 + Focus_Entry @204 + origin (1104, 864) + terminus (1254, 864) + ordinal 6) + (object InterMessView "" @240 + location (16, 976) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @241 + Parent_View @240 + location (1255, 932) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE0370018A" + anchor_loc 1 + nlines 1 + max_width 110 + justify 0 + label "start()" + pctDist 0.500000 + height 45 + orientation 0) + line_color 3342489 + client @201 + supplier @205 + Focus_Src @202 + Focus_Entry @206 + origin (1103, 976) + terminus (1408, 976) + ordinal 7) + (object SelfMessView "" @242 + location (16, 1056) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @243 + Parent_View @242 + location (1865, 1014) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE03750051" + anchor_loc 1 + nlines 1 + max_width 854 + justify 0 + label "fireLifecycleEvent(BEFORE_START_EVENT)" + pctDist 2.840000 + height 43 + orientation 0) + line_color 3342489 + client @205 + supplier @205 + Focus_Src @207 + Focus_Entry @208 + origin (1440, 1056) + terminus (1590, 1056) + ordinal 8) + (object SelfMessView "" @244 + location (16, 1168) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @245 + Parent_View @244 + location (1639, 1141) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE0389001C" + anchor_loc 1 + nlines 1 + max_width 373 + justify 0 + label "addDefaultMapper()" + pctDist 1.326667 + height 28 + orientation 0) + line_color 3342489 + client @205 + supplier @205 + Focus_Src @207 + Focus_Entry @209 + origin (1440, 1168) + terminus (1590, 1168) + ordinal 9) + (object SelfMessView "" @246 + location (16, 1296) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @247 + Parent_View @246 + location (1592, 1268) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE03980281" + anchor_loc 1 + nlines 1 + max_width 238 + justify 0 + label "logger.start()" + pctDist 1.020000 + height 29 + orientation 0) + line_color 3342489 + client @205 + supplier @205 + Focus_Src @207 + Focus_Entry @210 + origin (1440, 1296) + terminus (1590, 1296) + ordinal 10) + (object SelfMessView "" @248 + location (16, 1408) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @249 + Parent_View @248 + location (1593, 1380) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE03A80107" + anchor_loc 1 + nlines 1 + max_width 226 + justify 0 + label "realm.start()" + pctDist 1.026667 + height 29 + orientation 0) + line_color 3342489 + client @205 + supplier @205 + Focus_Src @207 + Focus_Entry @211 + origin (1440, 1408) + terminus (1590, 1408) + ordinal 11) + (object SelfMessView "" @250 + location (16, 1536) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @251 + Parent_View @250 + location (1608, 1508) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE03BD000D" + anchor_loc 1 + nlines 1 + max_width 259 + justify 0 + label "findMappers()" + pctDist 1.120000 + height 29 + orientation 0) + line_color 3342489 + client @205 + supplier @205 + Focus_Src @207 + Focus_Entry @212 + origin (1440, 1536) + terminus (1590, 1536) + ordinal 12) + (object SelfMessView "" @252 + location (16, 1648) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @253 + Parent_View @252 + location (1515, 1604) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE03E000A4" + anchor_loc 1 + nlines 1 + max_width 251 + justify 0 + label "findChildren()" + pctDist 0.500000 + height 45 + orientation 0) + line_color 3342489 + client @205 + supplier @205 + Focus_Src @207 + Focus_Entry @213 + origin (1440, 1648) + terminus (1590, 1648) + ordinal 13) + (object InterMessView "" @254 + location (1664, 1760) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @255 + Parent_View @254 + location (1591, 1716) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE03FB027A" + anchor_loc 1 + nlines 1 + max_width 110 + justify 0 + label "start()" + pctDist 0.500000 + height 45 + orientation 0) + line_color 3342489 + client @205 + supplier @214 + Focus_Src @207 + Focus_Entry @215 + origin (1439, 1760) + terminus (1744, 1760) + ordinal 14) + (object SelfMessView "" @256 + location (16, 1808) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @257 + Parent_View @256 + location (1606, 1784) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE043B02AE" + anchor_loc 1 + nlines 1 + max_width 854 + justify 0 + label "fireLifecycleEvent(BEFORE_START_EVENT)" + pctDist -1.133333 + height 24 + orientation 0) + line_color 3342489 + client @214 + supplier @214 + Focus_Src @215 + Focus_Entry @216 + origin (1776, 1808) + terminus (1926, 1808) + ordinal 15) + (object SelfMessView "" @258 + location (16, 1920) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @259 + Parent_View @258 + location (1963, 1877) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE045C021F" + anchor_loc 1 + nlines 1 + max_width 373 + justify 0 + label "addDefaultMapper()" + pctDist 1.253333 + height 44 + orientation 0) + line_color 3342489 + client @214 + supplier @214 + Focus_Src @215 + Focus_Entry @217 + origin (1776, 1920) + terminus (1926, 1920) + ordinal 16) + (object InterMessView "" @260 + location (2000, 2368) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @261 + Parent_View @260 + location (1919, 2324) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE048E00B9" + anchor_loc 1 + nlines 1 + max_width 110 + justify 0 + label "start()" + pctDist 0.500000 + height 45 + orientation 0) + line_color 3342489 + client @214 + supplier @221 + Focus_Src @215 + Focus_Entry @222 + origin (1775, 2368) + terminus (2064, 2368) + ordinal 20) + (object SelfMessView "" @262 + location (16, 2032) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @263 + Parent_View @262 + location (1916, 2004) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE049B000C" + anchor_loc 1 + nlines 1 + max_width 238 + justify 0 + label "logger.start()" + pctDist 0.933333 + height 29 + orientation 0) + line_color 3342489 + client @214 + supplier @214 + Focus_Src @215 + Focus_Entry @218 + origin (1776, 2032) + terminus (1926, 2032) + ordinal 17) + (object SelfMessView "" @264 + location (16, 2144) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @265 + Parent_View @264 + location (1916, 2117) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE04A303BB" + anchor_loc 1 + nlines 1 + max_width 238 + justify 0 + label "findMapper()" + pctDist 0.933333 + height 28 + orientation 0) + line_color 3342489 + client @214 + supplier @214 + Focus_Src @215 + Focus_Entry @219 + origin (1776, 2144) + terminus (1926, 2144) + ordinal 18) + (object SelfMessView "" @266 + location (16, 2256) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @267 + Parent_View @266 + location (1916, 2228) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE04A90342" + anchor_loc 1 + nlines 1 + max_width 251 + justify 0 + label "findChildren()" + pctDist 0.933333 + height 29 + orientation 0) + line_color 3342489 + client @214 + supplier @214 + Focus_Src @215 + Focus_Entry @220 + origin (1776, 2256) + terminus (1926, 2256) + ordinal 19) + (object NoteView @268 + location (2128, 1488) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @268 + location (1915, 1422) + fill_color 13434879 + nlines 2 + max_width 390 + label "#1 Catalina.start()") + line_color 3342489 + fill_color 13434879 + width 450 + height 144) + (object SelfMessView "" @269 + location (16, 2416) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @270 + Parent_View @269 + location (1644, 2498) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE05780138" + anchor_loc 1 + nlines 1 + max_width 854 + justify 0 + label "fireLifecycleEvent(BEFORE_START_EVENT)" + pctDist -3.020000 + height 45 + orientation 0) + line_color 3342489 + client @221 + supplier @221 + Focus_Src @222 + Focus_Entry @223 + origin (2096, 2416) + terminus (2246, 2416) + ordinal 21) + (object SelfMessView "" @271 + location (16, 2480) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @272 + Parent_View @271 + location (1705, 2582) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE05A80398" + anchor_loc 1 + nlines 1 + max_width 658 + justify 0 + label "fireLifecycleEvent(START_EVENT)" + pctDist -2.613333 + height 45 + orientation 0) + line_color 3342489 + client @221 + supplier @221 + Focus_Src @222 + Focus_Entry @224 + origin (2096, 2480) + terminus (2246, 2480) + ordinal 22) + (object SelfMessView "" @273 + location (16, 2560) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @274 + Parent_View @273 + location (1737, 2423) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE05BA0196" + anchor_loc 1 + nlines 1 + max_width 658 + justify 0 + label "fireLifecycleEvent(AFTER_EVENT)" + pctDist -2.393333 + height 138 + orientation 0) + line_color 3342489 + client @221 + supplier @221 + Focus_Src @222 + Focus_Entry @225 + origin (2096, 2560) + terminus (2246, 2560) + ordinal 23) + (object NoteView @275 + location (960, 1680) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @275 + location (635, 1571) + fill_color 13434879 + nlines 4 + max_width 615 + label "All StandardX will fire these events.") + line_color 3342489 + fill_color 13434879 + width 675 + height 231) + (object AttachView "" @276 + stereotype TRUE + line_color 3342489 + client @275 + supplier @272 + line_style 0) + (object AttachView "" @277 + stereotype TRUE + line_color 3342489 + client @275 + supplier @270 + line_style 0) + (object AttachView "" @278 + stereotype TRUE + line_color 3342489 + client @275 + supplier @274 + line_style 0))) + (object InteractionDiagram "4. catalina_start_2" + mechanism_ref @85 + quid "3DFE050900BF" + title "4. catalina_start_2" + zoom 100 + max_height 28350 + max_width 21600 + origin_x 0 + origin_y 1087 + items (list diagram_item_list + (object InterObjView "StandardHost" @279 + location (208, 224) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline TRUE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @279 + location (208, 224) + fill_color 13434879 + anchor_loc 1 + nlines 2 + max_width 282 + justify 0 + label "StandardHost") + icon_style "Icon" + line_color 3342489 + fill_color 13434879 + quidu "3DFE0538017B" + width 300 + height 2114 + icon_height 0 + icon_width 0 + icon_y_offset 0 + annotation 1 + Focus_Of_Control (object Focus_Of_Control "" @280 + location (208, 384) + line_color 3342489 + InterObjView @279 + height 1864 + y_coord 1804 + Nested FALSE) + Focus_Of_Control (object Focus_Of_Control "" @281 + location (208, 384) + line_color 3342489 + InterObjView @279 + height 60 + y_coord 0 + Nested TRUE) + Focus_Of_Control (object Focus_Of_Control "" @282 + location (208, 1088) + line_color 3342489 + InterObjView @279 + height 60 + y_coord 0 + Nested TRUE) + Focus_Of_Control (object Focus_Of_Control "" @283 + location (208, 1616) + line_color 3342489 + InterObjView @279 + height 60 + y_coord 0 + Nested TRUE)) + (object InterObjView "HostConfig" @284 + location (544, 224) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline TRUE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @284 + location (544, 224) + fill_color 13434879 + anchor_loc 1 + nlines 2 + max_width 282 + justify 0 + label "HostConfig") + icon_style "Icon" + line_color 3342489 + fill_color 13434879 + quidu "3DFE06A60131" + width 300 + height 2114 + icon_height 0 + icon_width 0 + icon_y_offset 0 + annotation 1 + Focus_Of_Control (object Focus_Of_Control "" @285 + location (544, 512) + line_color 3342489 + InterObjView @284 + height 696 + y_coord 636 + Nested FALSE) + Focus_Of_Control (object Focus_Of_Control "" @286 + location (544, 576) + line_color 3342489 + InterObjView @284 + height 60 + y_coord 0 + Nested TRUE) + Focus_Of_Control (object Focus_Of_Control "" @287 + location (544, 688) + line_color 3342489 + InterObjView @284 + height 60 + y_coord 0 + Nested TRUE) + Focus_Of_Control (object Focus_Of_Control "" @288 + location (544, 784) + line_color 3342489 + InterObjView @284 + height 60 + y_coord 0 + Nested TRUE) + Focus_Of_Control (object Focus_Of_Control "" @289 + location (544, 896) + line_color 3342489 + InterObjView @284 + height 60 + y_coord 0 + Nested TRUE) + Focus_Of_Control (object Focus_Of_Control "" @290 + location (544, 1008) + line_color 3342489 + InterObjView @284 + height 60 + y_coord 0 + Nested TRUE) + Focus_Of_Control (object Focus_Of_Control "" @291 + location (544, 1536) + line_color 3342489 + InterObjView @284 + height 200 + y_coord 140 + Nested FALSE) + Focus_Of_Control (object Focus_Of_Control "" @292 + location (544, 1536) + line_color 3342489 + InterObjView @284 + height 60 + y_coord 0 + Nested TRUE)) + (object InterObjView "StandardHostDeployer" @293 + location (944, 224) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline TRUE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @293 + location (944, 224) + fill_color 13434879 + anchor_loc 1 + nlines 2 + max_width 426 + justify 0 + label "StandardHostDeployer") + icon_style "Icon" + line_color 3342489 + fill_color 13434879 + quidu "3DFE079A0055" + width 444 + height 2114 + icon_height 0 + icon_width 0 + icon_y_offset 0 + annotation 1 + Focus_Of_Control (object Focus_Of_Control "" @294 + location (944, 1280) + line_color 3342489 + InterObjView @293 + height 824 + y_coord 764 + Nested FALSE) + Focus_Of_Control (object Focus_Of_Control "" @295 + location (944, 2128) + line_color 3342489 + InterObjView @293 + height 60 + y_coord 0 + Nested FALSE)) + (object InterObjView "Digester" @296 + location (1328, 224) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline TRUE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @296 + location (1328, 224) + fill_color 13434879 + anchor_loc 1 + nlines 2 + max_width 282 + justify 0 + label "Digester") + icon_style "Icon" + line_color 3342489 + fill_color 13434879 + quidu "3DFE07C9034C" + width 300 + height 2114 + icon_height 0 + icon_width 0 + icon_y_offset 0 + annotation 1 + Focus_Of_Control (object Focus_Of_Control "" @297 + location (1328, 1280) + line_color 3342489 + InterObjView @296 + height 60 + y_coord 0 + Nested FALSE) + Focus_Of_Control (object Focus_Of_Control "" @298 + location (1328, 1488) + line_color 3342489 + InterObjView @296 + height 60 + y_coord 0 + Nested FALSE) + Focus_Of_Control (object Focus_Of_Control "" @299 + location (1328, 1984) + line_color 3342489 + InterObjView @296 + height 60 + y_coord 0 + Nested FALSE)) + (object InterObjView "ContextRuleSet" @300 + location (1648, 224) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline TRUE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @300 + location (1648, 224) + fill_color 13434879 + anchor_loc 1 + nlines 2 + max_width 282 + justify 0 + label "ContextRuleSet") + icon_style "Icon" + line_color 3342489 + fill_color 13434879 + quidu "3DFE0834016F" + width 300 + height 2114 + icon_height 0 + icon_width 0 + icon_y_offset 0 + annotation 1 + Focus_Of_Control (object Focus_Of_Control "" @301 + location (1648, 1408) + line_color 3342489 + InterObjView @300 + height 60 + y_coord 0 + Nested FALSE) + Focus_Of_Control (object Focus_Of_Control "" @302 + location (1648, 1888) + line_color 3342489 + InterObjView @300 + height 60 + y_coord 0 + Nested FALSE)) + (object InterObjView "NamingRuleSet" @303 + location (1968, 224) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline TRUE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @303 + location (1968, 224) + fill_color 13434879 + anchor_loc 1 + nlines 2 + max_width 282 + justify 0 + label "NamingRuleSet") + icon_style "Icon" + line_color 3342489 + fill_color 13434879 + quidu "3DFE08D00173" + width 300 + height 2114 + icon_height 0 + icon_width 0 + icon_y_offset 0 + annotation 1 + Focus_Of_Control (object Focus_Of_Control "" @304 + location (1968, 1792) + line_color 3342489 + InterObjView @303 + height 60 + y_coord 0 + Nested FALSE)) + (object SelfMessView "" @305 + location (0, 384) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @306 + Parent_View @305 + location (555, 342) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE066C0341" + anchor_loc 1 + nlines 1 + max_width 651 + justify 0 + label "fireLifecycleEvent(START_EVENT)" + pctDist 2.206667 + height 43 + orientation 0) + line_color 3342489 + client @279 + supplier @279 + Focus_Src @280 + Focus_Entry @281 + origin (224, 384) + terminus (374, 384) + ordinal 0) + (object InterMessView "" @307 + location (384, 512) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @308 + Parent_View @307 + location (486, 468) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE06D20294" + anchor_loc 1 + nlines 1 + max_width 507 + justify 0 + label "interested[i].lifecycleEvent()" + pctDist 0.865574 + height 45 + orientation 0) + line_color 3342489 + client @279 + supplier @284 + Focus_Src @280 + Focus_Entry @285 + origin (223, 512) + terminus (528, 512) + ordinal 1) + (object SelfMessView "" @309 + location (16, 576) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @310 + Parent_View @309 + location (713, 537) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE06E9028D" + anchor_loc 1 + nlines 1 + max_width 297 + justify 0 + label "setDeployXML()" + pctDist 1.026667 + height 40 + orientation 0) + line_color 3342489 + client @284 + supplier @284 + Focus_Src @285 + Focus_Entry @286 + origin (560, 576) + terminus (710, 576) + ordinal 2) + (object SelfMessView "" @311 + location (16, 688) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @312 + Parent_View @311 + location (714, 645) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE06F300FF" + anchor_loc 1 + nlines 1 + max_width 288 + justify 0 + label "setLiveDeploy()" + pctDist 1.033333 + height 44 + orientation 0) + line_color 3342489 + client @284 + supplier @284 + Focus_Src @285 + Focus_Entry @287 + origin (560, 688) + terminus (710, 688) + ordinal 3) + (object SelfMessView "" @313 + location (16, 784) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @314 + Parent_View @313 + location (732, 756) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE06FB00D9" + anchor_loc 1 + nlines 1 + max_width 326 + justify 0 + label "setUnpacksWar()" + pctDist 1.153333 + height 29 + orientation 0) + line_color 3342489 + client @284 + supplier @284 + Focus_Src @285 + Focus_Entry @288 + origin (560, 784) + terminus (710, 784) + ordinal 4) + (object SelfMessView "" @315 + location (16, 896) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @316 + Parent_View @315 + location (747, 868) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE070C0015" + anchor_loc 1 + nlines 1 + max_width 350 + justify 0 + label "setXMLValidation()" + pctDist 1.246667 + height 29 + orientation 0) + line_color 3342489 + client @284 + supplier @284 + Focus_Src @285 + Focus_Entry @289 + origin (560, 896) + terminus (710, 896) + ordinal 5) + (object SelfMessView "" @317 + location (16, 1008) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @318 + Parent_View @317 + location (762, 980) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE073B0031" + anchor_loc 1 + nlines 1 + max_width 359 + justify 0 + label "deployDescriptors()" + pctDist 1.346667 + height 29 + orientation 0) + line_color 3342489 + client @284 + supplier @284 + Focus_Src @285 + Focus_Entry @290 + origin (560, 1008) + terminus (710, 1008) + ordinal 6) + (object InterMessView "" @319 + location (16, 1088) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @320 + Parent_View @319 + location (376, 1044) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE078B03BB" + anchor_loc 1 + nlines 1 + max_width 136 + justify 0 + label "install()" + pctDist 0.500000 + height 45 + orientation 1) + line_color 3342489 + client @284 + supplier @279 + Focus_Src @285 + Focus_Entry @282 + origin (528, 1088) + terminus (224, 1088) + ordinal 7) + (object InterMessView "" @321 + location (576, 1280) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @322 + Parent_View @321 + location (575, 1236) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE07B100BE" + anchor_loc 1 + nlines 1 + max_width 136 + justify 0 + label "install()" + pctDist 0.500000 + height 45 + orientation 0) + line_color 3342489 + client @279 + supplier @293 + Focus_Src @280 + Focus_Entry @294 + origin (223, 1280) + terminus (928, 1280) + ordinal 8) + (object InterMessView "" @323 + location (1152, 1280) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @324 + Parent_View @323 + location (1135, 1236) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE07D200ED" + anchor_loc 1 + nlines 1 + max_width 144 + justify 0 + label "create()" + pctDist 0.500000 + height 45 + orientation 0) + line_color 3342489 + client @293 + supplier @296 + Focus_Src @294 + Focus_Entry @297 + origin (959, 1280) + terminus (1312, 1280) + ordinal 9) + (object InterMessView "" @325 + location (1136, 1984) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @326 + Parent_View @325 + location (1135, 1940) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE07D603D7" + anchor_loc 1 + nlines 1 + max_width 136 + justify 0 + label "parse()" + pctDist 0.500000 + height 45 + orientation 0) + line_color 3342489 + client @293 + supplier @296 + Focus_Src @294 + Focus_Entry @299 + origin (959, 1984) + terminus (1312, 1984) + ordinal 16) + (object InterMessView "" @327 + location (1296, 1408) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @328 + Parent_View @327 + location (1295, 1364) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE08DA029B" + anchor_loc 1 + nlines 1 + max_width 106 + justify 0 + label "new()" + pctDist 0.500000 + height 45 + orientation 0) + line_color 3342489 + client @293 + supplier @300 + Focus_Src @294 + Focus_Entry @301 + origin (959, 1408) + terminus (1632, 1408) + ordinal 10) + (object InterMessView "" @329 + location (1456, 1792) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @330 + Parent_View @329 + location (1455, 1748) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE08E00091" + anchor_loc 1 + nlines 1 + max_width 106 + justify 0 + label "new()" + pctDist 0.500000 + height 45 + orientation 0) + line_color 3342489 + client @293 + supplier @303 + Focus_Src @294 + Focus_Entry @304 + origin (959, 1792) + terminus (1952, 1792) + ordinal 14) + (object InterMessView "" @331 + location (16, 1488) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @332 + Parent_View @331 + location (1182, 1445) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE08FA003D" + anchor_loc 1 + nlines 1 + max_width 387 + justify 0 + label "add(ContextRuleSet)" + pctDist 0.631728 + height 44 + orientation 0) + line_color 3342489 + client @293 + supplier @296 + Focus_Src @294 + Focus_Entry @298 + origin (959, 1488) + terminus (1312, 1488) + ordinal 11) + (object InterMessView "" @333 + location (1296, 1888) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @334 + Parent_View @333 + location (1295, 1844) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE0907015F" + anchor_loc 1 + nlines 1 + max_width 416 + justify 0 + label "add(NamingRuleSet())" + pctDist 0.500000 + height 45 + orientation 0) + line_color 3342489 + client @293 + supplier @300 + Focus_Src @294 + Focus_Entry @302 + origin (959, 1888) + terminus (1632, 1888) + ordinal 15) + (object NoteView @335 + location (2096, 2384) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @335 + location (1893, 2315) + fill_color 13434879 + nlines 2 + max_width 371 + label "#2 Catalina.start()") + line_color 3342489 + fill_color 13434879 + width 431 + height 150) + (object SelfMessView "" @336 + location (16, 1536) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @337 + Parent_View @336 + location (697, 1493) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE131F0327" + anchor_loc 1 + nlines 1 + max_width 244 + justify 0 + label "deployApps()" + pctDist 0.913333 + height 43 + orientation 0) + line_color 3342489 + client @284 + supplier @284 + Focus_Src @291 + Focus_Entry @292 + origin (560, 1536) + terminus (710, 1536) + ordinal 12) + (object InterMessView "" @338 + location (16, 1616) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @339 + Parent_View @338 + location (376, 1572) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE132D0309" + anchor_loc 1 + nlines 1 + max_width 136 + justify 0 + label "install()" + pctDist 0.500000 + height 45 + orientation 1) + line_color 3342489 + client @284 + supplier @279 + Focus_Src @291 + Focus_Entry @283 + origin (528, 1616) + terminus (224, 1616) + ordinal 13) + (object InterMessView "" @340 + location (576, 2128) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @341 + Parent_View @340 + location (575, 2084) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE133A036C" + anchor_loc 1 + nlines 1 + max_width 463 + justify 0 + label "install() // same as above" + pctDist 0.500000 + height 45 + orientation 0) + line_color 3342489 + client @279 + supplier @293 + Focus_Src @280 + Focus_Entry @295 + origin (223, 2128) + terminus (928, 2128) + ordinal 17))) + (object InteractionDiagram "5. catalina_start_3" + mechanism_ref @86 + quid "3DFE094A0346" + title "5. catalina_start_3" + zoom 100 + max_height 28350 + max_width 21600 + origin_x 0 + origin_y 0 + items (list diagram_item_list + (object InterObjView "Digester" @342 + location (176, 224) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline TRUE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @342 + location (176, 224) + fill_color 13434879 + anchor_loc 1 + nlines 2 + max_width 282 + justify 0 + label "Digester") + icon_style "Icon" + line_color 3342489 + fill_color 13434879 + quidu "3DFE095A0371" + width 300 + height 1214 + icon_height 0 + icon_width 0 + icon_y_offset 0 + annotation 1 + Focus_Of_Control (object Focus_Of_Control "" @343 + location (176, 352) + line_color 3342489 + InterObjView @342 + height 996 + y_coord 936 + Nested FALSE) + Focus_Of_Control (object Focus_Of_Control "" @344 + location (176, 352) + line_color 3342489 + InterObjView @342 + height 60 + y_coord 0 + Nested TRUE) + Focus_Of_Control (object Focus_Of_Control "" @345 + location (176, 448) + line_color 3342489 + InterObjView @342 + height 60 + y_coord 0 + Nested TRUE)) + (object InterObjView "Rule" @346 + location (480, 224) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline TRUE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @346 + location (480, 224) + fill_color 13434879 + anchor_loc 1 + nlines 2 + max_width 282 + justify 0 + label "Rule") + icon_style "Icon" + line_color 3342489 + fill_color 13434879 + quidu "3DFE0E7400D0" + width 300 + height 1214 + icon_height 0 + icon_width 0 + icon_y_offset 0 + annotation 1 + Focus_Of_Control (object Focus_Of_Control "" @347 + location (480, 560) + line_color 3342489 + InterObjView @346 + height 728 + y_coord 668 + Nested FALSE)) + (object InterObjView "StandardContext" @348 + location (816, 224) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline TRUE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @348 + location (816, 224) + fill_color 13434879 + anchor_loc 1 + nlines 2 + max_width 332 + justify 0 + label "StandardContext") + icon_style "Icon" + line_color 3342489 + fill_color 13434879 + quidu "3DFE0FC502A1" + width 350 + height 1214 + icon_height 0 + icon_width 0 + icon_y_offset 0 + annotation 1 + Focus_Of_Control (object Focus_Of_Control "" @349 + location (816, 592) + line_color 3342489 + InterObjView @348 + height 264 + y_coord 204 + Nested FALSE) + Focus_Of_Control (object Focus_Of_Control "" @350 + location (816, 1008) + line_color 3342489 + InterObjView @348 + height 60 + y_coord 0 + Nested FALSE)) + (object InterObjView "StandardPipeline" @351 + location (1184, 224) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline TRUE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @351 + location (1184, 224) + fill_color 13434879 + anchor_loc 1 + nlines 2 + max_width 363 + justify 0 + label "StandardPipeline") + icon_style "Icon" + line_color 3342489 + fill_color 13434879 + quidu "3DFE112F003F" + width 381 + height 1214 + icon_height 0 + icon_width 0 + icon_y_offset 0 + annotation 1 + Focus_Of_Control (object Focus_Of_Control "" @352 + location (1184, 736) + line_color 3342489 + InterObjView @351 + height 60 + y_coord 0 + Nested FALSE)) + (object InterObjView "StandardContextValve" @353 + location (1552, 224) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline TRUE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @353 + location (1552, 224) + fill_color 13434879 + anchor_loc 1 + nlines 2 + max_width 300 + justify 0 + label "StandardContextValve") + icon_style "Icon" + line_color 3342489 + fill_color 13434879 + quidu "3DFE110D0375" + width 318 + height 1214 + icon_height 0 + icon_width 0 + icon_y_offset 0 + annotation 1 + Focus_Of_Control (object Focus_Of_Control "" @354 + location (1552, 624) + line_color 3342489 + InterObjView @353 + height 60 + y_coord 0 + Nested FALSE)) + (object InterObjView "SetPropertiesRule" @355 + location (1920, 224) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline TRUE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @355 + location (1920, 224) + fill_color 13434879 + anchor_loc 1 + nlines 2 + max_width 363 + justify 0 + label "SetPropertiesRule") + icon_style "Icon" + line_color 3342489 + fill_color 13434879 + quidu "3DFE100303A4" + width 381 + height 1214 + icon_height 0 + icon_width 0 + icon_y_offset 0 + annotation 1 + Focus_Of_Control (object Focus_Of_Control "" @356 + location (1920, 928) + line_color 3342489 + InterObjView @355 + height 200 + y_coord 140 + Nested FALSE)) + (object InterObjView "SetNextRule" @357 + location (2272, 224) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline TRUE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @357 + location (2272, 224) + fill_color 13434879 + anchor_loc 1 + nlines 2 + max_width 282 + justify 0 + label "SetNextRule") + icon_style "Icon" + line_color 3342489 + fill_color 13434879 + quidu "3DFE12690267" + width 300 + height 1214 + icon_height 0 + icon_width 0 + icon_y_offset 0 + annotation 1 + Focus_Of_Control (object Focus_Of_Control "" @358 + location (2272, 1168) + line_color 3342489 + InterObjView @357 + height 60 + y_coord 0 + Nested FALSE)) + (object SelfMessView "" @359 + location (0, 352) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @360 + Parent_View @359 + location (267, 308) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE0E7801DB" + anchor_loc 1 + nlines 1 + max_width 108 + justify 0 + label "parse" + pctDist 0.500000 + height 45 + orientation 0) + line_color 3342489 + client @342 + supplier @342 + Focus_Src @343 + Focus_Entry @344 + origin (192, 352) + terminus (342, 352) + ordinal 0) + (object SelfMessView "" @361 + location (16, 448) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @362 + Parent_View @361 + location (345, 420) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE0F2F03D2" + anchor_loc 1 + nlines 1 + max_width 267 + justify 0 + label "startElement()" + pctDist 1.020000 + height 28 + orientation 0) + line_color 3342489 + client @342 + supplier @342 + Focus_Src @343 + Focus_Entry @345 + origin (192, 448) + terminus (342, 448) + ordinal 1) + (object InterMessView "" @363 + location (336, 560) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @364 + Parent_View @363 + location (327, 516) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE0F400214" + anchor_loc 1 + nlines 1 + max_width 132 + justify 0 + label "begin()" + pctDist 0.500000 + height 45 + orientation 0) + line_color 3342489 + client @342 + supplier @346 + Focus_Src @343 + Focus_Entry @347 + origin (191, 560) + terminus (464, 560) + ordinal 2) + (object InterMessView "" @365 + location (16, 592) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @366 + Parent_View @365 + location (647, 548) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE0FD30266" + anchor_loc 1 + nlines 1 + max_width 265 + justify 0 + label "newInstance()" + pctDist 0.500000 + height 45 + orientation 0) + line_color 3342489 + client @346 + supplier @348 + Focus_Src @347 + Focus_Entry @349 + origin (495, 592) + terminus (800, 592) + ordinal 3) + (object InterMessView "" @367 + location (864, 928) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @368 + Parent_View @367 + location (1199, 884) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE102002E9" + anchor_loc 1 + nlines 1 + max_width 132 + justify 0 + label "begin()" + pctDist 0.500000 + height 45 + orientation 0) + line_color 3342489 + client @346 + supplier @355 + Focus_Src @347 + Focus_Entry @356 + origin (495, 928) + terminus (1904, 928) + ordinal 6) + (object InterMessView "" @369 + location (1008, 736) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @370 + Parent_View @369 + location (1139, 693) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE114A0193" + anchor_loc 1 + nlines 1 + max_width 610 + justify 0 + label "setBasic(StandardContextValve)" + pctDist 0.915014 + height 44 + orientation 0) + line_color 3342489 + client @348 + supplier @351 + Focus_Src @349 + Focus_Entry @352 + origin (831, 736) + terminus (1168, 736) + ordinal 5) + (object InterMessView "" @371 + location (16, 624) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @372 + Parent_View @371 + location (1183, 580) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE115E001F" + anchor_loc 1 + nlines 1 + max_width 106 + justify 0 + label "new()" + pctDist 0.500000 + height 45 + orientation 0) + line_color 3342489 + client @348 + supplier @353 + Focus_Src @349 + Focus_Entry @354 + origin (831, 624) + terminus (1536, 624) + ordinal 4) + (object InterMessView "" @373 + location (1440, 1008) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @374 + Parent_View @373 + location (1368, 964) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE11D50391" + anchor_loc 1 + nlines 1 + max_width 1190 + justify 0 + label "//Using BeanUtil, set the object properties (from ex: admin.xml)" + pctDist 0.500000 + height 45 + orientation 1) + line_color 3342489 + client @355 + supplier @348 + Focus_Src @356 + Focus_Entry @350 + origin (1904, 1008) + terminus (832, 1008) + ordinal 7) + (object InterMessView "" @375 + location (1392, 1168) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @376 + Parent_View @375 + location (1375, 1124) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE128501C8" + anchor_loc 1 + nlines 1 + max_width 99 + justify 0 + label "end()" + pctDist 0.500000 + height 45 + orientation 0) + line_color 3342489 + client @346 + supplier @357 + Focus_Src @347 + Focus_Entry @358 + origin (495, 1168) + terminus (2256, 1168) + ordinal 8) + (object NoteView @377 + location (1216, 80) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @377 + location (900, 15) + fill_color 13434879 + nlines 2 + max_width 596 + label "HostConfig.deployDescriptor()") + line_color 3342489 + fill_color 13434879 + width 656 + height 143) + (object NoteView @378 + location (2128, 1888) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @378 + location (1947, 1822) + fill_color 13434879 + nlines 2 + max_width 327 + label "#3 Catalina.start()") + line_color 3342489 + fill_color 13434879 + width 387 + height 144))) + (object InteractionDiagram "6. catalina_start_4" + mechanism_ref @87 + quid "3DFE13890008" + title "6. catalina_start_4" + zoom 100 + max_height 28350 + max_width 21600 + origin_x 0 + origin_y 1818 + items (list diagram_item_list + (object InterObjView "Digester" @379 + location (176, 224) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline TRUE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @379 + location (176, 224) + fill_color 13434879 + anchor_loc 1 + nlines 2 + max_width 282 + justify 0 + label "Digester") + icon_style "Icon" + line_color 3342489 + fill_color 13434879 + quidu "3DFE13960364" + width 300 + height 2446 + icon_height 0 + icon_width 0 + icon_y_offset 0 + annotation 1 + Focus_Of_Control (object Focus_Of_Control "" @380 + location (176, 336) + line_color 3342489 + InterObjView @379 + height 1228 + y_coord 1168 + Nested FALSE) + Focus_Of_Control (object Focus_Of_Control "" @381 + location (176, 336) + line_color 3342489 + InterObjView @379 + height 60 + y_coord 0 + Nested TRUE) + Focus_Of_Control (object Focus_Of_Control "" @382 + location (176, 480) + line_color 3342489 + InterObjView @379 + height 60 + y_coord 0 + Nested TRUE) + Focus_Of_Control (object Focus_Of_Control "" @383 + location (176, 1616) + line_color 3342489 + InterObjView @379 + height 580 + y_coord 520 + Nested FALSE) + Focus_Of_Control (object Focus_Of_Control "" @384 + location (176, 1728) + line_color 3342489 + InterObjView @379 + height 60 + y_coord 0 + Nested TRUE)) + (object InterObjView "StandardHostDeployer" @385 + location (480, 224) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline TRUE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @385 + location (480, 224) + fill_color 13434879 + anchor_loc 1 + nlines 2 + max_width 301 + justify 0 + label "StandardHostDeployer") + icon_style "Icon" + line_color 3342489 + fill_color 13434879 + quidu "3DFE1D8A02DC" + width 319 + height 2446 + icon_height 0 + icon_width 0 + icon_y_offset 0 + annotation 1 + Focus_Of_Control (object Focus_Of_Control "" @386 + location (480, 576) + line_color 3342489 + InterObjView @385 + height 928 + y_coord 868 + Nested FALSE)) + (object InterObjView "StandardHost" @387 + location (800, 224) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline TRUE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @387 + location (800, 224) + fill_color 13434879 + anchor_loc 1 + nlines 2 + max_width 282 + justify 0 + label "StandardHost") + icon_style "Icon" + line_color 3342489 + fill_color 13434879 + quidu "3DFE1DF20141" + width 300 + height 2446 + icon_height 0 + icon_width 0 + icon_y_offset 0 + annotation 1 + Focus_Of_Control (object Focus_Of_Control "" @388 + location (800, 592) + line_color 3342489 + InterObjView @387 + height 852 + y_coord 792 + Nested FALSE)) + (object InterObjView "StandardContext" @389 + location (1120, 224) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline TRUE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @389 + location (1120, 224) + fill_color 13434879 + anchor_loc 1 + nlines 2 + max_width 295 + justify 0 + label "StandardContext") + icon_style "Icon" + line_color 3342489 + fill_color 13434879 + quidu "3DFE196D00D9" + width 313 + height 2446 + icon_height 0 + icon_width 0 + icon_y_offset 0 + annotation 1 + Focus_Of_Control (object Focus_Of_Control "" @390 + location (1120, 624) + line_color 3342489 + InterObjView @389 + height 760 + y_coord 700 + Nested FALSE) + Focus_Of_Control (object Focus_Of_Control "" @391 + location (1120, 800) + line_color 3342489 + InterObjView @389 + height 60 + y_coord 0 + Nested TRUE) + Focus_Of_Control (object Focus_Of_Control "" @392 + location (1120, 976) + line_color 3342489 + InterObjView @389 + height 60 + y_coord 0 + Nested TRUE) + Focus_Of_Control (object Focus_Of_Control "" @393 + location (1120, 1072) + line_color 3342489 + InterObjView @389 + height 60 + y_coord 0 + Nested TRUE)) + (object InterObjView "WebappLoader" @394 + location (1440, 224) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline TRUE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @394 + location (1440, 224) + fill_color 13434879 + anchor_loc 1 + nlines 2 + max_width 295 + justify 0 + label "WebappLoader") + icon_style "Icon" + line_color 3342489 + fill_color 13434879 + quidu "3DFE1FFA0347" + width 313 + height 2446 + icon_height 0 + icon_width 0 + icon_y_offset 0 + annotation 1 + Focus_Of_Control (object Focus_Of_Control "" @395 + location (1440, 640) + line_color 3342489 + InterObjView @394 + height 60 + y_coord 0 + Nested FALSE)) + (object InterObjView "StandardManager" @396 + location (1760, 224) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline TRUE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @396 + location (1760, 224) + fill_color 13434879 + anchor_loc 1 + nlines 2 + max_width 301 + justify 0 + label "StandardManager") + icon_style "Icon" + line_color 3342489 + fill_color 13434879 + quidu "3DFE201F0105" + width 319 + height 2446 + icon_height 0 + icon_width 0 + icon_y_offset 0 + annotation 1 + Focus_Of_Control (object Focus_Of_Control "" @397 + location (1760, 832) + line_color 3342489 + InterObjView @396 + height 60 + y_coord 0 + Nested FALSE) + Focus_Of_Control (object Focus_Of_Control "" @398 + location (1760, 1264) + line_color 3342489 + InterObjView @396 + height 60 + y_coord 0 + Nested FALSE)) + (object InterObjView "ContextConfig" @399 + location (1952, 352) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline TRUE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @399 + location (1952, 352) + fill_color 13434879 + anchor_loc 1 + nlines 2 + max_width 282 + justify 0 + label "ContextConfig") + icon_style "Icon" + line_color 3342489 + fill_color 13434879 + quidu "3DFE2087028C" + width 300 + height 2318 + icon_height 0 + icon_width 0 + icon_y_offset 0 + annotation 1 + Focus_Of_Control (object Focus_Of_Control "" @400 + location (1952, 412) + InterObjView @399 + height 60 + y_coord 0 + Nested FALSE) + Focus_Of_Control (object Focus_Of_Control "" @401 + location (1952, 1136) + line_color 3342489 + InterObjView @399 + height 1444 + y_coord 1384 + Nested FALSE) + Focus_Of_Control (object Focus_Of_Control "" @402 + location (1952, 1264) + line_color 3342489 + InterObjView @399 + height 60 + y_coord 0 + Nested TRUE) + Focus_Of_Control (object Focus_Of_Control "" @403 + location (1952, 1456) + line_color 3342489 + InterObjView @399 + height 1070 + y_coord 1010 + Nested TRUE) + Focus_Of_Control (object Focus_Of_Control "" @404 + location (1952, 1568) + line_color 3342489 + InterObjView @399 + height 952 + y_coord 892 + Nested TRUE) + Focus_Of_Control (object Focus_Of_Control "" @405 + location (1952, 1984) + line_color 3342489 + InterObjView @399 + height 152 + y_coord 92 + Nested TRUE)) + (object SelfMessView "" @406 + location (16, 336) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @407 + Parent_View @406 + location (267, 292) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE19AE0065" + anchor_loc 1 + nlines 1 + max_width 108 + justify 0 + label "parse" + pctDist 0.500000 + height 45 + orientation 0) + line_color 3342489 + client @379 + supplier @379 + Focus_Src @380 + Focus_Entry @381 + origin (192, 336) + terminus (342, 336) + ordinal 0) + (object SelfMessView "" @408 + location (16, 480) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @409 + Parent_View @408 + location (328, 437) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE19B102E9" + anchor_loc 1 + nlines 1 + max_width 267 + justify 0 + label "startElement()" + pctDist 0.906667 + height 44 + orientation 0) + line_color 3342489 + client @379 + supplier @379 + Focus_Src @380 + Focus_Entry @382 + origin (192, 480) + terminus (342, 480) + ordinal 1) + (object InterMessView "" @410 + location (16, 576) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @411 + Parent_View @410 + location (327, 552) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE1DFB0022" + anchor_loc 1 + nlines 1 + max_width 165 + justify 0 + label "addChild" + pctDist 0.498645 + height 25 + orientation 0) + line_color 3342489 + client @379 + supplier @385 + Focus_Src @380 + Focus_Entry @386 + origin (191, 576) + terminus (464, 576) + ordinal 2) + (object InterMessView "" @412 + location (16, 592) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @413 + Parent_View @412 + location (639, 548) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE1FB60277" + anchor_loc 1 + nlines 1 + max_width 165 + justify 0 + label "addChild" + pctDist 0.500000 + height 45 + orientation 0) + line_color 3342489 + client @385 + supplier @387 + Focus_Src @386 + Focus_Entry @388 + origin (495, 592) + terminus (784, 592) + ordinal 3) + (object InterMessView "" @414 + location (16, 624) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @415 + Parent_View @414 + location (959, 580) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE1FC40228" + anchor_loc 1 + nlines 1 + max_width 110 + justify 0 + label "start()" + pctDist 0.500000 + height 45 + orientation 0) + line_color 3342489 + client @387 + supplier @389 + Focus_Src @388 + Focus_Entry @390 + origin (815, 624) + terminus (1104, 624) + ordinal 4) + (object InterMessView "" @416 + location (16, 640) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @417 + Parent_View @416 + location (1279, 596) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE200603BE" + anchor_loc 1 + nlines 1 + max_width 82 + justify 0 + label "new" + pctDist 0.500000 + height 45 + orientation 0) + line_color 3342489 + client @389 + supplier @394 + Focus_Src @390 + Focus_Entry @395 + origin (1135, 640) + terminus (1424, 640) + ordinal 5) + (object SelfMessView "" @418 + location (16, 800) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @419 + Parent_View @418 + location (1224, 756) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE200C029A" + anchor_loc 1 + nlines 1 + max_width 186 + justify 0 + label "setLoader" + pctDist 0.593333 + height 45 + orientation 0) + line_color 3342489 + client @389 + supplier @389 + Focus_Src @390 + Focus_Entry @391 + origin (1136, 800) + terminus (1286, 800) + ordinal 6) + (object InterMessView "" @420 + location (16, 832) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @421 + Parent_View @420 + location (1439, 788) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE202C0250" + anchor_loc 1 + nlines 1 + max_width 82 + justify 0 + label "new" + pctDist 0.500000 + height 45 + orientation 0) + line_color 3342489 + client @389 + supplier @396 + Focus_Src @390 + Focus_Entry @397 + origin (1135, 832) + terminus (1744, 832) + ordinal 7) + (object SelfMessView "" @422 + location (16, 976) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @423 + Parent_View @422 + location (1260, 933) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE2032001C" + anchor_loc 1 + nlines 1 + max_width 221 + justify 0 + label "setManager" + pctDist 0.833333 + height 44 + orientation 0) + line_color 3342489 + client @389 + supplier @389 + Focus_Src @390 + Focus_Entry @392 + origin (1136, 976) + terminus (1286, 976) + ordinal 8) + (object SelfMessView "" @424 + location (16, 1072) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @425 + Parent_View @424 + location (1481, 1043) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE205B01A2" + anchor_loc 1 + nlines 1 + max_width 658 + justify 0 + label "fireLifecycleEvent(START_EVENT)" + pctDist 2.306667 + height 30 + orientation 0) + line_color 3342489 + client @389 + supplier @389 + Focus_Src @390 + Focus_Entry @393 + origin (1136, 1072) + terminus (1286, 1072) + ordinal 9) + (object InterMessView "" @426 + location (16, 1136) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @427 + Parent_View @426 + location (1535, 1092) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE20960003" + anchor_loc 1 + nlines 1 + max_width 745 + justify 0 + label " // Notify interested LifecycleListeners" + pctDist 0.500000 + height 45 + orientation 0) + line_color 3342489 + client @389 + supplier @399 + Focus_Src @390 + Focus_Entry @401 + origin (1135, 1136) + terminus (1936, 1136) + ordinal 10) + (object SelfMessView "" @428 + location (16, 1264) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @429 + Parent_View @428 + location (2043, 1220) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE20CF018C" + anchor_loc 1 + nlines 1 + max_width 110 + justify 0 + label "start()" + pctDist 0.500000 + height 45 + orientation 0) + line_color 3342489 + client @399 + supplier @399 + Focus_Src @401 + Focus_Entry @402 + origin (1968, 1264) + terminus (2118, 1264) + ordinal 11) + (object SelfMessView "" @430 + location (16, 1456) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @431 + Parent_View @430 + location (2027, 1413) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE20E303E2" + anchor_loc 1 + nlines 1 + max_width 275 + justify 0 + label "defaultConfig()" + pctDist 0.393333 + height 44 + orientation 0) + line_color 3342489 + client @399 + supplier @399 + Focus_Src @401 + Focus_Entry @403 + origin (1968, 1456) + terminus (2118, 1456) + ordinal 13) + (object SelfMessView "" @432 + location (16, 1568) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @433 + Parent_View @432 + location (2043, 1524) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE211D01A1" + anchor_loc 1 + nlines 1 + max_width 349 + justify 0 + label "applicationConfig()" + pctDist 0.500000 + height 45 + orientation 0) + line_color 3342489 + client @399 + supplier @399 + Focus_Src @401 + Focus_Entry @404 + origin (1968, 1568) + terminus (2118, 1568) + ordinal 14) + (object InterMessView "" @434 + location (1664, 1264) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @435 + Parent_View @434 + location (1439, 1220) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE20B600E5" + anchor_loc 1 + nlines 1 + max_width 110 + justify 0 + label "start()" + pctDist 0.500000 + height 45 + orientation 0) + line_color 3342489 + client @389 + supplier @396 + Focus_Src @390 + Focus_Entry @398 + origin (1135, 1264) + terminus (1744, 1264) + ordinal 12) + (object InterMessView "" @436 + location (16, 1616) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @437 + Parent_View @436 + location (1064, 1572) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE21B60288" + anchor_loc 1 + nlines 1 + max_width 145 + justify 0 + label "create()" + pctDist 0.500000 + height 45 + orientation 1) + line_color 3342489 + client @399 + supplier @379 + Focus_Src @404 + Focus_Entry @383 + origin (1936, 1616) + terminus (192, 1616) + ordinal 15) + (object SelfMessView "" @438 + location (16, 1728) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @439 + Parent_View @438 + location (457, 1701) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE21BE021B" + anchor_loc 1 + nlines 1 + max_width 530 + justify 0 + label "// Process web.xml * tld.xml" + pctDist 1.773333 + height 28 + orientation 0) + line_color 3342489 + client @379 + supplier @379 + Focus_Src @383 + Focus_Entry @384 + origin (192, 1728) + terminus (342, 1728) + ordinal 16) + (object InterObjView "StandardWrapper" @440 + location (2208, 224) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline TRUE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @440 + location (2208, 224) + fill_color 13434879 + anchor_loc 1 + nlines 2 + max_width 282 + justify 0 + label "StandardWrapper") + icon_style "Icon" + line_color 3342489 + fill_color 13434879 + quidu "3DFE220C0122" + width 300 + height 2446 + icon_height 0 + icon_width 0 + icon_y_offset 0 + annotation 1 + Focus_Of_Control (object Focus_Of_Control "" @441 + location (2208, 2016) + line_color 3342489 + InterObjView @440 + height 60 + y_coord 0 + Nested FALSE) + Focus_Of_Control (object Focus_Of_Control "" @442 + location (2208, 2176) + line_color 3342489 + InterObjView @440 + height 60 + y_coord 0 + Nested FALSE) + Focus_Of_Control (object Focus_Of_Control "" @443 + location (2208, 2288) + line_color 3342489 + InterObjView @440 + height 60 + y_coord 0 + Nested FALSE) + Focus_Of_Control (object Focus_Of_Control "" @444 + location (2208, 2400) + line_color 3342489 + InterObjView @440 + height 60 + y_coord 0 + Nested FALSE)) + (object InterMessView "" @445 + location (16, 1984) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @446 + Parent_View @445 + location (1063, 1940) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE228B03BA" + anchor_loc 1 + nlines 1 + max_width 1478 + justify 0 + label "createWarpper() // Invoked by a WebWrapperRule (not Directly by the Digester)" + pctDist 0.500000 + height 45 + orientation 0) + line_color 3342489 + client @379 + supplier @399 + Focus_Src @383 + Focus_Entry @405 + origin (191, 1984) + terminus (1936, 1984) + ordinal 17) + (object InterMessView "" @447 + location (16, 2016) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @448 + Parent_View @447 + location (2079, 1972) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE229A0004" + anchor_loc 1 + nlines 1 + max_width 82 + justify 0 + label "new" + pctDist 0.500000 + height 45 + orientation 0) + line_color 3342489 + client @399 + supplier @440 + Focus_Src @405 + Focus_Entry @441 + origin (1967, 2016) + terminus (2192, 2016) + ordinal 18) + (object InterMessView "" @449 + location (16, 2176) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @450 + Parent_View @449 + location (2116, 2134) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE22A700C1" + anchor_loc 1 + nlines 1 + max_width 405 + justify 0 + label "addInstanceListener()" + pctDist 0.662295 + height 43 + orientation 0) + line_color 3342489 + client @399 + supplier @440 + Focus_Src @404 + Focus_Entry @442 + origin (1967, 2176) + terminus (2192, 2176) + ordinal 19) + (object InterMessView "" @451 + location (2496, 2288) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @452 + Parent_View @451 + location (2116, 2245) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE22C701CC" + anchor_loc 1 + nlines 1 + max_width 410 + justify 0 + label "addLifecycleListener()" + pctDist 0.662295 + height 44 + orientation 0) + line_color 3342489 + client @399 + supplier @440 + Focus_Src @404 + Focus_Entry @443 + origin (1967, 2288) + terminus (2192, 2288) + ordinal 20) + (object InterMessView "" @453 + location (16, 2400) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @454 + Parent_View @453 + location (2124, 2357) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE22E80364" + anchor_loc 1 + nlines 1 + max_width 428 + justify 0 + label "addContainerListener()" + pctDist 0.701639 + height 44 + orientation 0) + line_color 3342489 + client @399 + supplier @440 + Focus_Src @404 + Focus_Entry @444 + origin (1967, 2400) + terminus (2192, 2400) + ordinal 21) + (object NoteView @455 + location (1216, 80) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @455 + location (825, 14) + fill_color 13434879 + nlines 2 + max_width 746 + label "Deploy App.") + line_color 3342489 + fill_color 13434879 + width 806 + height 144) + (object NoteView @456 + location (2144, 2704) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @456 + location (1953, 2641) + fill_color 13434879 + nlines 2 + max_width 347 + label "#4 Catalina.start()") + line_color 3342489 + fill_color 13434879 + width 407 + height 138))) + (object InteractionDiagram "1. catalina_request" + mechanism_ref @88 + quid "3DFE3B5001C3" + title "1. catalina_request" + zoom 100 + max_height 28350 + max_width 21600 + origin_x 0 + origin_y 0 + items (list diagram_item_list + (object InterObjView "ThreadPool" @457 + location (176, 224) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline TRUE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @457 + location (176, 224) + fill_color 13434879 + anchor_loc 1 + nlines 2 + max_width 282 + justify 0 + label "ThreadPool") + icon_style "Icon" + line_color 3342489 + fill_color 13434879 + quidu "3DFE402B02C5" + width 300 + height 1276 + icon_height 0 + icon_width 0 + icon_y_offset 0 + annotation 1 + Focus_Of_Control (object Focus_Of_Control "" @458 + location (176, 384) + line_color 3342489 + InterObjView @457 + height 304 + y_coord 244 + Nested FALSE)) + (object InterObjView "TcpWorkerThread" @459 + location (512, 224) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline TRUE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @459 + location (512, 224) + fill_color 13434879 + anchor_loc 1 + nlines 2 + max_width 332 + justify 0 + label "TcpWorkerThread") + icon_style "Icon" + line_color 3342489 + fill_color 13434879 + quidu "3DFE403200F8" + width 350 + height 1276 + icon_height 0 + icon_width 0 + icon_y_offset 0 + annotation 1 + Focus_Of_Control (object Focus_Of_Control "" @460 + location (512, 384) + line_color 3342489 + InterObjView @459 + height 244 + y_coord 184 + Nested FALSE)) + (object InterObjView "Http11Protocol" @461 + location (848, 224) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline TRUE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @461 + location (848, 224) + fill_color 13434879 + anchor_loc 1 + nlines 2 + max_width 282 + justify 0 + label "Http11Protocol") + icon_style "Icon" + line_color 3342489 + fill_color 13434879 + quidu "3DFE40750177" + width 300 + height 1276 + icon_height 0 + icon_width 0 + icon_y_offset 0 + annotation 1 + Focus_Of_Control (object Focus_Of_Control "" @462 + location (848, 400) + line_color 3342489 + InterObjView @461 + height 168 + y_coord 108 + Nested FALSE) + Focus_Of_Control (object Focus_Of_Control "" @463 + location (848, 448) + line_color 3342489 + InterObjView @461 + height 60 + y_coord 0 + Nested TRUE) + Focus_Of_Control (object Focus_Of_Control "" @464 + location (848, 592) + line_color 3342489 + InterObjView @461 + height 120 + y_coord 60 + Nested FALSE) + Focus_Of_Control (object Focus_Of_Control "" @465 + location (848, 592) + line_color 3342489 + InterObjView @461 + height 60 + y_coord 0 + Nested TRUE) + Focus_Of_Control (object Focus_Of_Control "" @466 + location (848, 736) + line_color 3342489 + InterObjView @461 + height 674 + y_coord 614 + Nested FALSE) + Focus_Of_Control (object Focus_Of_Control "" @467 + location (848, 736) + line_color 3342489 + InterObjView @461 + height 60 + y_coord 0 + Nested TRUE)) + (object InterObjView "CoyoteAdapter" @468 + location (1168, 224) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline TRUE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @468 + location (1168, 224) + fill_color 13434879 + anchor_loc 1 + nlines 2 + max_width 282 + justify 0 + label "CoyoteAdapter") + icon_style "Icon" + line_color 3342489 + fill_color 13434879 + quidu "3DFE410600DF" + width 300 + height 1276 + icon_height 0 + icon_width 0 + icon_y_offset 0 + annotation 1 + Focus_Of_Control (object Focus_Of_Control "" @469 + location (1168, 848) + line_color 3342489 + InterObjView @468 + height 502 + y_coord 442 + Nested FALSE) + Focus_Of_Control (object Focus_Of_Control "" @470 + location (1168, 944) + line_color 3342489 + InterObjView @468 + height 352 + y_coord 292 + Nested TRUE) + Focus_Of_Control (object Focus_Of_Control "" @471 + location (1168, 944) + line_color 3342489 + InterObjView @468 + height 60 + y_coord 0 + Nested TRUE)) + (object InterObjView "StandardEngine" @472 + location (1520, 224) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline TRUE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @472 + location (1520, 224) + fill_color 13434879 + anchor_loc 1 + nlines 2 + max_width 363 + justify 0 + label "StandardEngine") + icon_style "Icon" + line_color 3342489 + fill_color 13434879 + quidu "3DFE424B0349" + width 381 + height 1276 + icon_height 0 + icon_width 0 + icon_y_offset 0 + annotation 1 + Focus_Of_Control (object Focus_Of_Control "" @473 + location (1520, 1008) + line_color 3342489 + InterObjView @472 + height 228 + y_coord 168 + Nested FALSE)) + (object InterObjView "StandardPipeline" @474 + location (1872, 224) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline TRUE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @474 + location (1872, 224) + fill_color 13434879 + anchor_loc 1 + nlines 2 + max_width 282 + justify 0 + label "StandardPipeline") + icon_style "Icon" + line_color 3342489 + fill_color 13434879 + quidu "3DFE42900045" + width 300 + height 1276 + icon_height 0 + icon_width 0 + icon_y_offset 0 + annotation 1 + Focus_Of_Control (object Focus_Of_Control "" @475 + location (1872, 1040) + line_color 3342489 + InterObjView @474 + height 136 + y_coord 76 + Nested FALSE)) + (object InterObjView "StandardValveContext" @476 + location (2192, 224) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline TRUE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @476 + location (2192, 224) + fill_color 13434879 + anchor_loc 1 + nlines 2 + max_width 282 + justify 0 + label "StandardValveContext") + icon_style "Icon" + line_color 3342489 + fill_color 13434879 + quidu "3DFE42C002B1" + width 300 + height 1276 + icon_height 0 + icon_width 0 + icon_y_offset 0 + annotation 1 + Focus_Of_Control (object Focus_Of_Control "" @477 + location (2192, 1056) + line_color 3342489 + InterObjView @476 + height 60 + y_coord 0 + Nested FALSE)) + (object InterMessView "" @478 + location (16, 384) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @479 + Parent_View @478 + location (343, 340) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE40E701AE" + anchor_loc 1 + nlines 1 + max_width 112 + justify 0 + label "runIt()" + pctDist 0.500000 + height 45 + orientation 0) + line_color 3342489 + client @457 + supplier @459 + Focus_Src @458 + Focus_Entry @460 + origin (191, 384) + terminus (496, 384) + ordinal 0) + (object InterMessView "" @480 + location (16, 400) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @481 + Parent_View @480 + location (679, 356) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE40FC010E" + anchor_loc 1 + nlines 1 + max_width 359 + justify 0 + label "processConnection" + pctDist 0.500000 + height 45 + orientation 0) + line_color 3342489 + client @459 + supplier @461 + Focus_Src @460 + Focus_Entry @462 + origin (527, 400) + terminus (832, 400) + ordinal 1) + (object SelfMessView "" @482 + location (16, 448) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @483 + Parent_View @482 + location (969, 405) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE4111029F" + anchor_loc 1 + nlines 1 + max_width 175 + justify 0 + label "process()" + pctDist 0.706667 + height 44 + orientation 0) + line_color 3342489 + client @461 + supplier @461 + Focus_Src @462 + Focus_Entry @463 + origin (864, 448) + terminus (1014, 448) + ordinal 2) + (object SelfMessView "" @484 + location (16, 592) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @485 + Parent_View @484 + location (1048, 549) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE415C0151" + anchor_loc 1 + nlines 1 + max_width 291 + justify 0 + label "parseHeaders()" + pctDist 1.226667 + height 44 + orientation 0) + line_color 3342489 + client @461 + supplier @461 + Focus_Src @464 + Focus_Entry @465 + origin (864, 592) + terminus (1014, 592) + ordinal 3) + (object SelfMessView "" @486 + location (16, 736) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @487 + Parent_View @486 + location (1052, 692) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE41A60161" + anchor_loc 1 + nlines 1 + max_width 328 + justify 0 + label "prepareRequest()" + pctDist 1.253333 + height 44 + orientation 0) + line_color 3342489 + client @461 + supplier @461 + Focus_Src @466 + Focus_Entry @467 + origin (864, 736) + terminus (1014, 736) + ordinal 4) + (object InterMessView "" @488 + location (992, 848) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @489 + Parent_View @488 + location (1007, 804) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE41D60107" + anchor_loc 1 + nlines 1 + max_width 162 + justify 0 + label "service()" + pctDist 0.500000 + height 45 + orientation 0) + line_color 3342489 + client @461 + supplier @468 + Focus_Src @466 + Focus_Entry @469 + origin (863, 848) + terminus (1152, 848) + ordinal 5) + (object SelfMessView "" @490 + location (16, 944) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @491 + Parent_View @490 + location (1372, 916) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE422C01F1" + anchor_loc 1 + nlines 1 + max_width 373 + justify 0 + label "postParseRequest()" + pctDist 1.253333 + height 28 + orientation 0) + line_color 3342489 + client @468 + supplier @468 + Focus_Src @470 + Focus_Entry @471 + origin (1184, 944) + terminus (1334, 944) + ordinal 6) + (object InterMessView "" @492 + location (1344, 1008) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @493 + Parent_View @492 + location (1343, 964) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE42800238" + anchor_loc 1 + nlines 1 + max_width 149 + justify 0 + label "invoke()" + pctDist 0.500000 + height 45 + orientation 0) + line_color 3342489 + client @468 + supplier @472 + Focus_Src @470 + Focus_Entry @473 + origin (1183, 1008) + terminus (1504, 1008) + ordinal 7) + (object InterMessView "" @494 + location (16, 1040) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @495 + Parent_View @494 + location (1695, 996) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE429A002D" + anchor_loc 1 + nlines 1 + max_width 149 + justify 0 + label "invoke()" + pctDist 0.500000 + height 45 + orientation 0) + line_color 3342489 + client @472 + supplier @474 + Focus_Src @473 + Focus_Entry @475 + origin (1535, 1040) + terminus (1856, 1040) + ordinal 8) + (object InterMessView "" @496 + location (16, 1056) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @497 + Parent_View @496 + location (2031, 1012) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE42CE0230" + anchor_loc 1 + nlines 1 + max_width 149 + justify 0 + label "invoke()" + pctDist 0.500000 + height 45 + orientation 0) + line_color 3342489 + client @474 + supplier @476 + Focus_Src @475 + Focus_Entry @477 + origin (1887, 1056) + terminus (2176, 1056) + ordinal 9) + (object NoteView @498 + location (2000, 2016) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @498 + location (1862, 1956) + fill_color 13434879 + nlines 2 + max_width 240 + label "See next diagram") + line_color 3342489 + fill_color 13434879 + width 300 + height 132) + (object AttachView "" @499 + stereotype TRUE + line_color 3342489 + client @498 + supplier @476 + line_style 0))) + (object InteractionDiagram "2. catalina_request_2" + mechanism_ref @89 + quid "3DFE42F7024C" + title "2. catalina_request_2" + zoom 100 + max_height 28350 + max_width 21600 + origin_x 0 + origin_y 0 + items (list diagram_item_list + (object InterObjView "StandardContextValve" @500 + location (224, 224) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline TRUE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @500 + location (224, 224) + fill_color 13434879 + anchor_loc 1 + nlines 2 + max_width 401 + justify 0 + label "StandardContextValve") + icon_style "Icon" + line_color 3342489 + fill_color 13434879 + quidu "3DFE4307001E" + width 419 + height 1678 + icon_height 0 + icon_width 0 + icon_y_offset 0 + annotation 1 + Focus_Of_Control (object Focus_Of_Control "" @501 + location (224, 384) + line_color 3342489 + InterObjView @500 + height 386 + y_coord 326 + Nested FALSE) + Focus_Of_Control (object Focus_Of_Control "" @502 + location (224, 704) + line_color 3342489 + InterObjView @500 + height 60 + y_coord 0 + Nested TRUE) + Focus_Of_Control (object Focus_Of_Control "" @503 + location (224, 896) + line_color 3342489 + InterObjView @500 + height 916 + y_coord 856 + Nested FALSE) + Focus_Of_Control (object Focus_Of_Control "" @504 + location (224, 1024) + line_color 3342489 + InterObjView @500 + height 60 + y_coord 0 + Nested TRUE) + Focus_Of_Control (object Focus_Of_Control "" @505 + location (224, 1280) + line_color 3342489 + InterObjView @500 + height 60 + y_coord 0 + Nested TRUE)) + (object InterObjView "StandardEngineValve" @506 + location (592, 224) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline TRUE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @506 + location (592, 224) + fill_color 13434879 + anchor_loc 1 + nlines 2 + max_width 282 + justify 0 + label "StandardEngineValve") + icon_style "Icon" + line_color 3342489 + fill_color 13434879 + quidu "3DFE432801F3" + width 300 + height 1678 + icon_height 0 + icon_width 0 + icon_y_offset 0 + annotation 1 + Focus_Of_Control (object Focus_Of_Control "" @507 + location (592, 384) + line_color 3342489 + InterObjView @506 + height 264 + y_coord 204 + Nested FALSE)) + (object InterObjView "StandardHost" @508 + location (912, 224) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline TRUE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @508 + location (912, 224) + fill_color 13434879 + anchor_loc 1 + nlines 2 + max_width 282 + justify 0 + label "StandardHost") + icon_style "Icon" + line_color 3342489 + fill_color 13434879 + quidu "3DFE436503BD" + width 300 + height 1678 + icon_height 0 + icon_width 0 + icon_y_offset 0 + annotation 1 + Focus_Of_Control (object Focus_Of_Control "" @509 + location (912, 416) + line_color 3342489 + InterObjView @508 + height 431 + y_coord 371 + Nested FALSE) + Focus_Of_Control (object Focus_Of_Control "" @510 + location (912, 528) + line_color 3342489 + InterObjView @508 + height 60 + y_coord 0 + Nested TRUE) + Focus_Of_Control (object Focus_Of_Control "" @511 + location (912, 704) + line_color 3342489 + InterObjView @508 + height 120 + y_coord 60 + Nested TRUE)) + (object InterObjView "ErrorReportValve" @512 + location (1264, 224) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline TRUE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @512 + location (1264, 224) + fill_color 13434879 + anchor_loc 1 + nlines 2 + max_width 294 + justify 0 + label "ErrorReportValve") + icon_style "Icon" + line_color 3342489 + fill_color 13434879 + quidu "3DFE438C028D" + width 312 + height 1678 + icon_height 0 + icon_width 0 + icon_y_offset 0 + annotation 1 + Focus_Of_Control (object Focus_Of_Control "" @513 + location (1264, 896) + line_color 3342489 + InterObjView @512 + height 248 + y_coord 188 + Nested FALSE) + Focus_Of_Control (object Focus_Of_Control "" @514 + location (1264, 944) + line_color 3342489 + InterObjView @512 + height 60 + y_coord 0 + Nested TRUE)) + (object InterObjView "ErrorDispatcherValve" @515 + location (1584, 224) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline TRUE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @515 + location (1584, 224) + fill_color 13434879 + anchor_loc 1 + nlines 2 + max_width 295 + justify 0 + label "ErrorDispatcherValve") + icon_style "Icon" + line_color 3342489 + fill_color 13434879 + quidu "3DFE451F01EC" + width 313 + height 1678 + icon_height 0 + icon_width 0 + icon_y_offset 0 + annotation 1 + Focus_Of_Control (object Focus_Of_Control "" @516 + location (1584, 1168) + line_color 3342489 + InterObjView @515 + height 232 + y_coord 172 + Nested FALSE)) + (object InterObjView "StandardHostValve" @517 + location (1904, 224) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline TRUE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @517 + location (1904, 224) + fill_color 13434879 + anchor_loc 1 + nlines 2 + max_width 295 + justify 0 + label "StandardHostValve") + icon_style "Icon" + line_color 3342489 + fill_color 13434879 + quidu "3DFE47310130" + width 313 + height 1678 + icon_height 0 + icon_width 0 + icon_y_offset 0 + annotation 1 + Focus_Of_Control (object Focus_Of_Control "" @518 + location (1904, 1472) + line_color 3342489 + InterObjView @517 + height 280 + y_coord 220 + Nested FALSE) + Focus_Of_Control (object Focus_Of_Control "" @519 + location (1904, 1536) + line_color 3342489 + InterObjView @517 + height 60 + y_coord 0 + Nested TRUE)) + (object InterObjView "StandardContext" @520 + location (2224, 224) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline TRUE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @520 + location (2224, 224) + fill_color 13434879 + anchor_loc 1 + nlines 2 + max_width 282 + justify 0 + label "StandardContext") + icon_style "Icon" + line_color 3342489 + fill_color 13434879 + quidu "3DFE47C100F1" + width 300 + height 1678 + icon_height 0 + icon_width 0 + icon_y_offset 0 + annotation 1 + Focus_Of_Control (object Focus_Of_Control "" @521 + location (2224, 1632) + line_color 3342489 + InterObjView @520 + height 60 + y_coord 0 + Nested FALSE)) + (object InterMessView "" @522 + location (16, 384) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @523 + Parent_View @522 + location (407, 340) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE434C019B" + anchor_loc 1 + nlines 1 + max_width 146 + justify 0 + label "invoke()" + pctDist 0.500000 + height 45 + orientation 0) + line_color 3342489 + client @500 + supplier @506 + Focus_Src @501 + Focus_Entry @507 + origin (239, 384) + terminus (576, 384) + ordinal 0) + (object InterMessView "" @524 + location (16, 416) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @525 + Parent_View @524 + location (751, 372) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE436C009D" + anchor_loc 1 + nlines 1 + max_width 107 + justify 0 + label "map()" + pctDist 0.500000 + height 45 + orientation 0) + line_color 3342489 + client @506 + supplier @508 + Focus_Src @507 + Focus_Entry @509 + origin (607, 416) + terminus (896, 416) + ordinal 1) + (object InterMessView "" @526 + location (800, 528) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @527 + Parent_View @526 + location (751, 484) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE43830063" + anchor_loc 1 + nlines 1 + max_width 146 + justify 0 + label "invoke()" + pctDist 0.500000 + height 45 + orientation 0) + line_color 3342489 + client @506 + supplier @508 + Focus_Src @507 + Focus_Entry @510 + origin (607, 528) + terminus (896, 528) + ordinal 2) + (object InterMessView "" @528 + location (608, 704) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @529 + Parent_View @528 + location (568, 660) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE43B903BF" + anchor_loc 1 + nlines 1 + max_width 146 + justify 0 + label "invoke()" + pctDist 0.500000 + height 45 + orientation 1) + line_color 3342489 + client @508 + supplier @500 + Focus_Src @511 + Focus_Entry @502 + origin (896, 704) + terminus (240, 704) + ordinal 3) + (object InterMessView "" @530 + location (752, 896) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @531 + Parent_View @530 + location (743, 852) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE43C203A4" + anchor_loc 1 + nlines 1 + max_width 146 + justify 0 + label "invoke()" + pctDist 0.500000 + height 45 + orientation 0) + line_color 3342489 + client @500 + supplier @512 + Focus_Src @503 + Focus_Entry @513 + origin (239, 896) + terminus (1248, 896) + ordinal 4) + (object SelfMessView "" @532 + location (16, 944) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @533 + Parent_View @532 + location (1355, 900) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE442501B1" + anchor_loc 1 + nlines 1 + max_width 135 + justify 0 + label "report()" + pctDist 0.500000 + height 45 + orientation 0) + line_color 3342489 + client @512 + supplier @512 + Focus_Src @513 + Focus_Entry @514 + origin (1280, 944) + terminus (1430, 944) + ordinal 5) + (object InterMessView "" @534 + location (16, 1024) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @535 + Parent_View @534 + location (744, 980) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE46330293" + anchor_loc 1 + nlines 1 + max_width 230 + justify 0 + label "invokeNext()" + pctDist 0.500000 + height 45 + orientation 1) + line_color 3342489 + client @512 + supplier @500 + Focus_Src @513 + Focus_Entry @504 + origin (1248, 1024) + terminus (240, 1024) + ordinal 6) + (object InterMessView "" @536 + location (944, 1168) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @537 + Parent_View @536 + location (903, 1124) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE46E70026" + anchor_loc 1 + nlines 1 + max_width 146 + justify 0 + label "invoke()" + pctDist 0.500000 + height 45 + orientation 0) + line_color 3342489 + client @500 + supplier @515 + Focus_Src @503 + Focus_Entry @516 + origin (239, 1168) + terminus (1568, 1168) + ordinal 7) + (object InterMessView "" @538 + location (16, 1280) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @539 + Parent_View @538 + location (904, 1236) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE475D03A0" + anchor_loc 1 + nlines 1 + max_width 206 + justify 0 + label "invokeNext" + pctDist 0.500000 + height 45 + orientation 1) + line_color 3342489 + client @515 + supplier @500 + Focus_Src @516 + Focus_Entry @505 + origin (1568, 1280) + terminus (240, 1280) + ordinal 8) + (object InterMessView "" @540 + location (1184, 1472) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @541 + Parent_View @540 + location (1063, 1428) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE476503CA" + anchor_loc 1 + nlines 1 + max_width 146 + justify 0 + label "invoke()" + pctDist 0.500000 + height 45 + orientation 0) + line_color 3342489 + client @500 + supplier @517 + Focus_Src @503 + Focus_Entry @518 + origin (239, 1472) + terminus (1888, 1472) + ordinal 9) + (object SelfMessView "" @542 + location (16, 1536) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @543 + Parent_View @542 + location (1995, 1492) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE47CD0167" + anchor_loc 1 + nlines 1 + max_width 295 + justify 0 + label "map() //Context" + pctDist 0.500000 + height 45 + orientation 0) + line_color 3342489 + client @517 + supplier @517 + Focus_Src @518 + Focus_Entry @519 + origin (1920, 1536) + terminus (2070, 1536) + ordinal 10) + (object InterMessView "" @544 + location (16, 1632) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @545 + Parent_View @544 + location (2063, 1588) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE47D500B4" + anchor_loc 1 + nlines 1 + max_width 146 + justify 0 + label "invoke()" + pctDist 0.500000 + height 45 + orientation 0) + line_color 3342489 + client @517 + supplier @520 + Focus_Src @518 + Focus_Entry @521 + origin (1919, 1632) + terminus (2208, 1632) + ordinal 11))) + (object InteractionDiagram "3. catalina_request_3" + mechanism_ref @90 + quid "3DFE48A202AD" + title "3. catalina_request_3" + zoom 100 + max_height 28350 + max_width 21600 + origin_x 612 + origin_y 938 + items (list diagram_item_list + (object InterObjView "StandardContext" @546 + location (160, 224) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline TRUE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @546 + location (160, 224) + fill_color 13434879 + anchor_loc 1 + nlines 2 + max_width 282 + justify 0 + label "StandardContext") + icon_style "Icon" + line_color 3342489 + fill_color 13434879 + quidu "3DFE48B001D1" + width 300 + height 2226 + icon_height 0 + icon_width 0 + icon_y_offset 0 + annotation 1 + Focus_Of_Control (object Focus_Of_Control "" @547 + location (160, 400) + line_color 3342489 + InterObjView @546 + height 1960 + y_coord 1900 + Nested FALSE)) + (object InterObjView "StandardPipeline" @548 + location (480, 224) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline TRUE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @548 + location (480, 224) + fill_color 13434879 + anchor_loc 1 + nlines 2 + max_width 282 + justify 0 + label "StandardPipeline") + icon_style "Icon" + line_color 3342489 + fill_color 13434879 + quidu "3DFE48B80088" + width 300 + height 2226 + icon_height 0 + icon_width 0 + icon_y_offset 0 + annotation 1 + Focus_Of_Control (object Focus_Of_Control "" @549 + location (480, 400) + line_color 3342489 + InterObjView @548 + height 1900 + y_coord 1840 + Nested FALSE) + Focus_Of_Control (object Focus_Of_Control "" @550 + location (480, 1088) + line_color 3342489 + InterObjView @548 + height 60 + y_coord 0 + Nested TRUE)) + (object InterObjView "StandardValveContext" @551 + location (800, 224) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline TRUE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @551 + location (800, 224) + fill_color 13434879 + anchor_loc 1 + nlines 2 + max_width 282 + justify 0 + label "StandardValveContext") + icon_style "Icon" + line_color 3342489 + fill_color 13434879 + quidu "3DFE48D000DC" + width 300 + height 2226 + icon_height 0 + icon_width 0 + icon_y_offset 0 + annotation 1 + Focus_Of_Control (object Focus_Of_Control "" @552 + location (800, 736) + line_color 3342489 + InterObjView @551 + height 1510 + y_coord 1450 + Nested FALSE) + Focus_Of_Control (object Focus_Of_Control "" @553 + location (800, 1168) + line_color 3342489 + InterObjView @551 + height 1072 + y_coord 1012 + Nested TRUE)) + (object InterObjView "StandardContextValve" @554 + location (1104, 224) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline TRUE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @554 + location (1104, 224) + fill_color 13434879 + anchor_loc 1 + nlines 2 + max_width 282 + justify 0 + label "StandardContextValve") + icon_style "Icon" + line_color 3342489 + fill_color 13434879 + quidu "3DFE490303A7" + width 300 + height 2226 + icon_height 0 + icon_width 0 + icon_y_offset 0 + annotation 1 + Focus_Of_Control (object Focus_Of_Control "" @555 + location (1104, 800) + line_color 3342489 + InterObjView @554 + height 468 + y_coord 408 + Nested FALSE) + Focus_Of_Control (object Focus_Of_Control "" @556 + location (1104, 848) + line_color 3342489 + InterObjView @554 + height 60 + y_coord 0 + Nested TRUE)) + (object InterObjView "StandardWrapper" @557 + location (1424, 224) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline TRUE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @557 + location (1424, 224) + fill_color 13434879 + anchor_loc 1 + nlines 2 + max_width 288 + justify 0 + label "StandardWrapper") + icon_style "Icon" + line_color 3342489 + fill_color 13434879 + quidu "3DFE49370351" + width 306 + height 2226 + icon_height 0 + icon_width 0 + icon_y_offset 0 + annotation 1 + Focus_Of_Control (object Focus_Of_Control "" @558 + location (1424, 944) + line_color 3342489 + InterObjView @557 + height 264 + y_coord 204 + Nested FALSE) + Focus_Of_Control (object Focus_Of_Control "" @559 + location (1424, 1520) + line_color 3342489 + InterObjView @557 + height 340 + y_coord 280 + Nested FALSE)) + (object InterObjView "StandardWrapperValve" @560 + location (1744, 224) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline TRUE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @560 + location (1744, 224) + fill_color 13434879 + anchor_loc 1 + nlines 2 + max_width 282 + justify 0 + label "StandardWrapperValve") + icon_style "Icon" + line_color 3342489 + fill_color 13434879 + quidu "3DFE49890056" + width 300 + height 2226 + icon_height 0 + icon_width 0 + icon_y_offset 0 + annotation 1 + Focus_Of_Control (object Focus_Of_Control "" @561 + location (1744, 1440) + line_color 3342489 + InterObjView @560 + height 740 + y_coord 680 + Nested FALSE) + Focus_Of_Control (object Focus_Of_Control "" @562 + location (1744, 1616) + line_color 3342489 + InterObjView @560 + height 184 + y_coord 124 + Nested FALSE) + Focus_Of_Control (object Focus_Of_Control "" @563 + location (1744, 2000) + line_color 3342489 + InterObjView @560 + height 60 + y_coord 0 + Nested TRUE)) + (object InterObjView "ApplicationFilterChain" @564 + location (2064, 224) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline TRUE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @564 + location (2064, 224) + fill_color 13434879 + anchor_loc 1 + nlines 2 + max_width 282 + justify 0 + label "ApplicationFilterChain") + icon_style "Icon" + line_color 3342489 + fill_color 13434879 + quidu "3DFE4A1500B2" + width 300 + height 2226 + icon_height 0 + icon_width 0 + icon_y_offset 0 + annotation 1 + Focus_Of_Control (object Focus_Of_Control "" @565 + location (2064, 1680) + line_color 3342489 + InterObjView @564 + height 60 + y_coord 0 + Nested FALSE) + Focus_Of_Control (object Focus_Of_Control "" @566 + location (2064, 1808) + line_color 3342489 + InterObjView @564 + height 312 + y_coord 252 + Nested FALSE) + Focus_Of_Control (object Focus_Of_Control "" @567 + location (2064, 1872) + line_color 3342489 + InterObjView @564 + height 60 + y_coord 0 + Nested TRUE)) + (object InterMessView "" @568 + location (336, 400) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @569 + Parent_View @568 + location (319, 356) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE48BE0268" + anchor_loc 1 + nlines 1 + max_width 147 + justify 0 + label "invoke()" + pctDist 0.500000 + height 45 + orientation 0) + line_color 3342489 + client @546 + supplier @548 + Focus_Src @547 + Focus_Entry @549 + origin (175, 400) + terminus (464, 400) + ordinal 0) + (object InterMessView "" @570 + location (16, 736) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @571 + Parent_View @570 + location (639, 692) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE48EA003A" + anchor_loc 1 + nlines 1 + max_width 147 + justify 0 + label "invoke()" + pctDist 0.500000 + height 45 + orientation 0) + line_color 3342489 + client @548 + supplier @551 + Focus_Src @549 + Focus_Entry @552 + origin (495, 736) + terminus (784, 736) + ordinal 1) + (object InterMessView "" @572 + location (16, 800) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @573 + Parent_View @572 + location (951, 756) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE491102D6" + anchor_loc 1 + nlines 1 + max_width 147 + justify 0 + label "invoke()" + pctDist 0.500000 + height 45 + orientation 0) + line_color 3342489 + client @551 + supplier @554 + Focus_Src @552 + Focus_Entry @555 + origin (815, 800) + terminus (1088, 800) + ordinal 2) + (object SelfMessView "" @574 + location (16, 848) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @575 + Parent_View @574 + location (1322, 821) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE492F033D" + anchor_loc 1 + nlines 1 + max_width 437 + justify 0 + label "map //return Wrapper" + pctDist 1.346667 + height 28 + orientation 0) + line_color 3342489 + client @554 + supplier @554 + Focus_Src @555 + Focus_Entry @556 + origin (1120, 848) + terminus (1270, 848) + ordinal 3) + (object InterMessView "" @576 + location (1264, 944) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @577 + Parent_View @576 + location (1262, 901) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE494A0151" + anchor_loc 1 + nlines 1 + max_width 147 + justify 0 + label "invoke()" + pctDist 0.498270 + height 44 + orientation 0) + line_color 3342489 + client @554 + supplier @557 + Focus_Src @555 + Focus_Entry @558 + origin (1119, 944) + terminus (1408, 944) + ordinal 4) + (object InterMessView "" @578 + location (960, 1088) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @579 + Parent_View @578 + location (952, 1044) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE495F0288" + anchor_loc 1 + nlines 1 + max_width 147 + justify 0 + label "invoke()" + pctDist 0.500000 + height 45 + orientation 1) + line_color 3342489 + client @557 + supplier @548 + Focus_Src @558 + Focus_Entry @550 + origin (1408, 1088) + terminus (496, 1088) + ordinal 5) + (object InterMessView "" @580 + location (16, 1168) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @581 + Parent_View @580 + location (639, 1124) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE4976015D" + anchor_loc 1 + nlines 1 + max_width 147 + justify 0 + label "invoke()" + pctDist 0.500000 + height 45 + orientation 0) + line_color 3342489 + client @548 + supplier @551 + Focus_Src @549 + Focus_Entry @553 + origin (495, 1168) + terminus (784, 1168) + ordinal 6) + (object InterMessView "" @582 + location (1296, 1440) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @583 + Parent_View @582 + location (1271, 1396) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE4993023C" + anchor_loc 1 + nlines 1 + max_width 147 + justify 0 + label "invoke()" + pctDist 0.500000 + height 45 + orientation 0) + line_color 3342489 + client @551 + supplier @560 + Focus_Src @553 + Focus_Entry @561 + origin (815, 1440) + terminus (1728, 1440) + ordinal 7) + (object InterMessView "" @584 + location (1616, 1520) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @585 + Parent_View @584 + location (1584, 1476) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE49EC004F" + anchor_loc 1 + nlines 1 + max_width 175 + justify 0 + label "allocate()" + pctDist 0.500000 + height 45 + orientation 1) + line_color 3342489 + client @560 + supplier @557 + Focus_Src @561 + Focus_Entry @559 + origin (1728, 1520) + terminus (1440, 1520) + ordinal 8) + (object InterMessView "" @586 + location (1616, 1616) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @587 + Parent_View @586 + location (1583, 1572) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE4A200067" + anchor_loc 1 + nlines 1 + max_width 242 + justify 0 + label "return servlet" + pctDist 0.500000 + height 45 + orientation 0) + line_color 3342489 + client @557 + supplier @560 + Focus_Src @559 + Focus_Entry @562 + origin (1439, 1616) + terminus (1728, 1616) + ordinal 9) + (object InterMessView "" @588 + location (1936, 1680) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @589 + Parent_View @588 + location (1937, 1636) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE4A29027E" + anchor_loc 1 + nlines 1 + max_width 343 + justify 0 + label "createFilterChain()" + pctDist 0.619377 + height 45 + orientation 0) + line_color 3342489 + client @560 + supplier @564 + Focus_Src @562 + Focus_Entry @565 + origin (1759, 1680) + terminus (2048, 1680) + ordinal 10) + (object InterMessView "" @590 + location (16, 1808) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @591 + Parent_View @590 + location (1902, 1764) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE4A490283" + anchor_loc 1 + nlines 1 + max_width 170 + justify 0 + label "doFilter()" + pctDist 0.498270 + height 45 + orientation 0) + line_color 3342489 + client @560 + supplier @564 + Focus_Src @561 + Focus_Entry @566 + origin (1759, 1808) + terminus (2048, 1808) + ordinal 11) + (object InterObjView "$UNNAMED$0" @592 + location (2240, 368) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline TRUE + strike FALSE + color 0 + default_color TRUE) + label (object ItemLabel + Parent_View @592 + location (2240, 368) + fill_color 13434879 + anchor_loc 1 + nlines 2 + max_width 282 + justify 0 + label "") + stereotype (object ItemLabel + Parent_View @592 + location (2240, 368) + fill_color 13434879 + anchor 10 + anchor_loc 1 + nlines 1 + max_width 222 + justify 0 + label "<>") + icon_style "Icon" + line_color 3342489 + fill_color 13434879 + quidu "3DFE4BAE0056" + width 300 + height 2082 + icon_height 0 + icon_width 0 + icon_y_offset 0 + annotation 1 + Focus_Of_Control (object Focus_Of_Control "" @593 + location (2240, 428) + InterObjView @592 + height 60 + y_coord 0 + Nested FALSE) + Focus_Of_Control (object Focus_Of_Control "" @594 + location (2240, 1984) + line_color 3342489 + InterObjView @592 + height 60 + y_coord 0 + Nested FALSE)) + (object SelfMessView "" @595 + location (16, 1872) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @596 + Parent_View @595 + location (2155, 1828) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE4C2701C3" + anchor_loc 1 + nlines 1 + max_width 308 + justify 0 + label "internalDoFilter()" + pctDist 0.500000 + height 45 + orientation 0) + line_color 3342489 + client @564 + supplier @564 + Focus_Src @566 + Focus_Entry @567 + origin (2080, 1872) + terminus (2230, 1872) + ordinal 12) + (object InterMessView "" @597 + location (2144, 1984) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @598 + Parent_View @597 + location (2151, 1940) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE4CA502BF" + anchor_loc 1 + nlines 1 + max_width 162 + justify 0 + label "service()" + pctDist 0.500000 + height 45 + orientation 0) + line_color 3342489 + client @564 + supplier @592 + Focus_Src @566 + Focus_Entry @594 + origin (2079, 1984) + terminus (2224, 1984) + ordinal 13) + (object InterMessView "" @599 + location (16, 2000) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + label (object SegLabel @600 + Parent_View @599 + location (1904, 1956) + font (object Font + size 10 + face "Arial" + bold FALSE + italics FALSE + underline FALSE + strike FALSE + color 0 + default_color TRUE) + quidu "3DFE4CB4025B" + anchor_loc 1 + nlines 1 + max_width 113 + justify 0 + label "return" + pctDist 0.500000 + height 45 + orientation 1) + line_color 3342489 + client @564 + supplier @560 + Focus_Src @566 + Focus_Entry @563 + origin (2048, 2000) + terminus (1760, 2000) + ordinal 14))))) + root_subsystem (object SubSystem "Component View" + quid "3DFDF6CE036A" + physical_models (list unit_reference_list) + physical_presentations (list unit_reference_list + (object Module_Diagram "Main" + quid "3DFDF6D201FD" + title "Main" + zoom 100 + max_height 28350 + max_width 21600 + origin_x 0 + origin_y 0 + items (list diagram_item_list)))) + process_structure (object Processes + quid "3DFDF6CE0373" + ProcsNDevs (list + (object Process_Diagram "Deployment View" + quid "3DFDF6CE0387" + title "Deployment View" + zoom 100 + max_height 28350 + max_width 21600 + origin_x 0 + origin_y 0 + items (list diagram_item_list)))) + properties (object Properties + attributes (list Attribute_Set + (object Attribute + tool "Data Modeler" + name "propertyId" + value "809135966") + (object Attribute + tool "Data Modeler" + name "default__Project" + value (list Attribute_Set + (object Attribute + tool "Data Modeler" + name "project" + value "") + (object Attribute + tool "Data Modeler" + name "TableCounter" + value 0) + (object Attribute + tool "Data Modeler" + name "ViewCounter" + value 0) + (object Attribute + tool "Data Modeler" + name "DomainCounter" + value 0) + (object Attribute + tool "Data Modeler" + name "SPPackageCounter" + value 0) + (object Attribute + tool "Data Modeler" + name "TriggerCounter" + value 0) + (object Attribute + tool "Data Modeler" + name "IndexCounter" + value 0) + (object Attribute + tool "Data Modeler" + name "ConstraintCounter" + value 0) + (object Attribute + tool "Data Modeler" + name "StoreProcedureCounter" + value 0) + (object Attribute + tool "Data Modeler" + name "PrimaryKeyCounter" + value 0) + (object Attribute + tool "Data Modeler" + name "ForeignKeyCounter" + value 0) + (object Attribute + tool "Data Modeler" + name "JoinCounter" + value 0) + (object Attribute + tool "Data Modeler" + name "TableSpaceCounter" + value 0) + (object Attribute + tool "Data Modeler" + name "cONTAINERCounter" + value 0) + (object Attribute + tool "Data Modeler" + name "TablePrefix" + value "") + (object Attribute + tool "Data Modeler" + name "ViewPrefix" + value "") + (object Attribute + tool "Data Modeler" + name "DomainPrefix" + value "") + (object Attribute + tool "Data Modeler" + name "TriggerPrefix" + value "") + (object Attribute + tool "Data Modeler" + name "IndexPrefix" + value "") + (object Attribute + tool "Data Modeler" + name "ConstraintPrefix" + value "") + (object Attribute + tool "Data Modeler" + name "StoreProcedurePrefix" + value "") + (object Attribute + tool "Data Modeler" + name "PrimaryKeyPrefix" + value "") + (object Attribute + tool "Data Modeler" + name "ForeignKeyPrefix" + value "") + (object Attribute + tool "Data Modeler" + name "TableSpacePrefix" + value ""))) + (object Attribute + tool "Data Modeler" + name "default__Module-Spec" + value (list Attribute_Set + (object Attribute + tool "Data Modeler" + name "dmItem" + value FALSE) + (object Attribute + tool "Data Modeler" + name "DMName" + value "") + (object Attribute + tool "Data Modeler" + name "IsDatabase" + value FALSE) + (object Attribute + tool "Data Modeler" + name "TargetDatabase" + value "") + (object Attribute + tool "Data Modeler" + name "Location" + value "") + (object Attribute + tool "Data Modeler" + name "IsTableSpace" + value FALSE) + (object Attribute + tool "Data Modeler" + name "TableSpaceType" + value "") + (object Attribute + tool "Data Modeler" + name "IsDeault" + value FALSE) + (object Attribute + tool "Data Modeler" + name "BufferPool" + value "") + (object Attribute + tool "Data Modeler" + name "ExtentSize" + value 1) + (object Attribute + tool "Data Modeler" + name "PrefetchSize" + value 1) + (object Attribute + tool "Data Modeler" + name "PageSize" + value 4) + (object Attribute + tool "Data Modeler" + name "ManagedBy" + value "") + (object Attribute + tool "Data Modeler" + name "ContainerList" + value ""))) + (object Attribute + tool "Data Modeler" + name "default__Category" + value (list Attribute_Set + (object Attribute + tool "Data Modeler" + name "dmItem" + value FALSE) + (object Attribute + tool "Data Modeler" + name "DMName" + value "") + (object Attribute + tool "Data Modeler" + name "dmSchema" + value "") + (object Attribute + tool "Data Modeler" + name "dmDomainPackage" + value "") + (object Attribute + tool "Data Modeler" + name "IsSchema" + value FALSE) + (object Attribute + tool "Data Modeler" + name "IsDomainPackage" + value FALSE) + (object Attribute + tool "Data Modeler" + name "IsRootSchema" + value FALSE) + (object Attribute + tool "Data Modeler" + name "IsRootDomainPackage" + value FALSE) + (object Attribute + tool "Data Modeler" + name "IsSchemaPackage" + value FALSE) + (object Attribute + tool "Data Modeler" + name "DatabaseID" + value "") + (object Attribute + tool "Data Modeler" + name "DBMS" + value ""))) + (object Attribute + tool "Data Modeler" + name "default__Class" + value (list Attribute_Set + (object Attribute + tool "Data Modeler" + name "dmItem" + value FALSE) + (object Attribute + tool "Data Modeler" + name "DMName" + value "") + (object Attribute + tool "Data Modeler" + name "IsTable" + value FALSE) + (object Attribute + tool "Data Modeler" + name "IsView" + value FALSE) + (object Attribute + tool "Data Modeler" + name "IsDomain" + value FALSE) + (object Attribute + tool "Data Modeler" + name "IsSPPackage" + value FALSE) + (object Attribute + tool "Data Modeler" + name "Synonymns" + value "") + (object Attribute + tool "Data Modeler" + name "TableSpaceID" + value "") + (object Attribute + tool "Data Modeler" + name "SourceId" + value "") + (object Attribute + tool "Data Modeler" + name "SourceType" + value "") + (object Attribute + tool "Data Modeler" + name "CorrelationName" + value "") + (object Attribute + tool "Data Modeler" + name "SelectClause" + value "") + (object Attribute + tool "Data Modeler" + name "IsUpdateable" + value TRUE) + (object Attribute + tool "Data Modeler" + name "CheckOption" + value "None") + (object Attribute + tool "Data Modeler" + name "IsSnapShot" + value FALSE) + (object Attribute + tool "Data Modeler" + name "IsDistinct" + value FALSE) + (object Attribute + tool "Data Modeler" + name "PersistToServer" + value "") + (object Attribute + tool "Data Modeler" + name "IsPackage" + value FALSE))) + (object Attribute + tool "Data Modeler" + name "default__Attribute" + value (list Attribute_Set + (object Attribute + tool "Data Modeler" + name "dmItem" + value FALSE) + (object Attribute + tool "Data Modeler" + name "DMName" + value "") + (object Attribute + tool "Data Modeler" + name "Ordinal" + value 0) + (object Attribute + tool "Data Modeler" + name "IsIdentity" + value FALSE) + (object Attribute + tool "Data Modeler" + name "IsUnique" + value FALSE) + (object Attribute + tool "Data Modeler" + name "NullsAllowed" + value FALSE) + (object Attribute + tool "Data Modeler" + name "Length" + value 0) + (object Attribute + tool "Data Modeler" + name "Scale" + value 0) + (object Attribute + tool "Data Modeler" + name "ColumnType" + value "Native") + (object Attribute + tool "Data Modeler" + name "ForBitData" + value FALSE) + (object Attribute + tool "Data Modeler" + name "DefaultValueType" + value "") + (object Attribute + tool "Data Modeler" + name "DefaultValue" + value "") + (object Attribute + tool "Data Modeler" + name "SourceId" + value "") + (object Attribute + tool "Data Modeler" + name "SourceType" + value "") + (object Attribute + tool "Data Modeler" + name "OID" + value FALSE))) + (object Attribute + tool "Data Modeler" + name "default__Association" + value (list Attribute_Set + (object Attribute + tool "Data Modeler" + name "dmItem" + value FALSE) + (object Attribute + tool "Data Modeler" + name "DMName" + value "") + (object Attribute + tool "Data Modeler" + name "IsRelationship" + value FALSE) + (object Attribute + tool "Data Modeler" + name "SourceId" + value "") + (object Attribute + tool "Data Modeler" + name "SourceType" + value "") + (object Attribute + tool "Data Modeler" + name "RIMethod" + value "") + (object Attribute + tool "Data Modeler" + name "ParentUpdateRule" + value "") + (object Attribute + tool "Data Modeler" + name "ParentUpdateRuleName" + value "") + (object Attribute + tool "Data Modeler" + name "ParentDeleteRule" + value "") + (object Attribute + tool "Data Modeler" + name "ParentDeleteRuleName" + value "") + (object Attribute + tool "Data Modeler" + name "ChildInsertRestrict" + value FALSE) + (object Attribute + tool "Data Modeler" + name "ChildInsertRestrictName" + value "") + (object Attribute + tool "Data Modeler" + name "ChildMultiplicity" + value FALSE) + (object Attribute + tool "Data Modeler" + name "ChildMultiplicityName" + value ""))) + (object Attribute + tool "Data Modeler" + name "default__Role" + value (list Attribute_Set + (object Attribute + tool "Data Modeler" + name "dmItem" + value FALSE) + (object Attribute + tool "Data Modeler" + name "DMName" + value "") + (object Attribute + tool "Data Modeler" + name "ConstraintName" + value ""))) + (object Attribute + tool "Data Modeler" + name "default__Operation" + value (list Attribute_Set + (object Attribute + tool "Data Modeler" + name "dmItem" + value FALSE) + (object Attribute + tool "Data Modeler" + name "DMName" + value "") + (object Attribute + tool "Data Modeler" + name "IsConstraint" + value FALSE) + (object Attribute + tool "Data Modeler" + name "ConstraintType" + value "") + (object Attribute + tool "Data Modeler" + name "IsIndex" + value FALSE) + (object Attribute + tool "Data Modeler" + name "IsTrigger" + value FALSE) + (object Attribute + tool "Data Modeler" + name "IsStoredProcedure" + value FALSE) + (object Attribute + tool "Data Modeler" + name "IsCluster" + value FALSE) + (object Attribute + tool "Data Modeler" + name "TableSpace" + value "") + (object Attribute + tool "Data Modeler" + name "FillFactor" + value 0) + (object Attribute + tool "Data Modeler" + name "KeyList" + value "") + (object Attribute + tool "Data Modeler" + name "CheckPredicate" + value "") + (object Attribute + tool "Data Modeler" + name "IsUnique" + value FALSE) + (object Attribute + tool "Data Modeler" + name "DeferalMode" + value "") + (object Attribute + tool "Data Modeler" + name "InitialCheckTime" + value "") + (object Attribute + tool "Data Modeler" + name "TriggerType" + value "") + (object Attribute + tool "Data Modeler" + name "IsInsertEvent" + value FALSE) + (object Attribute + tool "Data Modeler" + name "IsUpdateEvent" + value FALSE) + (object Attribute + tool "Data Modeler" + name "IsDeleteEvent" + value FALSE) + (object Attribute + tool "Data Modeler" + name "RefOldTable" + value "") + (object Attribute + tool "Data Modeler" + name "RefNewTable" + value "") + (object Attribute + tool "Data Modeler" + name "RefOldRow" + value "") + (object Attribute + tool "Data Modeler" + name "RefNewRow" + value "") + (object Attribute + tool "Data Modeler" + name "IsRow" + value FALSE) + (object Attribute + tool "Data Modeler" + name "WhenClause" + value "") + (object Attribute + tool "Data Modeler" + name "Language" + value "SQL") + (object Attribute + tool "Data Modeler" + name "ProcType" + value "Procedure") + (object Attribute + tool "Data Modeler" + name "IsDeterministic" + value FALSE) + (object Attribute + tool "Data Modeler" + name "ParameterStyle" + value "") + (object Attribute + tool "Data Modeler" + name "ReturnedNull" + value FALSE) + (object Attribute + tool "Data Modeler" + name "ExternalName" + value "") + (object Attribute + tool "Data Modeler" + name "Length" + value "") + (object Attribute + tool "Data Modeler" + name "Scale" + value "") + (object Attribute + tool "Data Modeler" + name "ForBitData" + value FALSE) + (object Attribute + tool "Data Modeler" + name "DefaultValue" + value "") + (object Attribute + tool "Data Modeler" + name "DefaultValueType" + value ""))) + (object Attribute + tool "Data Modeler" + name "default__Parameter" + value (list Attribute_Set + (object Attribute + tool "Data Modeler" + name "dmItem" + value FALSE) + (object Attribute + tool "Data Modeler" + name "DMName" + value "") + (object Attribute + tool "Data Modeler" + name "IsInParameter" + value TRUE) + (object Attribute + tool "Data Modeler" + name "IsOutParameter" + value FALSE) + (object Attribute + tool "Data Modeler" + name "Ordinal" + value "") + (object Attribute + tool "Data Modeler" + name "Length" + value "") + (object Attribute + tool "Data Modeler" + name "Scale" + value "") + (object Attribute + tool "Data Modeler" + name "ForBitData" + value FALSE) + (object Attribute + tool "Data Modeler" + name "DefaultValueType" + value "") + (object Attribute + tool "Data Modeler" + name "DefaultValue" + value "") + (object Attribute + tool "Data Modeler" + name "OperationID" + value ""))) + (object Attribute + tool "Data Modeler" + name "HiddenTool" + value FALSE) + (object Attribute + tool "Data Modeler Communicator" + name "HiddenTool" + value FALSE) + (object Attribute + tool "Deploy" + name "HiddenTool" + value FALSE) + (object Attribute + tool "Rose Model Integrator" + name "HiddenTool" + value FALSE) + (object Attribute + tool "Rose Web Publisher" + name "HiddenTool" + value FALSE) + (object Attribute + tool "Web Modeler" + name "HiddenTool" + value FALSE)) + quid "3DFDF6CE0374")) diff --git a/webapps/docs/architecture/startup.xml b/webapps/docs/architecture/startup.xml new file mode 100644 index 000000000000..1cb5f086ec23 --- /dev/null +++ b/webapps/docs/architecture/startup.xml @@ -0,0 +1,73 @@ + + + +]> + + + &project; + + + Yoav Shapira + Startup + + + + + +
+ +

+This page describes how the Tomcat server starts up. There are several +different ways to start tomcat, including: +

    +
  • From the command line.
  • +
  • From a Java program as an embedded server.
  • +
  • Automatically as a Windows service.
  • +
+

+ + +

+A text description of the startup procedure is available +here. +

+
+ + +

+A UML sequence diagram of the startup procedure is available +here. +

+
+ + +

+The startup process can be customized in many ways, both +by modifying Tomcat code and by implementing your own +LifecycleListeners which are then registered in the server.xml +configuration file. +

+ +
+ +
+ + + +
diff --git a/webapps/docs/architecture/startup/serverStartup.pdf b/webapps/docs/architecture/startup/serverStartup.pdf new file mode 100644 index 000000000000..34aa59808b3a Binary files /dev/null and b/webapps/docs/architecture/startup/serverStartup.pdf differ diff --git a/webapps/docs/architecture/startup/serverStartup.txt b/webapps/docs/architecture/startup/serverStartup.txt new file mode 100644 index 000000000000..af8efdff50ee --- /dev/null +++ b/webapps/docs/architecture/startup/serverStartup.txt @@ -0,0 +1,138 @@ + Licensed to the Apache Software Foundation (ASF) under one or more + contributor license agreements. See the NOTICE file distributed with + this work for additional information regarding copyright ownership. + The ASF licenses this file to You under the Apache License, Version 2.0 + (the "License"); you may not use this file except in compliance with + the License. You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + + Unless required by applicable law or agreed to in writing, software + distributed under the License is distributed on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + See the License for the specific language governing permissions and + limitations under the License. + +Tomcat 5 Startup Sequence + +Sequence 1. Start from Command Line +Class: org.apache.catalina.startup.Bootstrap +What it does: + a) Set up classloaders + commonLoader (common)-> System Loader + sharedLoader (shared)-> commonLoader -> System Loader + catalinaLoader(server) -> commonLoader -> System Loader + b) Load startup class (reflection) + org.apache.catalina.startup.Catalina + setParentClassloader -> sharedLoader + Thread.contextClassloader -> catalinaLoader + c) Bootstrap.daemon.init() complete + +Sequence 2. Process command line argument (start, startd, stop, stopd) +Class: org.apache.catalina.startup.Bootstrap (assume command->start) +What it does: + a) Catalina.setAwait(true); + b) Catalina.load() + b1) initDirs() -> set properties like + catalina.home + catalina.base == catalina.home (most cases) + b2) initNaming + setProperty(javax.naming.Context.INITIAL_CONTEXT_FACTORY, + org.apache.naming.java.javaURLContextFactory ->default) + b3) createStartDigester() + Configures a digester for the main server.xml elements like + org.apache.catalina.core.StandardServer (can change of course :) + org.apache.catalina.deploy.NamingResources + Stores naming resources in the J2EE JNDI tree + org.apache.catalina.LifecycleListener + implements events for start/stop of major components + org.apache.catalina.core.StandardService + The single entry for a set of connectors, + so that a container can listen to multiple connectors + ie, single entry + org.apache.coyote.tomcat5.CoyoteConnector + Connectors to listen for incoming requests only + It also adds the following rulesets to the digester + NamingRuleSet + EngineRuleSet + HostRuleSet + ContextRuleSet + b4) Load the server.xml and parse it using the digester + Parsing the server.xml using the digester is an automatic + XML-object mapping tool, that will create the objects defined in server.xml + Startup of the actual container has not started yet. + b5) Assigns System.out and System.err to the SystemLogHandler class + b6) Calls initialize on all components, this makes each object register itself with the + JMX agent. + During the process call the Connectors also initialize the adapters. + The adapters are the components that do the request pre-processing. + Typical adapters are HTTP1.1 (default if no protocol is specified, + org.apache.coyote.http11.Http11Protocol) + AJP1.3 for mod_jk etc. + + c) Catalina.start() + c1) Starts the NamingContext and binds all JNDI references into it + c2) Starts the services under which are: + StandardService -> starts Engine (ContainerBase ->Logger,Loader,Realm,Cluster etc) + c3) StandardHost (started by the service) + Configures a ErrorReportValvem to do proper HTML output for different HTTP + errors codes + Starts the Valves in the pipeline (at least the ErrorReportValve) + Configures the StandardHostValve, + this valves ties the Webapp Class loader to the thread context + it also finds the session for the request + and invokes the context pipeline + Starts the HostConfig component + This component deploys all the webapps + (webapps & conf/Catalina/localhost/*.xml) + Webapps are installed using the deployer (StandardHostDeployer) + The deployer will create a Digester for your context, this digester + will then invoke ContextConfig.start() + The ContextConfig.start() will process the default web.xml (conf/web.xml) + and then process the applications web.xml (WEB-INF/web.xml) + + c4) During the lifetime of the container (StandardEngine) there is a background thread that + keeps checking if the context has changed. If a context changes (timestamp of war file, + context xml file, web.xml) then a reload is issued (stop/remove/deploy/start) + + d) Tomcat receives a request on an HTTP port + d1) The request is received by a separate thread which is waiting in the PoolTcpEndPoint + class. It is waiting for a request in a regular ServerSocket.accept() method. + When a request is received, this thread wakes up. + d2) The PoolTcpEndPoint assigns the a TcpConnection to handle the request. + It also supplies a JMX object name to the catalina container (not used I believe) + d3) The processor to handle the request in this case is Coyote Http11Processor, + and the process method is invoked. + This same processor is also continuing to check the input stream of the socket + until the keep alive point is reached or the connection is disconnected. + d4) The HTTP request is parsed using an internal buffer class (Coyote Http11 Internal Buffer) + The buffer class parses the request line, the headers, etc and store the result in a + Coyote request (not an HTTP request) This request contains all the HTTP info, such + as servername, port, scheme, etc. + d5) The processor contains a reference to an Adapter, in this case it is the + Coyote Tomcat 5 Adapter. Once the request has been parsed, the Http11 processor + invokes service() on the adapter. In the service method, the Request contains a + CoyoteRequest and CoyoteRespons (null for the first time) + The CoyoteRequest(Response) implements HttpRequest(Response) and HttpServletRequest(Response) + The adapter parses and associates everything with the request, cookies, the context through a + Mapper, etc + d6) When the parsing is finished, the CoyoteAdapter invokes its container (StandardEngine) + and invokes the invoke(request,response) method. + This initiates the HTTP request into the Catalina container starting at the engine level + d7) The StandardEngine.invoke() simply invokes the container pipeline.invoke() + d8) By default the engine only has one valve the StandardEngineValve, this valve simply + invokes the invoke() method on the Host pipeline (StandardHost.getPipeLine()) + d9) the StandardHost has two valves by default, the StandardHostValve and the ErrorReportValve + d10) The standard host valve associates the correct class loader with the current thread + It also retrieves the Manager and the session associated with the request (if there is one) + If there is a session access() is called to keep the session alive + d11) After that the StandardHostValve invokes the pipeline on the context associated + with the request. + d12) The first valve that gets invoked by the Context pipeline is the FormAuthenticator + valve. Then the StandardContextValve gets invoke. + The StandardContextValve invokes any context listeners associated with the context. + Next it invokes the pipeline on the Wrapper component (StandardWrapperValve) + d13) During the invocation of the StandardWrapperValve, the JSP wrapper (Jasper) gets invoked + This results in the actual compilation of the JSP. + And then invokes the actual servlet. + e) Invocation of the servlet class diff --git a/webapps/docs/balancer-howto.xml b/webapps/docs/balancer-howto.xml new file mode 100644 index 000000000000..b978b9ad65c9 --- /dev/null +++ b/webapps/docs/balancer-howto.xml @@ -0,0 +1,55 @@ + + + +]> + + + &project; + + + Yoav Shapira + Remy Maucherat + Andy Oliver + Load Balancer HOW-TO + + + + +
+ +
+ +
+ +Please refer to the JK 1.2.x documentation. + +
+ +
+ +Please refer to the mod_proxy documentation for Apache HTTP Server 2.2. This supports either +HTTP or AJP load balancing. This new version of mod_proxy is also usable with +Apache HTTP Server 2.0, but mod_proxy will have to be compiled separately using the code +from Apache HTTP Server 2.2. + +
+ + + +
diff --git a/webapps/docs/building.xml b/webapps/docs/building.xml new file mode 100644 index 000000000000..0dbddec18165 --- /dev/null +++ b/webapps/docs/building.xml @@ -0,0 +1,245 @@ + + + +]> + + + &project; + + + Remy Maucherat, Tim Whittington + Building Tomcat + + + + +
+ +
+ +
+ +

+Building Apache Tomcat from source is very easy, and is the first step to contributing to +Tomcat. The following is a step by step guide. +

+ +
+ +
+ +

+Tomcat requires a JDK (version 1.6 or later) to be installed. +
The Sun JDK can be downloaded +here. +

+ +

+IMPORTANT: Set an environment variable JAVA_HOME to the pathname of the +directory into which you installed the JDK release. +

+ +
+ +
+ +

+Download a binary distribution of Ant 1.8.1 or later from +here. +

+ +

+Unpack the binary distribution into a convenient location so that the +Ant release resides in its own directory (conventionally named +apache-ant-1.8.x). For the remainder of this guide, +the symbolic name ${ant.home} is used to refer to the full pathname of + the Ant installation directory directory. +

+ +

+IMPORTANT: Create an ANT_HOME environment variable to point the directory ${ant.home}, +and modify the PATH environment variable to include directory +${ant.home}/bin in its list. This makes the ant command line script +available, which will be used to actually perform the build. +

+ +
+ +
+ +

+ Tomcat SVN repository URL: + http://svn.apache.org/repos/asf/tomcat/trunk/ +

+

+ Tomcat source packages: + http://tomcat.apache.org/download-70.cgi. +

+ +

+ Checkout the source using SVN, or download and unpack a source package. + For the remainder of this guide, the symbolic name ${tomcat.source} is used to refer to the + location where the source has been placed. +

+ +
+ +
+ +

+Use the following commands to build Tomcat: +
+
+ cd ${tomcat.source}
+ ant
+
+

+ +

+NOTE: Users accessing the Internet through a proxy must use a properties + file to indicate to Ant the proxy configuration. Read below for details. +

+ +

+WARNING: Running this command will download binary binaries to the + /usr/share/java directory by default. + Make sure this is appropriate to do so on your computer. On Windows, + this usually corresponds to the C:\usr\share\java directory, + unless Cygwin is used. Read below to customize the directory used + to download the binaries. +

+ +

+ The build can be controlled by creating a ${tomcat.source}/build.properties + file and adding the following content to it: +
+
+ # ----- Proxy setup -----
+ # Uncomment if using a proxy server.
+ #proxy.host=proxy.domain
+ #proxy.port=8080
+ #proxy.use=on
+
+ # ----- Default Base Path for Dependent Packages -----
+ # Replace this path with the directory path where
+ # dependencies binaries should be downloaded.
+ base.path=/usr/share/java
+
+

+ +

+Once the build has completed successfully, a usable Tomcat installation will have been +produced in the ${tomcat.source}/output/build directory, and can be started +and stopped with the usual scripts. +

+
+ +
+ +

+IMPORTANT: This is not a supported means of building Tomcat; this information is +provided without warranty :-). +The only supported means of building Tomcat is with the Ant build described above. +However, some developers like to work on Java code with a Java IDE, +and the following steps have been used by some developers. +

+ +

+NOTE: This will not let you build everything under Eclipse; +the build process requires use of Ant for the many stages that aren't +simple Java compilations. +However, it will allow you to view and edit the Java code, +get warnings, reformat code, perform refactorings, run Tomcat +under the IDE, and so on. +

+

+Sample Eclipse project files and launch targets are provided in the +res/ide-support/eclipse directory of the source tree. +The instructions below will automatically copy these into the required locations. +

+

+An Ant target is provided as a convenience to download all binary dependencies, and to create +the Eclipse project and classpath files in the root of the source tree. +
+
+ cd ${tomcat.source}
+ ant ide-eclipse
+
+

+ +

+Start Eclipse and create a new Workspace. +

+ +

+Open the Preferences dialog and then select Java->Build Path->Classpath +Variables to add two new Classpath Variables: +

+ +

+ + + +
TOMCAT_LIBS_BASEThe same location as the base.path + setting in build.properties, where the binary dependencies have been downloaded
ANT_HOMEthe base path of Ant 1.8.1 or later
+

+ +

+Use File->Import and choose Existing Projects into Workspace. +From there choose the root directory of the Tomcat source tree (${tomcat.source}) +and import the Tomcat project located there. +

+ +

+start-tomcat and stop-tomcat launch configurations are provided in +res/ide-support/eclipse and will be available in the Run->Run Configurations +dialog. Use these to start and stop Tomcat from Eclipse. +
If you want to configure these yourself (or are using a different IDE) +then use org.apache.catalina.startup.Bootstrap as the main class, +start/stop etc. as program arguments, and specify -Dcatalina.home=... +(with the name of your build directory) as VM arguments. +

+ +

+Tweaking a few formatting preferences will make it much easier to keep consistent with Tomcat +coding conventions (and have your contributions accepted): +

+

+ + + + + + + +
Java -> Code Style -> Formatter -> Edit...Tab policy: Spaces only
Tab and Indentation size: 4
General -> Editors -> Text EditorsDisplayed tab width: 2
Insert spaces for tabs
Show whitespace characters (optional)
XML -> XML Files -> EditorIndent using spaces
Indentation size: 2
Ant -> Editor -> FormatterTab size: 2
Use tab character instead of spaces: unchecked
+

+ +
+ +
+

+The same general approach should work for most IDEs; it has been reported +to work in IntelliJ IDEA, for example. +

+ +
+ + +
diff --git a/webapps/docs/cgi-howto.xml b/webapps/docs/cgi-howto.xml new file mode 100644 index 000000000000..c84e0b55c106 --- /dev/null +++ b/webapps/docs/cgi-howto.xml @@ -0,0 +1,100 @@ + + + +]> + + + &project; + + + Glenn L. Nielsen + CGI How To + + + + +
+ +
+ +
+ +

The CGI (Common Gateway Interface) defines a way for a web server to +interact with external content-generating programs, which are often +referred to as CGI programs or CGI scripts. +

+ +

Within Tomcat, CGI support can be added when you are using Tomcat as your +HTTP server and require CGI support. Typically this is done +during development when you don't want to run a web server like +Apache httpd. +Tomcat's CGI support is largely compatible with Apache httpd's, +but there are some limitations (e.g., only one cgi-bin directory). +

+ +

CGI support is implemented using the servlet class +org.apache.catalina.servlets.CGIServlet. Traditionally, +this servlet is mapped to the URL pattern "/cgi-bin/*".

+ +

By default CGI support is disabled in Tomcat.

+
+ +
+ +

CAUTION - CGI scripts are used to execute programs +external to the Tomcat JVM. If you are using the Java SecurityManager this +will bypass your security policy configuration in catalina.policy.

+ +

Remove the XML comments from around the CGI servlet and servlet-mapping +configuration in $CATALINA_BASE/conf/web.xml.

+ +

Only Contexts which are marked as privileged may use the CGI servlet (see the +privileged property of the Context element).

+ +
+ +
+ +

There are several servlet init parameters which can be used to +configure the behaviour of the CGI servlet. +

    +
  • cgiPathPrefix - The CGI search path will start at +the web application root directory + File.separator + this prefix. +The default cgiPathPrefix is WEB-INF/cgi
  • +
  • debug - Debugging detail level for messages logged +by this servlet. Default 0.
  • +
  • executable - The of the executable to be used to +run the script. Default is perl.
  • +
  • parameterEncoding - Name of the parameter encoding +to be used with the GCI servlet. Default is +System.getProperty("file.encoding","UTF-8").
  • +
  • passShellEnvironment - Should the shell environment +variables (if any) be passed to the CGI script? Default is +false.
  • +
  • stderrTimeout - The time (in milliseconds) to wait for +the reading of stderr to complete before terminating the CGI process. Default +is 2000.
  • +
+

+ +
+ + + +
diff --git a/webapps/docs/changelog.xml b/webapps/docs/changelog.xml new file mode 100644 index 000000000000..ac6ab063e9d2 --- /dev/null +++ b/webapps/docs/changelog.xml @@ -0,0 +1,921 @@ + + + +]> + + + + &project; + + + Remy Maucherat + Filip Hanik + Rainer Jung + Konstantin Kolinko + Peter Rossbach + Keiichi Fujino + Tim Whittington + Changelog + + + + +
+ + + + 48644: Review all instances of catching Throwable and + re-throw where appropriate. (markt) + + + Allow glob patterns in the jarsToSkip configuration and add + some debug logging to the jar scanner. (rjung) + + + 48738: Workaround a couple of long standing JDK bugs to + enable GZIP compressed output streams to be flushed. Based on a patch + provided by Jiong Wang. (markt) + + + 49195: Don't report an error when shutting down a Windows + service for a Tomcat instance that has a disabled shutdown port. (markt) + + + 49209: Prevent possible AccessControlException during + undeployment when running with a security manager. Patch provided by + Sylvain Laurent. + + + 49657: Handle CGI executables with spaces in the path. + (markt) + + + 49667: Ensure that using the JDBC driver memory leak + prevention code does not cause a one of the memory leaks it is meant to + avoid. (markt) + + + 49670: Restore SSO functionality that was broken by Lifecycle + refactoring. (markt) + + + 49698: Allow a listener to complete an asynchronous request + if it times out. (markt) + + + 49714: The annotation process of Jar doesn't influence + distributable element of web.xml. (kfujino) + + + 49721: Alls JAR in a web application should be searched for + resources, not just those with a web-fragment.xml that is going to be + processed. (markt) + + + 49728: Improve PID file handling when another process is + managing the PID file and Tomcat does not have write access. (markt) + + + 49730: Fix a race condition in StandardThreadExector that can + cause requests to experience large delays. Patch provided by Sylvain + Laurent. (markt) + + + 49749: Single sign on cookies should have httpOnly flag set + using same rules as session cookies. (markt) + + + 49750: Align WebappClassLoader.validate() + implementation with Javadoc and ensure that javax.servlet.* + classes can not be loaded by a WebappClassLoader instance. + Patch provided by pid. (markt) + + + 49757: Correct some generics warnings. Based on a patch + provided by Gábor. (markt) + + + Provide 100 Continue responses at appropriate points during FORM + authentication if client indicates that they are expected. (markt) + + + 49779: Improve handling of POST requests and FORM + authentication, particularly when the user agent responds to the 302 + response by repeating the POST request including a request body. Any + request body provided at this point is now swallowed. (markt) + + + CSRF prevention filter did not correctly handle URLs that used anchors. + (markt) + + + Fix memory leak on web application stopped caused by failed to + de-register the web application's Servlets with the MBean server. + (markt) + + + More tweaks to the Lifecycle refactoring to ensure that when a component + is being destroyed, the destroy method is only called once on each + child component. (markt) + + + 48967: Replace strings "catalina.base" and "catalina.home" + by globally defined constants. Patch provided by Marc Guillemot. (rjung) + + + Keep the MBean names for web applications consistent between Tomcat 6 + and Tomcat 7. (markt) + + + 49856: Add an executorName attribute to Connectors so it is + possible to trace ThreadPool to Connector to Executor via the JMX + interface. (markt) + + + 49865: Tomcat failed to start if catalina.properties was not + present. (markt) + + + 49876: Fix the generics warnings in the copied Apache Jakarta + BCEL code. Based on a patch by Gábor. (markt) + + + 49883: Ensure that the CombinedRealm and LockOutRealm return + a name for use in log messages rather than throwing an + UnsupportedOperationException. (markt) + + + 49884: Fix occassional NullPointerException on async + complete(). This resulted in a major refactoring of the async + implementation to address a number of threading issues. (markt) + + + Update the version numbers in ServerInfo defaults to Tomcat 7.0.x. + (markt) + + + 49892: Correct JNDI name for method resource injections. + Based on a patch by Gurkan Erdogdu. (markt) + + + Ensure that Context elements defined in server.xml use any configClass + setting specified in the parent Host element. (markt) + + + GSOC 2010. Enable the creation of Services, Engines, Connectors, Hosts + and Contexts via JMX from a minimal server.xml that contains only a + Server element. Based on a patch by Chamith Buddhika. (markt) + + + 49909: Fix a regression introduced with the fix for + 47950 that prevented JSTL classes being loaded. (markt) + + + 49915: Make error more obvious, particularly when accessed + via JConsole, if StandardServer.storeConfig() is called when there is + no StoreConfig implementation present. (markt) + + + 50018: Fix some minor Javadoc errors in Jasper source. + Based on a patch by sebb. (timw) + + + 50021: Correct a regression in the fix for 46844 + that may have caused additional problems during a failure at start up. + (markt) + + + + + + + Wait for the connectors to exit before closing them down. (mturk) + + + Follow up to 48545. Make JSSE connectors more tolerant of a + incorrect trust store password. (markt) + + + Fix some edge cases in the NIO connector when handling requests that are + not received all at the same time and the socket needs to be returned to + the poller. (markt) + + + Further work to reduce the code duplication in the HTTP connectors. + (markt) + + + Make sure acceptor threads are stopped when the connector is stopped. + (markt) + + + Make sure async timeout thread is stopped when the connector is stopped. + (markt) + + + 49625: Ensure Vary header is set if response may be + compressed rather than only setting it if it is compressed. (markt) + + + 49802: Re-factor connector pause, stop and destroy methods so + that calling any of those methods has the expected results. (markt) + + + Various refactorings to reduce code duplication and unnecessary code in + the connectors. (markt) + + + 49860: Add support for trailing headers in chunked HTTP + requests. (markt) + + + + + + + 49665: Provide better information including JSP file name and + location when a missing file is detected during TLD handling. Patch + provided by Ted Leung. (markt) + + + 49726: Specifying a default content type via a JSP property + group should not prevent a page from setting some other content type. + (markt) + + + 49799: The new omit attribute for + jsp:attribute elements now supports the use of expressions + and expression language. (markt) + + + 49916: Switch to using an initialisation parameter to pass + JSP file information from Catalina to Jasper. This simplifies the + Catalina code as well as making it easier for Geronimo and others to + integrate Jasper. Patch provided by David Jencks. (markt) + + + 49985: Fix thread safety issue in EL parser. (markt) + + + + + + + Remove domainReplication attribute from ClusterManager. + If you send session to only same domain, use DomainFilterInterceptor. + (kfujino) + + + Add Null check when CHANGE_SESSION_ID message received. (kfujino) + + + Add support for LAST_ACCESS_AT_START system property to DeltaSession. + (kfujino) + + + Avoid a NPE in the DeltaManager when a parallel request invalidates the + session before the current request has a chance to send the replication + message. (markt) + + + 49905: Prevent memory leak when using asynchronous session + replication. (markt) + + + 49924: When non-primary node changes into a primary node, + make sure isPrimarySession is changed to true. (kfujino) + + + + + + + Correct the class name of the default JAR scanner in the documentation + web application. (rjung) + + + 49585: Update JSVC documentation to reflect new packaging + of Commons Daemon. (markt) + + + Update the Servlet, JSP and EL Javadoc links to link to the + specifications and the relevant part of the Java EE 6 Javadoc. (markt) + + + Update a few places in the docs where the Manager documentation referred + to the old role name of manager rather than than the new manager-script. + (markt) + + + + + + + 49861: Don't log RMI ports formatted with commas for the + JMX remote listener. (markt) + + + + + + + Correct the user names created by the Windows installer for the Manager + and Host Manager applications. (mturk) + + + Correct the Eclipse compiler dependency in the Jasper POM. (markt) + + + Extend Checkstyle validation checks to check import order. (markt) + + + 49758: Fix generics warnings exposed by a fix in Eclipse 3.6. + Patch provided by sebb. (markt) + + + Update commons pool to 1.5.5. (markt) + + + 49955: Improvement and correction of Building Tomcat guide. + Based on a patch from Wesley Acheson. (timw) + + + +
+
+ + + + Fix regression that prevented running with a security manager enabled. + (markt) + + + + + + + Correct Javadoc errors. (markt) + + + Provide Javadoc for Servlet 3.0 API, JSP 2.2 API and EL 2.2 API. + (markt) + + + Remove second copy of RUNNING.txt from the full-docs distribution. Some + unpacking utilities can't handle multiple copies of a file with the same + name in a directory. (markt) + + + + + + + Extend Checkstyle validation checks to check for tabs in nearly all text + files. (markt) + + + Update Commons Daemon from 1.0.2 to 1.0.3.(markt) + + + Update Eclipse JDT Core Batch Compiler (ecj.jar) from 3.5.1 to 3.6. + (markt) + + + +
+
+ + + + GSOC 2010. Continue work to align MBean descriptors with reality. Patch + provided by Chamith Buddhika. (markt) + + + When running under a security manager, enforce package access and + package definition restrictions defined in the catalina.properties file. + (markt) + + + When using a Loader configured with + searchExternalFirst="true" failure to find the + class in an external repository should not prevent searching of the + local repositories. (markt) + + + Add entryPoint support to the CSRF prevention filter. (markt) + + + 48297: Correctly initialise handler chain for web services + resources. (markt) + + + 48960: Add a new option to the SSI Servlet and SSI Filter to + allow the disabling of the exec command. This is now + disabled by default. Based on a patch by Yair Lenga. (markt) + + + 48998, 49617: Add the ExpiresFilter, a port of the + httpd mod_expires module. Patch provided by Cyrille Le Clerc. (markt) + + + 49030: When initializing/starting/stopping connectors and + one of them fails, do not ignore the others. (markt/kkolinko) + + + 49128: Don't swallow exceptions unnecessarily in + WebappClassLoader.start(). (markt) + + + 49182: Align comments in setclasspath.[sh|bat] with + behaviour. Based on a patch provided by sebb. (markt) + + + 49230: Enhance JRE leak prevention listener with protection + for the keep-alive thread started by + sun.net.www.http.HttpClient. Based on a patch provided by + Rob Kooper. (markt) + + + 49414: When reporting threads that may have triggered a + memory leak on web application stop, attempt to differentiate between + request processing threads and threads started by the application. + (markt) + + + 49428: Add a work-around for the known namespace issues for + some Microsoft WebDAV clients. Patch provided by Panagiotis Astithas. + (markt) + + + Add support for *.jar pattern in VirtualWebappLoader. + (kkolinko) + + + Use a LockOutRealm in the default configuration to prevent attempts to + guess user passwords by brute-force. (markt) + + + 49478: Add support for user specified character sets to the + AddDefaultCharsetFilter. Based on a patch by Felix + Schumacher. (markt) + + + 49503: Make sure connectors bind to their associated ports + sufficiently early to allow jsvc and the + org.apache.catalina.startup.EXIT_ON_INIT_FAILURE system property to + operate correctly. (markt) + + + 49525: Ensure cookies for the ROOT context have a path of / + rather than an empty string. (markt) + + + 49528, 49567: Ensure that + AsyncContext.isAsyncStarted() returns the correct value + after AsyncContext.start() and that if + AsyncContext.complete() is called on a separate thread that + it is handled correctly. (markt) + + + 49530: Contexts and Servlets not stopped when Tomcat is shut + down. (markt) + + + 49536: If no ROOT context is deployed, ensure a 404 rather + than a 200 is returned for requests that don't map to any other context. + (markt) + + + Additional debug logging in StandardContext to provide information on + Manager selection. (markt) + + + 49550: Supress deprecation warning where deprecated code is + required to be used. No functional change. Patch provided by Sebb. + (markt) + + + 49551: Allow default context.xml location to be specified + using an absolute path. (markt) + + + Improve logging of unhandled exceptions in servlets by including the + path of the context where the error occurred. (markt) + + + Include session ID in error message logged when trying to set an + attribute on an invalid session. (markt) + + + Improve the CSRF protection filter by using SecureRandom rather than + Random to generate nonces. Also make the implementation class used user + configurable. (markt) + + + Avoid NullPointerException, when copyXML=true and META-INF/context.xml + does not exist. (kfujino) + + + 49598: When session is changed and the session cookie is + replaced, ensure that the new Set-Cookie header overwrites the old + Set-Cookie header. (markt) + + + Create a thread to trigger asynchronous timeouts when using the BIO + connector, change the default timeout to 10s (was infinite) and make the + default timeout configurable using the asyncTimeout + attribute on the connector. (pero/markt) + + + 49600: Make exceptions returned by the + ProxyDirContext consistent for resources that weren't found + by checking the DirContext or the cache. Test case based on + a patch provided by Marc Guillemot. (markt) + + + 49613: Improve performance when using SSL for applications + that make multiple class to Request.getAttributeNames(). + Patch provided by Sampo Savolainen. (markt) + + + Handle the edge cases where resources packaged in JARs have names that + start with a single quote character or a double quote character. (markt) + + + Correct copy and paste typo in web.xml parsing rules that mixed up + local-ejb-ref and resource-env-ref. (markt) + + + Refactor session managers to remove unused code and to reduce code + duplication. Also, all session managers used for session replication now + extend org.apache.catalina.ha.session.ClusterManagerBase. + (markt) + + + + + + + Remove references to Jikes since it does not support Java 6. (markt) + + + Correct over zealous type checking for EL in attributes that broke the + use of JSF converters. (markt) + + + Correct algorithm used to identify correct method to use when a + MethodExpressions is used in EL. (markt) + + + 49217: Ensure that identifiers used in EL meet the + requirements of the Java Language Specification. (markt) + + + Improve logging of JSP exceptions by including JSP snippet (if enabled) + rather than just the root cause in the host log. (markt) + + + 49555: Correctly handled Tag Libraries where functions are + defined in static inner classes. (markt) + + + + + + + 49127: Don't swallow exceptions unnecessarily in + SimpleTcpReplicationManager.startInternal(). (markt) + + + 49407: Change the BackupManager so it is consistent with + DeltaManager and reports both primary and backup sessions when active + sessions are requested. (markt) + + + 49445: When session ID is changed after authentication, + ensure the DeltaManager replicates the change in ID to the other nodes + in the cluster. (kfujino) + + + + + + + 49112: Update the ROOT web application's index page. Patch + provided by pid. (markt) + + + 49213: Add the permissions necessary to enable the Manager + application to operate currently when running with a security manager. + (markt) + + + 49436: Correct documented default for readonly attribute of + the UserDatabase component. (markt) + + + 49475: Use new role name for manager application access on + the ROOT web application's index page. (markt) + + + 49476: CSRF protection was preventing access to the session + expiration features. Also switch the manager application to the generic + CSRF protection filter. (markt) + + + Better handle failure to create directories required for new hosts in + the Host Manager application. (markt) + + + Switch the Host Manager application to the generic CSRF protection for + the HTML interface and prevent started hosts from being started and + stopped hosts from being stopped. (markt) + + + 49518: Fix typo in extras documentation. (markt) + + + 49522: Fix regression due to change of name for MBeans for + naming resources that broke the complete server status page in the + manager application. Note these MBeans now have a new name. (markt) + + + 49570: When using the example compression filter, set the + Vary header on compressed responses. (markt) + + + Add redirects for the root of the manager and host-manager web + applications that redirect users to the html interface rather than + returning a 404. (markt) + + + Provide the HTML Manager application with the ability to differentiate + between primary, backup and proxy sessions. Note that proxy sessions are + only shown if enabled in web.xml. (markt) + + + + + + + 49130: Better describe the core package in the Windows + installer, making it clear that the service will be installed. Patch + provided by sebb. (markt) + + + Re-factor unit tests to enable them to be run once with each of the HTTP + connector implementations (BIO, NIO and APR/native). (markt) + + + 49268: Add the necessary plumbing to include CheckStyle in + the build process. Start with no checks. Additional checks will be + added as they are agreed. (markt) + + + Updated to Ant 1.8.1. The build now requires a minimum of Ant 1.8.x. + (markt) + + + Update the re-packaged version of commons-fileupload from 1.2.1 to + 1.2.2. The layout of re-packaged version was also restored to the + original commons-fileupload layout to make merging of future updates + easier. (markt) + + + Update the re-packaged version of Jakarta BCEL from trunk revision + 880760 to trunk revision 978831. (markt) + + + +
+
+ + + + Update Servlet support to the Servlet 3.0 specification. (all) + + + Improve and document VirtualWebappLoader. (rjung) + + + 43642: Add prestartminSpareThreads attribute for Executor. + (jfclere) + + + Switch from AnnotationProcessor to InstanceManager. Patch provided by + David Jecks with modifications by Remy. (remm/fhanik) + + + 620845 and 669119. Make shutdown address + configurable. (jfclere) + + + 651977 Add some missing control checks to + ThreadWithAttributes. (markt) + + + 677640 Add a startup class that does not require any + configuration files. (costin) + + + 700532 Log if temporary file operations within the CGI + servlet fail. Make sure header Reader is closed on failure. (markt) + + + 708541 Delete references to DefaultContext which was removed + in 6.0.x. (markt) + + + 709018 Initial implementation of an asynchronous file handler + for JULI. (fhanik) + + + Give session thisAccessedTime and lastAccessedTime clear semantics. + (rjung) + + + Expose thisAccessedTime via Session interface. (rjung) + + + Provide a log format for JULI that provides the same information as the + default but on a single line. (markt) + + + 723889 Provide the ability to configure the Executor job + queue size and a timeout for adding jobs to the queue. (fhanik) + + + Add support for aliases to StandardContext. This allows content from + other directories and/or WAR files to be mapped to paths within the + context. (markt) + + + Provide clearer definition of Lifecycle interface, particularly start + and stop, and align components that implement Lifecycle with this + definition. (markt) + + + 48662: Provide a new option to control the copying of context + XML descriptors from web applications to the host's xmlBase. Copying of + XMl descriptors is now disabled by default. (markt) + + + Move comet classes from the org.apache.catalina package to the + org.apache.catalina.comet package to allow comet to work under a + security manager. (markt) + + + + + + + Port SSLInsecureRenegotiation from mod_ssl. This requires + to use tomcat-native 1.2.21 that have option to detect this + support from OpenSSL library. (mturk) + + + Allow bigger AJP packets also for request bodies and responses + using the packetSize attribute of the Connector. (rjung) + + 703017 Make Java socket options consistent between NIO + and JIO connector. Expose all the socket options available on + java.net.Socket (fhanik) + + + 46051: The writer returned by getWriter() now + conforms to the PrintWriter specification and uses platform + dependent line endings rather than always using \r\n. + (markt) + + + Use tc-native 1.2.x which is based on APR 1.3.3+ (mturk) + + + 724239 NIO connector now always uses an Executor. (fhanik) + + + 724393 Implement keepAliveCount for NIO connector in a thread + safe manner. (fhanik) + + + 724849 Implement keep alive timeout for NIO connector. + (fhanik) + + + + + + + Update JSP support to the JSP 2.2 specification. (markt) + + + Update EL support to the EL 2.2 specification. (markt) + + + 787978 Use "1.6" as the default value for compilerSourceVM + and compilerTargetVM options of Jasper. (kkolinko) + + + 48358: Add support for limiting the number of JSPs that are + loaded at any one time. Based on a patch by Isabel Drost. (markt) + + + 48689: Access TLD files through a new JarResource interface + to make extending Jasper simpler, particularly in OSGi environments. + Patch provided by Jarek Gawor. (markt) + + + + + + + Add support for UDP and secure communication to tribes. (fhanik) + + + Add versioning to the tribes communication protocol to support future + developments. (fhanik) + + + Add a demo on how to use the payload. (fhanik) + + + Started to add JMX support to the cluster implementation. (markt) + + + 609778 Minor fixes to the throughput interceptor and the + NIO receiver. (fhanik) + + + 630234 Additional checks for the NIO receiver. (fhanik) + + + 671650 Improve error message when multicast is not enabled. + (fhanik) + + + + + + + 631321 Update changelog to support the <rev> element + in the documentation. (fhanik) + + + A number of additional roles were added to the Manager and Host Manager + applications to separate out permissions for the HTML interface, the + text interface and the JMX proxy. (markt) + + + CSRF protection was added to the Manager and Host Manager applications. + (markt) + + + List array elements in the JMX proxy output of the Manager application. + (rjung) + + + + + + + A new JmxRemoteLifecycleListener that can be used to fix the ports used + for remote JMX connections, eg when using JConsole. (markt) + + + + + + + Numerous code clean-up changes including the use of generics and + removing unused imports, fields, parameters and methods. (markt) + + + All deprecated internal code has been removed. Warning: If you + have custom components for a previous Tomcat version that extend + internal Tomcat classes and override deprecated methods it is highly + likely that they will no longer work. (markt) + + + Parameterize version number throughout build scripts and source. (rjung) + + + +
+ +
diff --git a/webapps/docs/class-loader-howto.xml b/webapps/docs/class-loader-howto.xml new file mode 100644 index 000000000000..c7968ef2ec8e --- /dev/null +++ b/webapps/docs/class-loader-howto.xml @@ -0,0 +1,204 @@ + + + +]> + + + &project; + + + Craig R. McClanahan + Yoav Shapira + Class Loader HOW-TO + + + + +
+ +
+ +
+ +

Like many server applications, Tomcat installs a variety of class loaders +(that is, classes that implement java.lang.ClassLoader) to allow +different portions of the container, and the web applications running on the +container, to have access to different repositories of available classes and +resources. This mechanism is used to provide the functionality defined in the +Servlet Specification, version 2.4 -- in particular, Sections 9.4 and 9.6.

+ +

In a J2SE 2 (that is, J2SE 1.2 or later) environment, class loaders are +arranged in a parent-child tree. Normally, when a class loader is asked to +load a particular class or resource, it delegates the request to a parent +class loader first, and then looks in its own repositories only if the parent +class loader(s) cannot find the requested class or resource. The model for +web application class loaders differs slightly from this, as discussed below, +but the main principles are the same.

+ +

When Tomcat is started, it creates a set of class loaders that are +organized into the following parent-child relationships, where the parent +class loader is above the child class loader:

+ + + Bootstrap + | + System + | + Common + / \ + Webapp1 Webapp2 ... + + +

The characteristics of each of these class loaders, including the source +of classes and resources that they make visible, are discussed in detail in +the following section.

+ +
+ +
+ +

As indicated in the diagram above, Tomcat creates the following class +loaders as it is initialized:

+
    +
  • Bootstrap - This class loader contains the basic runtime + classes provided by the Java Virtual Machine, plus any classes from JAR + files present in the System Extensions directory + ($JAVA_HOME/jre/lib/ext). NOTE - Some JVMs may + implement this as more than one class loader, or it may not be visible + (as a class loader) at all.
  • +
  • System - This class loader is normally initialized from + the contents of the CLASSPATH environment variable. All such + classes are visible to both Tomcat internal classes, and to web + applications. However, the standard Tomcat startup scripts + ($CATALINA_HOME/bin/catalina.sh or + %CATALINA_HOME%\bin\catalina.bat) totally ignore the contents + of the CLASSPATH environment variable itself, and instead + build the System class loader from the following repositories: +
      +
    • $CATALINA_HOME/bin/bootstrap.jar - Contains the main() method + that is used to initialize the Tomcat server, and the class loader + implementation classes it depends on.
    • +
    • $CATALINA_HOME/bin/tomcat-juli.jar - Package renamed Commons + logging API, and java.util.logging LogManager.
    • +
  • +
  • Common - This class loader contains additional classes + that are made visible to both Tomcat internal classes and to all web + applications. Normally, application classes should NOT + be placed here. All unpacked classes and resources in + $CATALINA_HOME/lib, as well as classes and + resources in JAR files are made visible through this + class loader. By default, that includes the following: +
      +
    • annotations-api.jar - JEE annotations classes.
    • +
    • catalina.jar - Implementation of the Catalina servlet + container portion of Tomcat.
    • +
    • catalina-ant.jar - Tomcat Catalina Ant tasks.
    • +
    • catalina-ha.jar - High availability package.
    • +
    • catalina-tribes.jar - Group communication package.
    • +
    • el-api.jar - EL 2.1 API.
    • +
    • jasper.jar - Jasper 2 Compiler and Runtime.
    • +
    • jasper-el.jar - Jasper 2 EL implementation.
    • +
    • ecj-*.jar - Eclipse JDT Java compiler.
    • +
    • jsp-api.jar - JSP 2.1 API.
    • +
    • servlet-api.jar - Servlet 3.0 API.
    • +
    • tomcat-coyote.jar - Tomcat connectors and utility classes.
    • +
    • tomcat-dbcp.jar - package renamed database connection + pool based on Commons DBCP.
    • +
    • tomcat-i18n-**.jar - Optional JARs containing resource bundles + for other languages. As default bundles are also included in each + individual JAR, they can be safely removed if no internationalization + of messages is needed.
    • +
  • +
  • WebappX - A class loader is created for each web + application that is deployed in a single Tomcat instance. All unpacked + classes and resources in the /WEB-INF/classes directory of + your web application archive, plus classes and resources in JAR files + under the /WEB-INF/lib directory of your web application + archive, are made visible to the containing web application, but to + no others.
  • +
+ +

As mentioned above, the web application class loader diverges from the +default Java 2 delegation model (in accordance with the recommendations in the +Servlet Specification, version 2.3, section 9.7.2 Web Application Classloader). +When a request to load a +class from the web application's WebappX class loader is processed, +this class loader will look in the local repositories first, +instead of delegating before looking. There are exceptions. Classes which are +part of the JRE base classes cannot be overriden. For some classes (such as +the XML parser components in J2SE 1.4+), the J2SE 1.4 endorsed feature can be +used. +Last, any JAR containing servlet API classes will be ignored by the +classloader. +All other class loaders in Tomcat follow the usual delegation pattern.

+ +

Therefore, from the perspective of a web application, class or resource +loading looks in the following repositories, in this order:

+
    +
  • Bootstrap classes of your JVM
  • +
  • System class loader classes (described above)
  • +
  • /WEB-INF/classes of your web application
  • +
  • /WEB-INF/lib/*.jar of your web application
  • +
  • $CATALINA_HOME/lib
  • +
  • $CATALINA_HOME/lib/*.jar
  • +
+ +
+ + +
+ +

Among many other changes, the JSE 5 release packages the JAXP APIs, and +a version of Xerces, inside the JRE. This has impacts on applications that +wish to use their own XML parser.

+ +

In previous versions of Tomcat, you could simply replace the XML parser +in the $CATALINA_HOME/common/lib directory to change the parser +used by all web applications. However, this technique will not be effective +when you are running on JSE 5, because the usual class loader delegation +process will always choose the implementation inside the JDK in preference +to this one.

+ +

JDK 1.5 supports a mechanism called the "Endorsed Standards Override +Mechanism" to allow replacement of APIs created outside of the JCP (i.e. +DOM and SAX from W3C). It can also be used to update the XML parser +implementation. For more information, see: + +http://download.oracle.com/javase/1.5.0/docs/guide/standards/index.html.

+ +

Tomcat utilizes this mechanism by including the system property setting +-Djava.endorsed.dirs=$JAVA_ENDORSED_DIRS in the +command line that starts the container.

+ +
+ + +
+ +

When running under a security manager the locations from which classes +are permitted to be loaded will also depend on the contents of your policy +file. See Security Manager HOW-TO +for further information.

+ +
+ + + + +
diff --git a/webapps/docs/cluster-howto.xml b/webapps/docs/cluster-howto.xml new file mode 100644 index 000000000000..03afde6fe83e --- /dev/null +++ b/webapps/docs/cluster-howto.xml @@ -0,0 +1,699 @@ + + + +]> + + + &project; + + + Filip Hanik + Peter Rossbach + Clustering/Session Replication HOW-TO + + + + +
+

You can also check the configuration reference documentation. +

+
+ +
+ +
+ +
+

+ Simply add <Cluster className="org.apache.catalina.ha.tcp.SimpleTcpCluster"/> + to your <Engine> or your <Host> element to enable clustering. +

+

+ Using the above configuration will enable all-to-all session replication + using the DeltaManager to replicate session deltas. By all-to-all we mean that the session gets replicated to all the other + nodes in the cluster. This works great for smaller cluster but we don't recommend it for larger clusters(a lot of tomcat nodes). + Also when using the delta manager it will replicate to all nodes, even nodes that don't have the application deployed.
+ To get around this problem, you'll want to use the BackupManager. This manager only replicates the session data to one backup + node, and only to nodes that have the application deployed. Downside of the BackupManager: not quite as battle tested as the delta manager. +
+ Here are some of the important default values:
+ 1. Multicast address is 228.0.0.4
+ 2. Multicast port is 45564 (the port and the address together determine cluster membership.
+ 3. The IP broadcasted is java.net.InetAddress.getLocalHost().getHostAddress() (make sure you don't broadcast 127.0.0.1, this is a common error)
+ 4. The TCP port listening for replication messages is the first available server socket in range 4000-4100
+ 5. Two listeners are configured ClusterSessionListener and JvmRouteSessionIDBinderListener
+ 6. Two interceptors are configured TcpFailureDetector and MessageDispatch15Interceptor
+ The following is the default cluster configuration:
+ + <Cluster className="org.apache.catalina.ha.tcp.SimpleTcpCluster" + channelSendOptions="8"> + + <Manager className="org.apache.catalina.ha.session.DeltaManager" + expireSessionsOnShutdown="false" + notifyListenersOnReplication="true"/> + + <Channel className="org.apache.catalina.tribes.group.GroupChannel"> + <Membership className="org.apache.catalina.tribes.membership.McastService" + address="228.0.0.4" + port="45564" + frequency="500" + dropTime="3000"/> + <Receiver className="org.apache.catalina.tribes.transport.nio.NioReceiver" + address="auto" + port="4000" + autoBind="100" + selectorTimeout="5000" + maxThreads="6"/> + + <Sender className="org.apache.catalina.tribes.transport.ReplicationTransmitter"> + <Transport className="org.apache.catalina.tribes.transport.nio.PooledParallelSender"/> + </Sender> + <Interceptor className="org.apache.catalina.tribes.group.interceptors.TcpFailureDetector"/> + <Interceptor className="org.apache.catalina.tribes.group.interceptors.MessageDispatch15Interceptor"/> + </Channel> + + <Valve className="org.apache.catalina.ha.tcp.ReplicationValve" + filter=""/> + <Valve className="org.apache.catalina.ha.session.JvmRouteBinderValve"/> + + <Deployer className="org.apache.catalina.ha.deploy.FarmWarDeployer" + tempDir="/tmp/war-temp/" + deployDir="/tmp/war-deploy/" + watchDir="/tmp/war-listen/" + watchEnabled="false"/> + + <ClusterListener className="org.apache.catalina.ha.session.JvmRouteSessionIDBinderListener"/> + <ClusterListener className="org.apache.catalina.ha.session.ClusterSessionListener"/> + </Cluster> + +

+

Will cover this section in more detail later in this document.

+
+ +
+ +

To run session replication in your Tomcat 7.0 container, the following steps +should be completed:

+
    +
  • All your session attributes must implement java.io.Serializable
  • +
  • Uncomment the Cluster element in server.xml
  • +
  • If you have defined custom cluster valves, make sure you have the ReplicationValve defined as well under the Cluster element in server.xml
  • +
  • If your Tomcat instances are running on the same machine, make sure the tcpListenPort + attribute is unique for each instance, in most cases Tomcat is smart enough to resolve this on it's own by autodetecting available ports in the range 4000-4100
  • +
  • Make sure your web.xml has the + <distributable/> element
  • +
  • If you are using mod_jk, make sure that jvmRoute attribute is set at your Engine <Engine name="Catalina" jvmRoute="node01" > + and that the jvmRoute attribute value matches your worker name in workers.properties
  • +
  • Make sure that all nodes have the same time and sync with NTP service!
  • +
  • Make sure that your loadbalancer is configured for sticky session mode.
  • +
+

Load balancing can be achieved through many techniques, as seen in the +Load Balancing chapter.

+

Note: Remember that your session state is tracked by a cookie, so your URL must look the same from the out + side otherwise, a new session will be created.

+

Note: Clustering support currently requires the JDK version 1.5 or later.

+

The Cluster module uses the Tomcat JULI logging framework, so you can configure logging + through the regular logging.properties file. To track messages, you can enable logging on the key:org.apache.catalina.tribes.MESSAGES

+
+ + +
+ +

To enable session replication in Tomcat, three different paths can be followed to achieve the exact same thing:

+
    +
  1. Using session persistence, and saving the session to a shared file system (PersistenceManager + FileStore)
  2. +
  3. Using session persistence, and saving the session to a shared database (PersistenceManager + JDBCStore)
  4. +
  5. Using in-memory-replication, using the SimpleTcpCluster that ships with Tomcat (lib/catalina-tribes.jar + lib/catalina-ha.jar)
  6. +
+ +

In this release of session replication, Tomcat can perform an all-to-all replication of session state using the DeltaManager or + perform backup replication to only one node using the BackupManager. + The all-to-all replication is an algorithm that is only efficient when the clusters are small. For larger clusters, to use + a primary-secondary session replication where the session will only be stored at one backup server simply setup the BackupManager.
+ Currently you can use the domain worker attribute (mod_jk > 1.2.8) to build cluster partitions + with the potential of having a more scaleable cluster solution with the DeltaManager(you'll need to configure the domain interceptor for this). + In order to keep the network traffic down in an all-to-all environment, you can split your cluster + into smaller groups. This can be easily achieved by using different multicast addresses for the different groups. + A very simple setup would look like this: +

+ + + DNS Round Robin + | + Load Balancer + / \ + Cluster1 Cluster2 + / \ / \ + Tomcat1 Tomcat2 Tomcat3 Tomcat4 + + +

What is important to mention here, is that session replication is only the beginning of clustering. + Another popular concept used to implement clusters is farming, i.e., you deploy your apps only to one + server, and the cluster will distribute the deployments across the entire cluster. + This is all capabilities that can go into with the FarmWarDeployer (s. cluster example at server.xml)

+

In the next section will go deeper into how session replication works and how to configure it.

+ +
+ +
+

Membership is established using multicast heartbeats. + Hence, if you wish to subdivide your clusters, you can do this by + changing the multicast IP address or port in the <Membership> element. +

+

+ The heartbeat contains the IP address of the Tomcat node and the TCP port that + Tomcat listens to for replication traffic. All data communication happens over TCP. +

+

+ The ReplicationValve is used to find out when the request has been completed and initiate the + replication, if any. Data is only replicated if the session has changed (by calling setAttribute or removeAttribute + on the session). +

+

+ One of the most important performance considerations is the synchronous versus asynchronous replication. + In a synchronous replication mode the request doesn't return until the replicated session has been + sent over the wire and reinstantiated on all the other cluster nodes. + Synchronous vs. asynchronous is configured using the channelSendOptions + flag and is an integer value. The default value for the SimpleTcpCluster/DeltaManager combo is + 8, which is asynchronous. You can read more on the send flag(overview) or the + send flag(javadoc). + During async replication, the request is returned before the data has been replicated. async replication yields shorter + request times, and synchronous replication guarantees the session to be replicated before the request returns. +

+
+ +
+

+ If you are using mod_jk and not using sticky sessions or for some reasons sticky session don't + work, or you are simply failing over, the session id will need to be modified as it previously contained + the worker id of the previous tomcat (as defined by jvmRoute in the Engine element). + To solve this, we will use the JvmRouteBinderValve. +

+

+ The JvmRouteBinderValve rewrites the session id to ensure that the next request will remain sticky + (and not fall back to go to random nodes since the worker is no longer available) after a fail over. + The valve rewrites the JSESSIONID value in the cookie with the same name. + Not having this valve in place, will make it harder to ensure stickyness in case of a failure for the mod_jk module. +

+

+ By default, if no valves are configured, the JvmRouteBinderValve is added on. + The cluster message listener called JvmRouteSessionIDBinderListener is also defined by default and is used to actually rewrite the + session id on the other nodes in the cluster once a fail over has occurred. + Remember, if you are adding your own valves or cluster listeners in server.xml then the defaults are no longer valid, + make sure that you add in all the appropriate valves and listeners as defined by the default. +

+

+ Hint:
+ With attribute sessionIdAttribute you can change the request attribute name that included the old session id. + Default attribute name is org.apache.catalina.cluster.session.JvmRouteOrignalSessionID. +

+

+ Trick:
+ You can enable this mod_jk turnover mode via JMX before you drop a node to all backup nodes! + Set enable true on all JvmRouteBinderValve backups, disable worker at mod_jk + and then drop node and restart it! Then enable mod_jk Worker and disable JvmRouteBinderValves again. + This use case means that only requested session are migrated. +

+ + +
+ +
+ + <Cluster className="org.apache.catalina.ha.tcp.SimpleTcpCluster" + channelSendOptions="6"> + + <Manager className="org.apache.catalina.ha.session.BackupManager" + expireSessionsOnShutdown="false" + notifyListenersOnReplication="true" + mapSendOptions="6"/> + <!-- + <Manager className="org.apache.catalina.ha.session.DeltaManager" + expireSessionsOnShutdown="false" + notifyListenersOnReplication="true"/> + --> + <Channel className="org.apache.catalina.tribes.group.GroupChannel"> + <Membership className="org.apache.catalina.tribes.membership.McastService" + address="228.0.0.4" + port="45564" + frequency="500" + dropTime="3000"/> + <Receiver className="org.apache.catalina.tribes.transport.nio.NioReceiver" + address="auto" + port="5000" + selectorTimeout="100" + maxThreads="6"/> + + <Sender className="org.apache.catalina.tribes.transport.ReplicationTransmitter"> + <Transport className="org.apache.catalina.tribes.transport.nio.PooledParallelSender"/> + </Sender> + <Interceptor className="org.apache.catalina.tribes.group.interceptors.TcpFailureDetector"/> + <Interceptor className="org.apache.catalina.tribes.group.interceptors.MessageDispatch15Interceptor"/> + <Interceptor className="org.apache.catalina.tribes.group.interceptors.ThroughputInterceptor"/> + </Channel> + + <Valve className="org.apache.catalina.ha.tcp.ReplicationValve" + filter=".*\.gif;.*\.js;.*\.jpg;.*\.png;.*\.htm;.*\.html;.*\.css;.*\.txt;"/> + + <Deployer className="org.apache.catalina.ha.deploy.FarmWarDeployer" + tempDir="/tmp/war-temp/" + deployDir="/tmp/war-deploy/" + watchDir="/tmp/war-listen/" + watchEnabled="false"/> + + <ClusterListener className="org.apache.catalina.ha.session.ClusterSessionListener"/> + </Cluster> + +

+ Break it down!! +

+ + <Cluster className="org.apache.catalina.ha.tcp.SimpleTcpCluster" + channelSendOptions="6"> + +

+ The main element, inside this element all cluster details can be configured. + The channelSendOptions is the flag that is attached to each message sent by the + SimpleTcpCluster class or any objects that are invoking the SimpleTcpCluster.send method. + The description of the send flags is available at + our javadoc site + The DeltaManager sends information using the SimpleTcpCluster.send method, while the backup manager + sends it itself directly through the channel. +
For more info, Please visit the reference documentation +

+ + <Manager className="org.apache.catalina.ha.session.BackupManager" + expireSessionsOnShutdown="false" + notifyListenersOnReplication="true" + mapSendOptions="6"/> + <!-- + <Manager className="org.apache.catalina.ha.session.DeltaManager" + expireSessionsOnShutdown="false" + notifyListenersOnReplication="true"/> + --> + +

+ This is a template for the manager configuration that will be used if no manager is defined in the <Context> + element. In Tomcat 5.x each webapp marked distributable had to use the same manager, this is no longer the case + since Tomcat you can define a manager class for each webapp, so that you can mix managers in your cluster. + Obviously the managers on one node's application has to correspond with the same manager on the same application on the other node. + If no manager has been specified for the webapp, and the webapp is marked <distributable/> Tomcat will take this manager configuration + and create a manager instance cloning this configuration. +
For more info, Please visit the reference documentation +

+ + <Channel className="org.apache.catalina.tribes.group.GroupChannel"> + +

+ The channel element is Tribes, the group communication framework + used inside Tomcat. This element encapsulates everything that has to do with communication and membership logic. +
For more info, Please visit the reference documentation +

+ + <Membership className="org.apache.catalina.tribes.membership.McastService" + address="228.0.0.4" + port="45564" + frequency="500" + dropTime="3000"/> + +

+ Membership is done using multicasting. Please note that Tribes also supports static memberships using the + StaticMembershipInterceptor if you want to extend your membership to points beyond multicasting. + The address attribute is the multicast address used and the port is the multicast port. These two together + create the cluster separation. If you want a QA cluster and a production cluster, the easiest config is to + have the QA cluster be on a separate multicast address/port combination the the production cluster.
+ The membership component broadcasts TCP adress/port of itselt to the other nodes so that communication between + nodes can be done over TCP. Please note that the address being broadcasted is the one of the + Receiver.address attribute. +
For more info, Please visit the reference documentation +

+ + <Receiver className="org.apache.catalina.tribes.transport.nio.NioReceiver" + address="auto" + port="5000" + selectorTimeout="100" + maxThreads="6"/> + +

+ In tribes the logic of sending and receiving data has been broken into two functional components. The Receiver, as the name suggests + is responsible for receiving messages. Since the Tribes stack is thread less, (a popular improvement now adopted by other frameworks as well), + there is a thread pool in this component that has a maxThreads and minThreads setting.
+ The address attribute is the host address that will be broadcasted by the membership component to the other nodes. +
For more info, Please visit the reference documentation +

+ + + <Sender className="org.apache.catalina.tribes.transport.ReplicationTransmitter"> + <Transport className="org.apache.catalina.tribes.transport.nio.PooledParallelSender"/> + </Sender> + +

+ The sender component, as the name indicates is responsible for sending messages to other nodes. + The sender has a shell component, the ReplicationTransmitter but the real stuff done is done in the + sub component, Transport. + Tribes support having a pool of senders, so that messages can be sent in parallel and if using the NIO sender, + you can send messages concurrently as well.
+ Concurrently means one message to multiple senders at the same time and Parallel means multiple messages to multiple senders + at the same time. +
For more info, Please visit the reference documentation +

+ + <Interceptor className="org.apache.catalina.tribes.group.interceptors.TcpFailureDetector"/> + <Interceptor className="org.apache.catalina.tribes.group.interceptors.MessageDispatch15Interceptor"/> + <Interceptor className="org.apache.catalina.tribes.group.interceptors.ThroughputInterceptor"/> + </Channel> + +

+ Tribes uses a stack to send messages through. Each element in the stack is called an interceptor, and works much like the valves do + in the Tomcat servlet container. + Using interceptors, logic can be broken into more managable pieces of code. The interceptors configured above are:
+ TcpFailureDetector - verifies crashed members through TCP, if multicast packets get dropped, this interceptor protects against false positives, + ie the node marked as crashed even though it still is alive and running.
+ MessageDispatch15Interceptor - dispatches messages to a thread (thread pool) to send message asynchrously.
+ ThroughputInterceptor - prints out simple stats on message traffic.
+ Please note that the order of interceptors is important. the way they are defined in server.xml is the way they are represented in the + channel stack. Think of it as a linked list, with the head being the first most interceptor and the tail the last. +
For more info, Please visit the reference documentation +

+ + <Valve className="org.apache.catalina.ha.tcp.ReplicationValve" + filter=".*\.gif;.*\.js;.*\.jpg;.*\.png;.*\.htm;.*\.html;.*\.css;.*\.txt;"/> + +

+ The cluster uses valves to track requests to web applications, we've mentioned the ReplicationValve and the JvmRouteBinderValve above. + The <Cluster> element itself is not part of the pipeline in Tomcat, instead the cluster adds the valve to its parent container. + If the <Cluster> elements is configured in the <Engine> element, the valves get added to the engine and so on. +
For more info, Please visit the reference documentation +

+ + <Deployer className="org.apache.catalina.ha.deploy.FarmWarDeployer" + tempDir="/tmp/war-temp/" + deployDir="/tmp/war-deploy/" + watchDir="/tmp/war-listen/" + watchEnabled="false"/> + +

+ The default tomcat cluster supports farmed deployment, ie, the cluster can deploy and undeploy applications on the other nodes. + The state of this component is currently in flux but will be addressed soon. There was a change in the deployment algorithm + between Tomcat 5.0 and 5.5 and at that point, the logic of this component changed to where the deploy dir has to match the + webapps directory. +
For more info, Please visit the reference documentation +

+ + <ClusterListener className="org.apache.catalina.ha.session.ClusterSessionListener"/> + </Cluster> + +

+ Since the SimpleTcpCluster itself is a sender and receiver of the Channel object, components can register themselves as listeners to + the SimpleTcpCluster. The listener above ClusterSessionListener listens for DeltaManager replication messages + and applies the deltas to the manager that in turn applies it to the session. +
For more info, Please visit the reference documentation +

+ +
+ +
+ +

Component Levels: + + Server + | + Service + | + Engine + | \ + | --- Cluster --* + | + Host + | + ------ + / \ + Cluster Context(1-N) + | \ + | -- Manager + | \ + | -- DeltaManager + | -- BackupManager + | + --------------------------- + | \ + Channel \ + ----------------------------- \ + | \ + Interceptor_1 .. \ + | \ + Interceptor_N \ + ----------------------------- \ + | | | \ + Receiver Sender Membership \ + -- Valve + | \ + | -- ReplicationValve + | -- JvmRouteBinderValve + | + -- LifecycleListener + | + -- ClusterListener + | \ + | -- ClusterSessionListener + | -- JvmRouteSessionIDBinderListener + | + -- Deployer + \ + -- FarmWarDeployer + + + +

+ +
+
+

To make it easy to understand how clustering works, We are gonna take you through a series of scenarios. + In the scenario we only plan to use two tomcat instances TomcatA and TomcatB. + We will cover the following sequence of events:

+ +
    +
  1. TomcatA starts up
  2. +
  3. TomcatB starts up (Wait that TomcatA start is complete)
  4. +
  5. TomcatA receives a request, a session S1 is created.
  6. +
  7. TomcatA crashes
  8. +
  9. TomcatB receives a request for session S1
  10. +
  11. TomcatA starts up
  12. +
  13. TomcatA receives a request, invalidate is called on the session (S1)
  14. +
  15. TomcatB receives a request, for a new session (S2)
  16. +
  17. TomcatA The session S2 expires due to inactivity.
  18. +
+ +

Ok, now that we have a good sequence, we will take you through exactly what happens in the session repliction code

+ +
    +
  1. TomcatA starts up +

    + Tomcat starts up using the standard start up sequence. When the Host object is created, a cluster object is associated with it. + When the contexts are parsed, if the distributable element is in place in web.xml + Tomcat asks the Cluster class (in this case SimpleTcpCluster) to create a manager + for the replicated context. So with clustering enabled, distributable set in web.xml + Tomcat will create a DeltaManager for that context instead of a StandardManager. + The cluster class will start up a membership service (multicast) and a replication service (tcp unicast). + More on the architecture further down in this document. +

    +
  2. +
  3. TomcatB starts up +

    + When TomcatB starts up, it follows the same sequence as TomcatA did with one exception. + The cluster is started and will establish a membership (TomcatA,TomcatB). + TomcatB will now request the session state from a server that already exists in the cluster, + in this case TomcatA. TomcatA responds to the request, and before TomcatB starts listening + for HTTP requests, the state has been transferred from TomcatA to TomcatB. + In case TomcatA doesn't respond, TomcatB will time out after 60 seconds, and issue a log + entry. The session state gets transferred for each web application that has distributable in + its web.xml. Note: To use session replication efficiently, all your tomcat instances should be + configured the same. +

    +
  4. +
  5. TomcatA receives a request, a session S1 is created. +

    + The request coming in to TomcatA is treated exactly the same way as without session replication. + The action happens when the request is completed, the ReplicationValve will intercept + the request before the response is returned to the user. + At this point it finds that the session has been modified, and it uses TCP to replicata the + session to TomcatB. Once the serialized data has been handed off to the operating systems TCP logic, + the request returns to the user, back through the valve pipeline. + For each request the entire session is replicated, this allows code that modifies attributes + in the session without calling setAttribute or removeAttribute to be replicated. + a useDirtyFlag configuration parameter can be used to optimize the number of times + a session is replicated. +

    + +
  6. +
  7. TomcatA crashes +

    + When TomcatA crashes, TomcatB receives a notification that TomcatA has dropped out + of the cluster. TomcatB removes TomcatA from its membership list, and TomcatA will no longer + be notified of any changes that occurs in TomcatB. + The load balancer will redirect the requests from TomcatA to TomcatB and all the sessions + are current. +

    +
  8. +
  9. TomcatB receives a request for session S1 +

    Nothing exciting, TomcatB will process the request as any other request. +

    +
  10. +
  11. TomcatA starts up +

    Upon start up, before TomcatA starts taking new request and making itself + available to it will follow the start up sequence described above 1) 2). + It will join the cluster, contact TomcatB for the current state of all the sessions. + And once it receives the session state, it finishes loading and opens its HTTP/mod_jk ports. + So no requests will make it to TomcatA until it has received the session state from TomcatB. +

    +
  12. +
  13. TomcatA receives a request, invalidate is called on the session (S1) +

    The invalidate is call is intercepted, and the session is queued with invalidated sessions. + When the request is complete, instead of sending out the session that has changed, it sends out + an "expire" message to TomcatB and TomcatB will invalidate the session as well. +

    + +
  14. +
  15. TomcatB receives a request, for a new session (S2) +

    Same scenario as in step 3) +

    + + +
  16. +
  17. TomcatA The session S2 expires due to inactivity. +

    The invalidate is call is intercepted the same was as when a session is invalidated by the user, + and the session is queued with invalidated sessions. + At this point, the invalidet session will not be replicated across until + another request comes through the system and checks the invalid queue. +

    +
  18. +
+ +

Phuuuhh! :)

+ +

Membership + Clustering membership is established using very simple multicast pings. + Each Tomcat instance will periodically send out a multicast ping, + in the ping message the instance will broad cast its IP and TCP listen port + for replication. + If an instance has not received such a ping within a given timeframe, the + member is considered dead. Very simple, and very effective! + Of course, you need to enable multicasting on your system. +

+ +

TCP Replication + Once a multicast ping has been received, the member is added to the cluster + Upon the next replication request, the sending instance will use the host and + port info and establish a TCP socket. Using this socket it sends over the serialized data. + The reason I choose TCP sockets is because it has built in flow control and guaranteed delivery. + So I know, when I send some data, it will make it there :) +

+ +

Distributed locking and pages using frames + Tomcat does not keep session instances in sync across the cluster. + The implementation of such logic would be to much overhead and cause all + kinds of problems. If your client accesses the same session + simultanously using multiple requests, then the last request + will override the other sessions in the cluster. +

+ +
+ + +
+

Monitoring is a very important question when you use a cluster. Some of the cluster objects are JMX MBeans

+

Add the following parameter to your startup script with Java 5: + +set CATALINA_OPTS=\ +-Dcom.sun.management.jmxremote \ +-Dcom.sun.management.jmxremote.port=%my.jmx.port% \ +-Dcom.sun.management.jmxremote.ssl=false \ +-Dcom.sun.management.jmxremote.authenticate=false + +

+

Activate JMX with JDK 1.4: +

    +
  1. Install the compat package
  2. +
  3. Install the mx4j-tools.jar at common/lib (use the same mx4j version as your tomcat release)
  4. +
  5. Configure a MX4J JMX HTTP Adaptor at your AJP Connector

    + +<Connector port="${AJP.PORT}" + handler.list="mx" + mx.enabled="true" + mx.httpHost="${JMX.HOST}" + mx.httpPort="${JMX.PORT}" + protocol="AJP/1.3" /> + +
  6. +
  7. Start your tomcat and look with your browser to http://${JMX.HOST}:${JMX.PORT}
  8. +
  9. With the connector parameter mx.authMode="basic" mx.authUser="tomcat" mx.authPassword="strange" you can control the access!
  10. +
+

+

+List of Cluster Mbeans
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
NameDescriptionMBean ObjectName - EngineMBean ObjectName - Host
ClusterThe complete cluster elementtype=Clustertype=Cluster,host=${HOST}
DeltaManagerThis manager control the sessions and handle session replication type=Manager,path=${APP.CONTEXT.PATH}, host=${HOST}type=Manager,path=${APP.CONTEXT.PATH}, host=${HOST}
ReplicationValveThis valve control the replication to the backup nodestype=Valve,name=ReplicationValvetype=Valve,name=ReplicationValve,host=${HOST}
JvmRouteBinderValveThis is a cluster fallback valve to change the Session ID to the current tomcat jvmroute.type=Valve,name=JvmRouteBinderValve, + path=${APP.CONTEXT.PATH}type=Valve,name=JvmRouteBinderValve,host=${HOST}, + path=${APP.CONTEXT.PATH}
+

+
+ +
+

Please see the clustering section of the FAQ.

+
+ + + +
diff --git a/webapps/docs/config/ajp.xml b/webapps/docs/config/ajp.xml new file mode 100644 index 000000000000..638ec1722ba5 --- /dev/null +++ b/webapps/docs/config/ajp.xml @@ -0,0 +1,485 @@ + + + +]> + + + &project; + + + Remy Maucherat + Yoav Shapira + Andrew R. Jaquith + The AJP Connector + + + + +
+ +
+ +
+ +

The AJP Connector element represents a + Connector component that communicates with a web + connector via the AJP protocol. This is used for cases + where you wish to invisibly integrate Tomcat into an existing (or new) + Apache installation, and you want Apache to handle the static content + contained in the web application, and/or utilize Apache's SSL + processing.

+ +

This connector supports load balancing when used in conjunction with + the jvmRoute attribute of the + Engine.

+ +

The native connectors supported with this Tomcat release are: +

    +
  • JK 1.2.x with any of the supported servers
  • +
  • mod_proxy on Apache httpd 2.x (included by default in Apache HTTP + Server 2.2), with AJP enabled: see + the + httpd docs for details.
  • +
+

+ +

Other native connectors supporting AJP may work, but are no longer + supported.

+ +
+ + +
+ + + +

All implementations of Connector + support the following attributes:

+ + + + +

A boolean value which can be used to enable or disable the TRACE + HTTP method. If not specified, this attribute is set to false.

+
+ + +

The default timeout for asynchronous requests in milliseconds. If not + specified, this attribute is set to 10000 (10 seconds).

+
+ + +

Set to true if you want calls to + request.getRemoteHost() to perform DNS lookups in + order to return the actual host name of the remote client. Set + to false to skip the DNS lookup and return the IP + address in String form instead (thereby improving performance). + By default, DNS lookups are enabled.

+
+ + +

The maximum size in bytes of the POST which will be handled by + the container FORM URL parameter parsing. The limit can be disabled by + setting this attribute to a value less than or equal to 0. + If not specified, this attribute is set to 2097152 (2 megabytes).

+
+ + +

The maximum size in bytes of the POST which will be saved/buffered by + the container during FORM or CLIENT-CERT authentication. For both types + of authentication, the POST will be saved/buffered before the user is + authenticated. For CLIENT-CERT authentication, the POST is buffered for + the duration of the SSL handshake and the buffer emptied when the request + is processed. For FORM authentication the POST is saved whilst the user + is re-directed to the login form and is retained until the user + successfully authenticates or the session associated with the + authentication request expires. The limit can be disabled by setting this + attribute to -1. Setting the attribute to zero will disable the saving of + POST data during authentication. If not specified, this attribute is set + to 4096 (4 kilobytes).

+
+ + +

The TCP port number on which this Connector + will create a server socket and await incoming connections. Your + operating system will allow only one server application to listen + to a particular port number on a particular IP address.

+
+ + +

Sets the protocol to handle incoming traffic. To configure an AJP + connector this must be specified. If no value for protocol is provided, + an HTTP connector rather than an AJP connector + will be configured.
+ The standard protocol value for an AJP connector is AJP/1.3 + which uses an auto-switching mechanism to select either a Java based + connector or an APR/native based connector. If the + PATH (Windows) or LD_LIBRARY_PATH (on most unix + systems) environment variables contain the Tomcat native library, the + native/APR connector will be used. If the native library cannot be + found, the Java based connector will be used.
+ To use an explicit protocol rather than rely on the auto-switching + mechanism described above, the following values may be used:
+ org.apache.coyote.ajp.AjpProtocol + - blocking Java connector
+ org.apache.coyote.ajp.AjpAprProtocol + - the APR/native connector.
+ Custom implementations may also be used.

+
+ + +

If this Connector is being used in a proxy + configuration, configure this attribute to specify the server name + to be returned for calls to request.getServerName(). + See Proxy Support for more + information.

+
+ + +

If this Connector is being used in a proxy + configuration, configure this attribute to specify the server port + to be returned for calls to request.getServerPort(). + See Proxy Support for more + information.

+
+ + +

If this Connector is supporting non-SSL + requests, and a request is received for which a matching + <security-constraint> requires SSL transport, + Catalina will automatically redirect the request to the port + number specified here.

+
+ + +

Set this attribute to the name of the protocol you wish to have + returned by calls to request.getScheme(). For + example, you would set this attribute to "https" + for an SSL Connector. The default value is "http". +

+
+ + +

Set this attribute to true if you wish to have + calls to request.isSecure() to return true + for requests received by this Connector. You would want this on an + SSL Connector or a non SSL connector that is receiving data from a + SSL accelerator, like a crypto card, a SSL appliance or even a webserver. + The default value is false.

+
+ + +

This specifies the character encoding used to decode the URI bytes, + after %xx decoding the URL. If not specified, ISO-8859-1 will be used. +

+
+ + +

This specifies if the encoding specified in contentType should be used + for URI query parameters, instead of using the URIEncoding. This + setting is present for compatibility with Tomcat 4.1.x, where the + encoding specified in the contentType, or explicitly set using + Request.setCharacterEncoding method was also used for the parameters from + the URL. The default value is false. +

+
+ + +

Set this attribute to true to cause Tomcat to use + the IP address passed by the native web server to determine the Host + to send the request to. The default value is false.

+
+ + +

Set this attribute to true to cause Tomcat to advertise + support for the Servlet specification using the header recommended in the + specification. The default value is false.

+
+ +
+ +
+ + + +

To use AJP, you must specify the protocol attribute (see above).

+ +

These implementations support the AJP 1.3 protocol.

+ +

They support the following additional attributes (in addition to the + common attributes listed above):

+ +

The BIO and APR/native implementations (there is no NIO implementation for + APR) both support the following additional attributes in addition to the + standard Connector attributes listed above:

+ + + + +

The maximum queue length for incoming connection requests when + all possible request processing threads are in use. Any requests + received when the queue is full will be refused. The default + value is 100.

+
+ + +

The number of threads to be used to accept connections. Increase this + value on a multi CPU machine, although you would never really need more + than 2. Also, with a lot of non keep alive connections, you + might want to increase this value as well. Default value is + 1.

+
+ + +

For servers with more than one IP address, this attribute + specifies which address will be used for listening on the specified + port. By default, this port will be used on all IP addresses + associated with the server. A value of 127.0.0.1 + indicates that the Connector will only listen on the loopback + interface.

+
+ + +

The number of milliseconds during which the sockets used by this + Connector will linger when they are closed. + The default value -1 which disables this option.

+
+ + +

The number of milliseconds this Connector will wait, + after accepting a connection, for the request URI line to be + presented. The default value is 60000 (i.e. 60 seconds).

+
+ + +

A reference to the name in an Executor + element. If this attribute is set, and the named executor exists, the + connector will use the executor, and all the other thread attributes will + be ignored. Note that if a shared executor is not specified for a + connector then the connector will use a private, internal executor to + provide the thread pool.

+
+ + +

The number of milliseconds this Connector will wait for + another AJP request before closing the connection. + The default value is to use the value that has been set for the + connectionTimeout attribute.

+
+ + +

The maximum number of request processing threads to be created + by this Connector, which therefore determines the + maximum number of simultaneous requests that can be handled. If + not specified, this attribute is set to 200. If an executor is associated + with this connector, this attribute is ignored as the connector will + execute tasks using the executor rather than an internal thread pool.

+
+ + +

The minimum number of threads always kept running. If not specified, + the default of 10 is used.

+
+ + +

This attribute sets the maximum AJP packet size in Bytes. The maximum + value is 65536. It should be the same as the max_packet_size + directive configured for mod_jk. Normally it is not necessary to change + the maximum packet size. Problems with the default value have been + reported when sending certificates or certificate chains. The default + value is 8192.

+
+ + +

The protocol handler caches Processor objects to speed up performance. + This setting dictates how many of these objects get cached. + -1 means unlimited, default is 200. Set this + value somewhere close to your maxThreads value.

+
+ + +

Only requests from workers with this secret keyword will be accepted. +

+
+ + +

If set to true, the TCP_NO_DELAY option will be + set on the server socket, which improves performance under most + circumstances. This is set to true by default.

+
+ + +

The priority of the request processing threads within the JVM. + The default value is java.lang.Thread#NORM_PRIORITY. + See the JavaDoc for the java.lang.Thread class for more details on + what this priority means. +

+
+ + +

If set to true, the authentication will be done in Tomcat. + Otherwise, the authenticated principal will be propagated from the native + webserver and used for authorization in Tomcat. + The default value is true.

+
+ +
+ +
+ + + +

The BIO implementation supports the following Java TCP socket attributes + in addition to the common Connector and AJP attributes listed above.

+ + + +

(int)The socket receive buffer (SO_RCVBUF) size in bytes. JVM default + used if not set.

+
+ +

(int)The socket send buffer (SO_SNDBUF) size in bytes. JVM default + used if not set.

+
+ +

(bool)This is equivalent to standard attribute + tcpNoDelay.

+
+ +

(bool)Boolean value for the socket's keep alive setting + (SO_KEEPALIVE). JVM default used if not set.

+
+ +

(bool)Boolean value for the socket OOBINLINE setting. JVM default + used if not set.

+
+ +

(bool)Boolean value for the sockets reuse address option + (SO_REUSEADDR). JVM default used if not set.

+
+ +

(bool)Boolean value for the sockets so linger option (SO_LINGER). + A value for the standard attribute connectionLinger + that is >=0 is equivalent to setting this to true. + A value for the standard attribute connectionLinger + that is <0 is equivalent to setting this to false. + Both this attribute and soLingerTime must be set else the + JVM defaults will be used for both.

+
+ +

(int)Value in seconds for the sockets so linger option (SO_LINGER). + This is equivalent to standard attribute + connectionLinger. + Both this attribute and soLingerOn must be set else the + JVM defaults will be used for both.

+
+ +

This is equivalent to standard attribute + connectionTimeout.

+
+ +

(byte)Value between 0 and 255 for the + traffic class on the socket. JVM default used if not set.

+

NoteOn some JDK versions, setting + soTrafficClass causes a problem. A work around for this + is to add the -Djava.net.preferIPv4Stack=true value to your + JVM options.

+
+ +

(int)The first value for the performance settings. See + Socket Performance Options + All three performance attributes must be set else the JVM defaults will + be used for all three.

+
+ +

(int)The second value for the performance settings. See + Socket Performance Options + All three performance attributes must be set else the JVM defaults will + be used for all three.

+
+ +

(int)The third value for the performance settings. See + Socket Performance Options + All three performance attributes must be set else the JVM defaults will + be used for all three.

+
+ +

(int) The timeout for a socket unlock. When a connector is stopped, it will try to release the acceptor thread by opening a connector to itself. + The default value is 250 and the value is in milliseconds

+
+
+
+ + + +

The APR/native implementation supports the following attributes in + addition to the common Connector and AJP attributes listed above.

+ + + +

Duration of a poll call. Lowering this value will slightly decrease + latency of connections being kept alive in some cases, but will use more + CPU as more poll calls are being made. The default value is 2000 (2ms). +

+
+ + +

Amount of sockets that the poller responsible for polling kept alive + connections can hold at a given time. Extra connections will be closed + right away. The default value is 8192, corresponding to 8192 keep-alive + connections.

+
+ +
+ +
+ +
+ + +
+ +

None at this time.

+ +
+ +
+ + + +

The proxyName and proxyPort attributes can + be used when Tomcat is run behind a proxy server. These attributes + modify the values returned to web applications that call the + request.getServerName() and request.getServerPort() + methods, which are often used to construct absolute URLs for redirects. + Without configuring these attributes, the values returned would reflect + the server name and port on which the connection from the proxy server + was received, rather than the server name and port to whom the client + directed the original request.

+ +

For more information, see the + Proxy Support HOW-TO.

+ +
+ +
+ + + +
diff --git a/webapps/docs/config/cluster-channel.xml b/webapps/docs/config/cluster-channel.xml new file mode 100644 index 000000000000..68e673e8e1a8 --- /dev/null +++ b/webapps/docs/config/cluster-channel.xml @@ -0,0 +1,105 @@ + + + +]> + + + &project; + + + Filip Hanik + The Cluster Channel object + + + + +
+ +
+ +
+ The cluster channel is the main component of a small framework we've nicknamed Apache Tribes.
+ The channel manages a set of sub components and together they create a group communication framework.
+ This framework is then used internally by the components that need to send messages between different Tomcat instances. +
+ A few examples of these components would be the SimpleTcpCluster that does the messaging for the DeltaManager, + or the BackupManager that uses a different replication strategy. The ReplicatedContext object does also + use the channel object to communicate context attribute changes. +
+
+

Channel/Membership:
+ The Membership component is responsible for auto discovering new nodes in the cluster + and also to provide for notifications for any nodes that have not responded with a heartbeat. + The default implementation uses multicast.
+ In the membership component you configure how your nodes, aka. members, are to be discovered and/or + divided up. + You can always find out more about Apache Tribes +

+

Channel/Sender:
+ The Sender component manages all outbound connections and data messages that are sent + over the network from one node to another. + This component allows messages to be sent in parallel. + The default implementation uses TCP client sockets, and socket tuning for outgoing messages are + configured here.
+ You can always find out more about Apache Tribes +

+

Channel/Sender/Transport:
+ The Transport component is the bottom IO layer for the sender component. + The default implementation uses non-blocking TCP client sockets.
+ You can always find out more about Apache Tribes +

+

Channel/Receiver:
+ The receiver component listens for messages from other nodes. + Here you will configure the cluster thread pool, as it will dispatch incoming + messages to a thread pool for faster processing. + The default implementation uses non-blocking TCP server sockets.
+ You can always find out more about Apache Tribes +

+

Channel/Interceptor:
+ The channel will send messages through an interceptor stack. Because of this, you have the ability to + customize the way messages are sent and received, and even how membership is handled.
+ You can always find out more about Apache Tribes +

+
+ + +
+ + + + + + + The default value here is org.apache.catalina.tribes.group.GroupChannel and is + currently the only implementation available. + + + + + + + + + +
+ + + + +
diff --git a/webapps/docs/config/cluster-deployer.xml b/webapps/docs/config/cluster-deployer.xml new file mode 100644 index 000000000000..0dde8275fb45 --- /dev/null +++ b/webapps/docs/config/cluster-deployer.xml @@ -0,0 +1,65 @@ + + + +]> + + + &project; + + + Filip Hanik + The Cluster Deployer object + + + + +
+ +
+ +
+

TODO - Complete documentation

+ + +
+ + +
+ + + + + + + + + + + + + + + + +
+ + + + +
diff --git a/webapps/docs/config/cluster-interceptor.xml b/webapps/docs/config/cluster-interceptor.xml new file mode 100644 index 000000000000..6298306f2640 --- /dev/null +++ b/webapps/docs/config/cluster-interceptor.xml @@ -0,0 +1,197 @@ + + + +]> + + + &project; + + + Filip Hanik + The Channel Interceptor object + + + + +
+ +
+ +
+

+ Apache Tribes supports an interceptor architecture to intercept both messages and membership notifications. + This architecture allows decoupling of logic and opens the way for some very kewl feature add ons. +

+
+ +
+

+

    +
  • org.apache.catalina.tribes.group.interceptors.TcpFailureDetector
  • +
  • org.apache.catalina.tribes.group.interceptors.ThroughputInterceptor
  • +
  • org.apache.catalina.tribes.group.interceptors.MessageDispatch15Interceptor
  • +
  • org.apache.catalina.tribes.group.interceptors.MessageDispatchInterceptor
  • +
  • org.apache.catalina.tribes.group.interceptors.NonBlockingCoordinator
  • +
  • org.apache.catalina.tribes.group.interceptors.OrderInterceptor
  • +
  • org.apache.catalina.tribes.group.interceptors.SimpleCoordinator
  • +
  • org.apache.catalina.tribes.group.interceptors.StaticMembershipInterceptor
  • +
  • org.apache.catalina.tribes.group.interceptors.TwoPhaseCommitInterceptor
  • +
  • org.apache.catalina.tribes.group.interceptors.DomainFilterInterceptor
  • +
  • org.apache.catalina.tribes.group.interceptors.FragmentationInterceptor
  • +
  • org.apache.catalina.tribes.group.interceptors.GzipInterceptor
  • +
+

+
+ +
+

+ In addition to dynamic discovery, Apache Tribes also supports static membership, with membership verification. + To achieve this add the org.apache.catalina.tribes.group.interceptors.StaticMembershipInterceptor + underneath the org.apache.catalina.tribes.group.interceptors.TcpFailureDetector interceptor. + Inside the StaticMembershipInterceptor you can add the static members you wish to have. + The TcpFailureDetector will do a health check on the static members,and also monitor them for crashes + so they will have the same level of notification mechanism as the members that are automatically discovered. + + <Interceptor className="org.apache.catalina.tribes.group.interceptors.StaticMembershipInterceptor"> + <Member className="org.apache.catalina.tribes.membership.StaticMember" + port="5678" + securePort="-1" + host="tomcat01.mydomain.com" + domain="staging-cluster" + uniqueId="{0,1,2,3,4,5,6,7,8,9}"/> + </Interceptor> + + +

+
+ +
+ + + + + Required, as there is no default + + + If you want the interceptor to trigger on certain message depending on the message's option flag, + you can setup the interceptors flag here. + The default value is 0, meaning this interceptor will trigger on all messages. + + + + + + + + The logical cluster domain that this Interceptor accepts. + Two different type of values are possible:
+ 1. Regular string values like "staging-domain" or "tomcat-cluster" will be converted into bytes + using ISO-8859-1 encoding.
+ 2. byte array in string form, for example {216,123,12,3}
+
+
+
+ + + + Required, This dispatcher uses JDK 1.5 java.util.concurrent package + + + The default and hard coded value is 8 (org.apache.catalina.tribes.Channel.SEND_OPTIONS_ASYNCHRONOUS). + The dispatcher will trigger on this value only, as it is predefined by Tribes. + The other attributes are inherited from its base class org.apache.catalina.tribes.group.interceptors.MessageDispatchInterceptor. + + + + + + + Required, Same implementation as MessageDispatch15Interceptor, but with JDK 1.4 compliance. + + + The default and hard coded value is 8 (org.apache.catalina.tribes.Channel.SEND_OPTIONS_ASYNCHRONOUS). + The dispatcher will trigger on this value only, as it is predefined by Tribes. + + + What behavior should be executed when the dispatch queue is full. If true (default), then the message is + is sent synchronously, if false an error is thrown. + + + Size in bytes of the dispatch queue, the default value is 1024*1024*64 (64MB) sets the maximum queue size for the dispatch queue + if the queue fills up, one can trigger the behavior, if alwaysSend is set to true, the message will be sent synchronously + if the flag is false, an error is thrown + + + + + + + + + + + Defines the interval in number of messages when we are to report the throughput statistics. + The report is logged to the org.apache.juli.logging.LogFactory.getLog(ThroughputInterceptor.class) + logger under the INFO level. + Default value is to report every 10000 messages. + + + + + + + + Only one implementation available:org.apache.catalina.tribes.membership.StaticMember + + + The port that this static member listens to for cluster messages + + + The secure port this static member listens to for encrypted cluster messages + default value is -1, this value means the member is not listening on a secure port + + + The host (or network interface) that this static member listens for cluster messages. + Three different type of values are possible:
+ 1. IP address in the form of "216.123.1.23"
+ 2. Hostnames like "tomcat01.mydomain.com" or "tomcat01" as long as they resolve correctly
+ 3. byte array in string form, for example {216,123,12,3}
+
+ + The logical cluster domain for this this static member listens for cluster messages. + Two different type of values are possible:
+ 1. Regular string values like "staging-domain" or "tomcat-cluster" will be converted into bytes + using ISO-8859-1 encoding. + 2. byte array in string form, for example {216,123,12,3}
+
+ + A universally uniqueId for this static member. + The values must be 16 bytes in the following form:
+ 1. byte array in string form, for example {0,1,2,3,4,5,6,7,8,9,10,11,12,13,14,15}
+
+
+
+ + +
+ + + + +
diff --git a/webapps/docs/config/cluster-listener.xml b/webapps/docs/config/cluster-listener.xml new file mode 100644 index 000000000000..067dc710e503 --- /dev/null +++ b/webapps/docs/config/cluster-listener.xml @@ -0,0 +1,80 @@ + + + +]> + + + &project; + + + Filip Hanik + The ClusterListener object + + + + +
+ +
+ +
+

+ The org.apache.catalina.ha.ClusterListener base class + lets you listen in on messages that are received by the Cluster component. +

+ +
+
+

+ When using the DeltaManager, the messages are received by the Cluster object and are propagated to the + to the manager through this listener. +

+
+
+

+ Listens for session Id changes. This listener is only used if you are using mod_jk + along with the jvmRoute attribute where the session Id can change. + In the event of a change, the JvmRouteBinderValve will broadcast the + session change and it will get picked up by this listener. +

+
+ +
+ + + + + + + + + + + + + + + + +
+ + + + +
diff --git a/webapps/docs/config/cluster-manager.xml b/webapps/docs/config/cluster-manager.xml new file mode 100644 index 000000000000..1c9db997befb --- /dev/null +++ b/webapps/docs/config/cluster-manager.xml @@ -0,0 +1,130 @@ + + + +]> + + + &project; + + + Filip Hanik + The ClusterManager object + + + + +
+ +
+ +
+

A cluster manager is an extension to Tomcat's session manager interface, + org.apache.catalina.Manager. + A cluster manager must implement the + org.apache.catalina.ha.ClusterManager and is solely responsible + for how the session is replicated.
+ There are currently two different managers, the + org.apache.catalina.ha.session.DeltaManager replicates deltas of + session data to all members in the cluster. This implementation is proven and + works very well, but has a limitation as it requires the cluster members to be + homogeneous, all nodes must deploy the same applications and be exact + replicas. The org.apache.catalina.ha.session.BackupManager also + replicates deltas but only to one backup node. The location of the backup node + is known to all nodes in the cluster. It also supports heterogeneous + deployments, so the manager knows at what locations the web application is + deployed.

+
+ +
+

The <Manager> element defined inside the + <Cluster> element is the template defined for all web + applications that are marked <distributable/> in their + web.xml file. However, you can still override the manager + implementation on a per web application basis, by putting the + <Manager> inside the <Context> element + either in the context.xml file or the + server.xml file.

+
+ +
+ + + + + + The name of this cluster manager, the name is used to identify a + session manager on a node. The name might get modified by the + Cluster element to make it unique in the container. + + + Set to true if you wish to have session listeners notified + when session attributes are being replicated or removed across Tomcat + nodes in the cluster. + + + When a web application is being shutdown, Tomcat issues an expire call + to each session to notify all the listeners. If you wish for all + sessions to expire on all nodes when a shutdown occurs on one node, set + this value to true. Default value is false. + + + + + + + When a web application is being shutdown, Tomcat issues an expire call + to each session to notify all the listeners. If you wish for all + sessions to expire on all nodes when a shutdown occurs on one node, set + this value to true. + Default value is false. + + + The maximum number of active sessions that will be created by this + Manager, or -1 (the default) for no limit. For this manager, all + sessions are counted as active sessions irrespective if whether or not + the current node is the primary node for the session. + + + The time in seconds to wait for a session state transfer to complete + from another node when a node is starting up. + Default value is 60 seconds. + + + + + + + The backup manager uses a replicated map, this map is sending and + receiving messages. You can setup the flag for how this map is sending + messages, the default value is 6(synchronous).
+ Note that if you use asynchronous messaging it is possible for update + messages for a session to be processed by the receiving node in a + different order to the order in which they were sent. +
+ + The maximum number of active sessions that will be created by this + Manager, or -1 (the default) for no limit. For this manager, only + sessions where the current node is the primary node for the session are + considered active sessions. + +
+
+
+ +
diff --git a/webapps/docs/config/cluster-membership.xml b/webapps/docs/config/cluster-membership.xml new file mode 100644 index 000000000000..c477f298ed81 --- /dev/null +++ b/webapps/docs/config/cluster-membership.xml @@ -0,0 +1,174 @@ + + + +]> + + + &project; + + + Filip Hanik + The Cluster Membership object + + + + +
+ +
+ +
+

+ The membership component in the Apache Tribes Channel is responsible + for dynamic discovery of other members(nodes) in the cluster. +

+
+ +
+

+ The default implementation of the cluster group notification is built on top of multicast heartbeats + sent using UDP packets to a multicast IP address. + Cluster members are grouped together by using the same multicast address/port combination. + Each member sends out a heartbeat with a given interval (frequency), and this + heartbeat is used for dynamic discovery. + In a similar fashion, if a heartbeat has not been received in a timeframe specified by dropTime + ms. a member is considered suspect and the channel and any membership listener will be notified. +

+
+ + + +
+ + + + + + +

+ The default value is org.apache.catalina.tribes.membership.McastService + and is currently the only implementation. + This implementation uses multicast heartbeats for member discovery. +

+
+ +

+ The multicast address that the membership will broadcast its presence and listen + for other heartbeats on. The default value is 228.0.0.4 + Make sure your network is enabled for multicast traffic.
+ The multicast address, in conjunction with the port is what + creates a cluster group. To divide up your farm into several different group, or to + split up QA from production, change the port or the address +
Previously known as mcastAddr. +

+
+ +

+ The multicast port, the default value is 45564
+ The multicast port, in conjunction with the address is what + creates a cluster group. To divide up your farm into several different group, or to + split up QA from production, change the port or the address +

+
+ +

+ The frequency in milliseconds in which heartbeats are sent out. The default value is 500 ms.
+ In most cases the default value is sufficient. Changing this value, simply changes the interval in between heartbeats. +

+
+ +

+ The membership component will time out members and notify the Channel if a member fails to send a heartbeat within + a give time. The default value is 3000 ms. This means, that if a heartbeat is not received from a + member in that timeframe, the membership component will notify the cluster of this.
+ On a high latency network you may wish to increase this value, to protect against false positives.
+ Apache Tribes also provides a TcpFailureDetector that will + verify a timeout using a TCP connection when a heartbeat timeout has occurred. This protects against false positives. +

+
+ +

+ Use this attribute if you wish to bind your multicast traffic to a specific network interface. + By default, or when this attribute is unset, it tries to bind to 0.0.0.0 and sometimes on multihomed hosts + this becomes a problem. +

+
+ +

+ The time-to-live setting for the multicast heartbeats. + This setting should be a value between 0 and 255. The default value is VM implementation specific. +

+
+ +

+ Apache Tribes has the ability to logically group members into domains, by using this domain attribute. + The org.apache.catalina.tribes.Member.getDomain() method returns the value specified here. +

+
+ +

+ The sending and receiving of heartbeats is done on a single thread, hence to avoid blocking this thread forever, + you can control the SO_TIMEOUT value on this socket.
+ If a value smaller or equal to 0 is presented, the code will default this value to frequency +

+
+ +

+ In case of a network failure, Java multicast socket don't transparently fail over, instead the socket will continuously + throw IOException upon each receive request. When recoveryEnabled is set to true, this will close the multicast socket + and open a new socket with the same properties as defined above.
+ The default is true.
+

+
+ +

+ When recoveryEnabled==true this value indicates how many times we will try recovery. + The default is 10.
+

+
+ +

+ When recoveryEnabled==true this value indicates how long time (in milliseconds) + the system will sleep in between recovery attempts, until we either recovered successfully or we have reached the + recoveryCounter limit. + The default is 5000 (5 seconds).
+

+
+ + +

+ Membership uses multicast, it will call java.net.MulticastSocket.setLoopbackMode(localLoopbackDisabled). + When localLoopbackDisabled==true multicast messages will not reach other nodes on the same local machine. + The default is false.
+

+
+ + +
+ + +
+ + +
+ + + + +
diff --git a/webapps/docs/config/cluster-receiver.xml b/webapps/docs/config/cluster-receiver.xml new file mode 100644 index 000000000000..e7479751f668 --- /dev/null +++ b/webapps/docs/config/cluster-receiver.xml @@ -0,0 +1,173 @@ + + + +]> + + + &project; + + + Filip Hanik + The Cluster Receiver object + + + + +
+ +
+ +
+

+ The receiver component is responsible for receiving cluster messages. + As you might notice through the configuration, is that the receiving of messages + and sending of messages are two different components, this is different from many other + frameworks, but there is a good reason for it, to decouple the logic for how messages are sent from + how messages are received.
+ The receiver is very much like the Tomcat Connector, its the base of the thread pool + for incoming cluster messages. The receiver is straight forward, but all the socket settings + for incoming traffic are managed here. +

+
+ +
+

+ The receiver supports both a non blocking, org.apache.catalina.tribes.transport.nio.NioReceiver, and a + blocking, org.apache.catalina.tribes.transport.bio.BioReceiver. It is preferred to use the non blocking receiver + to be able to grow your cluster without running into thread starvation.
+ Using the non blocking receiver allows you to with a very limited thread count to serve a large number of messages. + Usually the rule is to use 1 thread per node in the cluster for small clusters, and then depending on your message frequency + and your hardware, you'll find an optimal number of threads peak out at a certain number. +

+
+ +
+ + + + The implementation of the receiver component. Two implementations available, + org.apache.catalina.tribes.transport.nio.NioReceiver and + org.apache.catalina.tribes.transport.bio.BioReceiver.
+ The org.apache.catalina.tribes.transport.nio.NioReceiver is the + preferred implementation +
+ + The address (network interface) to listen for incoming traffic. + Same as the bind address. The default value is auto and translates to + java.net.InetAddress.getLocalHost().getHostAddress(). + + + Possible values are true or false. + Set to true if you want the receiver to use direct bytebuffers when reading data + from the sockets. + + + The listen port for incoming data. The default value is 4000. + To avoid port conflicts the receiver will automatically bind to a free port within the range of + port <= bindPort <= port+autoBind + So for example, if port is 4000, and autoBind is set to 10, then the receiver will open up + a server socket on the first available port in the range 4000-4100. + + + Default value is 100. + Use this value if you wish to automatically avoid port conflicts the cluster receiver will try to open a + server socket on the port attribute port, and then work up autoBind number of times. + + + The secure listen port. This port is SSL enabled. If this attribute is omitted no SSL port is opened up. + There default value is unset, meaning there is no SSL socket available. + + + The UDP listen port. If this attribute is omitted no UDP port is opened up. + There default value is unset, meaning there is no UDP listener available. + + + The value in milliseconds for the polling timeout in the NioReceiver. On older versions of the JDK + there have been bugs, that should all now be cleared out where the selector never woke up. + The default value is a very high 5000 milliseconds. + + + The maximum number of threads in the receiver thread pool. The default value is 6 + Adjust this value relative to the number of nodes in the cluster, the number of messages being exchanged and + the hardware you are running on. A higher value doesn't mean more efficiency, tune this value according to your + own test results. + + + Minimum number of threads to be created when the receiver is started up. Default value is 6 + + + Boolean value for the socket OOBINLINE option. Possible values are true or false. + + + The receiver buffer size on the receiving sockets. Value is in bytes, the default value is 43800 bytes. + + + The sending buffer size on the receiving sockets. Value is in bytes, the default value is 25188 bytes. + + + The receive buffer size on the datagram socket. + Default value is 25188 bytes. + + + The send buffer size on the datagram socket. + Default value is 43800 bytes. + + + Boolean value for the socket SO_KEEPALIVE option. Possible values are true or false. + + + Boolean value to determine whether to use the SO_LINGER socket option. + Possible values are true or false. Default value is true. + + + Sets the SO_LINGER socket option time value. The value is in seconds. + The default value is 3 seconds. + + + Boolean value for the socket SO_REUSEADDR option. Possible values are true or false. + + + Sets the traffic class level for the socket, the value is between 0 and 255. + Different values are defined in + java.net.Socket#setTrafficClass(int). + + + Boolean value for the socket TCP_NODELAY option. Possible values are true or false. + The default value is true + + + Sets the SO_TIMEOUT option on the socket. The value is in milliseconds and the default value is 3000 + milliseconds. + + + Boolean value whether to use a shared buffer pool of cached org.apache.catalina.tribes.io.XByteBuffer + objects. If set to true, the XByteBuffer that is used to pass a message up the channel, will be recycled at the end + of the requests. This means that interceptors in the channel must not maintain a reference to the object + after the org.apache.catalina.tribes.ChannelInterceptor#messageReceived method has exited. + +
+
+ + + + + +
+ +
diff --git a/webapps/docs/config/cluster-sender.xml b/webapps/docs/config/cluster-sender.xml new file mode 100644 index 000000000000..46a9397c9ce3 --- /dev/null +++ b/webapps/docs/config/cluster-sender.xml @@ -0,0 +1,177 @@ + + + +]> + + + &project; + + + Filip Hanik + The Cluster Sender object + + + + +
+ +
+ +
+

+ The channel sender component is responsible for delivering outgoing cluster messages over the network. + In the default implementation, org.apache.catalina.tribes.transport.ReplicationTransmitter, + the sender is a fairly empty shell with not much logic around a fairly complex <Transport> + component the implements the actual delivery mechanism. +

+
+ +
+

+ In the default transport implementation, org.apache.catalina.tribes.transport.nio.PooledParallelSender, + Apache Tribes implements what we like to call "Concurrent Parallel Delivery". + This means that we can send a message to more than one destination at the same time(parallel), and + deliver two messages to the same destination at the same time(concurrent). Combine these two and we have + "Concurrent Parallel Delivery". +

+

+ When is this useful? The simplest example we can think of is when part of your code is sending a 10MB message, + like a war file being deployed, and you need to push through a small 10KB message, say a session being replicated, + you don't have to wait for the 10MB message to finish, as a separate thread will push in the small message + transmission at the same time. Currently there is no interrupt, pause or priority mechanism available, but check back soon. +

+
+ +
+

+ The nested element <Transport> is is not required, by encouraged, as this is where + you would set all the socket options for the outgoing messages. Please see its attributes below. + There are two implementations, in a similar manner to the receiver, one is non-blocking + based and the other is built using blocking IO.
+ org.apache.catalina.tribes.transport.bio.PooledMultiSender is the blocking implementation and + org.apache.catalina.tribes.transport.nio.PooledParallelSender. + Parallel delivery is not available for the blocking implementation due to the fact that it is blocking a thread on sending data. +

+
+ +
+ + + + Required, only available implementation is org.apache.catalina.tribes.transport.ReplicationTransmitter + + + + + + + Required, an implementation of the org.apache.catalina.tribes.transport.MultiPointSender.
+ Non-blocking implementation is org.apache.catalina.tribes.transport.nio.PooledParallelSender
+ Blocking implementation is org.apache.catalina.tribes.transport.bio.PooledMultiSender +
+ + The receive buffer size on the socket. + Default value is 25188 bytes. + + + The send buffer size on the socket. + Default value is 43800 bytes. + + + The receive buffer size on the datagram socket. + Default value is 25188 bytes. + + + The send buffer size on the datagram socket. + Default value is 43800 bytes. + + + Possible values are true or false. + Set to true if you want the receiver to use direct bytebuffers when writing data + to the sockets. Default value is false + + + The number of requests that can go through the socket before the socket is closed, and reopened + for the next request. The default value is -1, which is unlimited. + + + The number of milliseconds a connection is kept open after its been opened. + The default value is -1, which is unlimited. + + + Sets the SO_TIMEOUT option on the socket. The value is in milliseconds and the default value is 3000 + milliseconds.(3 seconds) This timeout starts when a message send attempt is starting, until the transfer has been completed. + For the NIO sockets, this will mean, that the caller can guarantee that we will not attempt sending the message + longer than this timeout value. For the blocking IO implementation, this translated directly to the soTimeout.
+ A timeout will not spawn a retry attempt, in order to guarantee the return of the application thread. +
+ + How many times do we retry a failed message, that received a IOException at the socket level. + The default value is 1, meaning we will retry a message that has failed once. + In other words, we will attempt a message send no more than twice. One is the original send, and one is the + maxRetryAttempts. + + + Boolean value for the socket OOBINLINE option. Possible values are true or false. + + + Boolean value for the socket SO_KEEPALIVE option. Possible values are true or false. + + + Boolean value to determine whether to use the SO_LINGER socket option. + Possible values are true or false. Default value is true. + + + Sets the SO_LINGER socket option time value. The value is in seconds. + The default value is 3 seconds. + + + Boolean value for the socket SO_REUSEADDR option. Possible values are true or false. + + + Sets the traffic class level for the socket, the value is between 0 and 255. + Default value is int soTrafficClass = 0x04 | 0x08 | 0x010; + Different values are defined in + java.net.Socket#setTrafficClass(int). + + + Boolean value for the socket TCP_NODELAY option. Possible values are true or false. + The default value is true + + + Boolean value, default value is true. + If set to true, the sender will throw a org.apache.catalina.tribes.RemoteProcessException + when we receive a negative ack from the remote member. + Set to false, and Tribes will treat a positive ack the same way as a negative ack, that the message was received. + +
+
+ + + + The maximum number of concurrent connections from A to B. + The value is based on a per-destination count. + The default value is 25 + + + + +
+ +
diff --git a/webapps/docs/config/cluster-valve.xml b/webapps/docs/config/cluster-valve.xml new file mode 100644 index 000000000000..95aa35bc5fe6 --- /dev/null +++ b/webapps/docs/config/cluster-valve.xml @@ -0,0 +1,106 @@ + + + +]> + + + &project; + + + Filip Hanik + The Cluster Valve object + + + + +
+ +
+ +
+

+ A cluster valve is no different from any other Tomcat Valve. + The cluster valves are interceptors in the invocation chain for HTTP requests, and the clustering implementation + uses these valves to make intelligent decision around data and when data should be replicated. +

+

+ A cluster valve must implement the org.apache.catalina.ha.ClusterValve interface. + This is a simple interface that extends the org.apache.catalina.Valve interface. +

+
+ +
+ The ReplicationValve will notify the cluster at the end of a HTTP request + so that the cluster can make a decision whether there is data to be replicated or not. + + + + Set value to org.apache.catalina.ha.tcp.ReplicationValve + + + For known file extensions or urls, you can use a filter to + notify the cluster that the session has not been modified during this + request and the cluster doesn't have to probe the session managers for changes. + If there is a filter match, the cluster assumes there has been no session change. + An example filter would look like filter=".*\.gif;.*\.js;.*\.jpg;.*\.png;.*\.htm;.*\.html;.*\.css;.*\.txt;" + The filter uses regular expressions and each filter is delimited by a semi colon. + Pattern#compile(java.lang.String) + + + Boolean value, so to true, and the replication valve will insert a request attribute with the name + defined by the primaryIndicatorName attribute. + The value inserted into the request attribute is either Boolean.TRUE or + Boolean.FALSE + + + Default value is org.apache.catalina.ha.tcp.isPrimarySession + The value defined here is the name of the request attribute that contains the boolean value + if the session is primary on this server or not. + + + Boolean value. Set to true if you want the valve to collect request statistics. + Default value is false + + + +
+ +
+ In case of a mod_jk failover, the JvmRouteBinderValve will replace the + jvmWorker attribute in the session Id, to make future requests stick to this + node. If you want failback capability, don't enable this valve, but if you want your failover to stick, + and for mod_jk not to have to keep probing the node that went down, you use this valve. + + + + org.apache.catalina.ha.session.JvmRouteBinderValve + + + Default value is true + Runtime attribute to turn on and off turn over of the session's jvmRoute value. + + + + +
+ + + + +
diff --git a/webapps/docs/config/cluster.xml b/webapps/docs/config/cluster.xml new file mode 100644 index 000000000000..a88ea93ec513 --- /dev/null +++ b/webapps/docs/config/cluster.xml @@ -0,0 +1,169 @@ + + + +]> + + + &project; + + + Filip Hanik + The Cluster object + + + + +
+ +
+ +
+

+ The tomcat cluster implementation provides session replication, context attribute replication and + cluster wide WAR file deployment. + While the Cluster configuration is fairly complex, the default configuration will work + for most people out of the box.

+ The Tomcat Cluster implementation is very extensible, and hence we have exposed a myriad of options, + making the configuration seem like a lot, but don't lose faith, instead you have a tremendous control + over what is going on.

+
+
+

+ You can place the <Cluster> element inside either the <Engine> + container or the <Host> container.
+ Placing it in the engine, means that you will support clustering in all virtual hosts of Tomcat, + and share the messaging component. When you place the <Cluster> inside the <Engine> + element, the cluster will append the host name of each session manager to the managers name so that two contexts with + the same name but sitting inside two different hosts will be distinguishable. +

+
+
+

To configure context attribute replication, simply do this by swapping out the context implementation + used for your application context. + <Context className="org.apache.catalina.ha.context.ReplicatedContext"/> + This context extends the Tomcat StandardContext + so all the options from the base implementation are valid. +

+
+
+

Manager:
+ The session manager element identifies what kind of session manager is used in this cluster implementation. + This manager configuration is identical to the one you would use in a regular <Context> configuration. +
The default value is the org.apache.catalina.ha.session.DeltaManager that is closely coupled with + the SimpleTcpCluster implementation. Other managers like the org.apache.catalina.ha.session.BackupManager + are/could be loosely coupled and don't rely on the SimpleTcpCluster for its data replication. +

+

Channel:
+ The Channel and its sub components are all part of the IO layer + for the cluster group, and is a module in it's own that we have nick named "Tribes" +
+ Any configuring and tuning of the network layer, the messaging and the membership logic + will be done in the channel and its nested components. + You can always find out more about Apache Tribes +

+

Valve:
+ The Tomcat Cluster implementation uses Tomcat Valves to + track when requests enter and exit the servlet container. It uses these valves to be able to make + intelligent decisions on when to replicate data, which is always at the end of a request. +

+

Deployer:
+ The Deployer component is the Tomcat Farm Deployer. It allows you to deploy and undeploy applications + cluster wide. +

+

ClusterListener:
+ ClusterListener's are used to track messages sent and received using the SimpleTcpCluster. + If you wish to track messages, you can add a listener here, or you can add a valve to the channel object. +

+
+ +
+

+ Deprecated settings: In the previous version of Tomcat you were able to control session + manager settings using manager.<property>=value. + This has been discontinued, as the way it was written interferes with + the ability to support multiple different manager classes under one cluster implementation, + as the same properties might have the different effect on different managers. +

+
+ +
+ + + +

The main cluster class, currently only one is available, + org.apache.catalina.ha.tcp.SimpleTcpCluster +

+
+ +

The Tribes channel send options, default is 8.
+ This option is used to set the flag that all messages sent through the + SimpleTcpCluster uses. The flag decides how the messages are sent, and is a simple logical OR.
+ + + int options= Channel.SEND_OPTIONS_ASYNCHRONOUS | + Channel.SEND_OPTIONS_SYNCHRONIZED_ACK | + Channel.SEND_OPTIONS_USE_ACK; + + Some of the values are:
+ Channel.SEND_OPTIONS_SYNCHRONIZED_ACK = 0x0004
+ Channel.SEND_OPTIONS_ASYNCHRONOUS = 0x0008
+ Channel.SEND_OPTIONS_USE_ACK = 0x0002
+ So to use ACK and ASYNC messaging, the flag would be 10 (8+2) or 0x000B
+ Note that if you use ASYNC messaging it is possible for update messages + for a session to be processed by the receiving nodes in a different order + to the order in which they were sent. +

+
+ +

Sets the start and stop flags for the <Channel> object used by the cluster. + The default is Channel.DEFAULT which starts all the channel services, such as + sender, receiver, multicast sender and multicast receiver. + The following flags are available today: + + Channel.DEFAULT = Channel.SND_RX_SEQ (1)| Channel.SND_TX_SEQ (2)| Channel.MBR_RX_SEQ (4)| Channel.MBR_TX_SEQ (8); + + To start a channel without multicasting, you would want to use the value Channel.SND_RX_SEQ | Channel.SND_TX_SEQ + that equals to 3. +

+
+ + +

Enable this flag don't forget to disable the channel heartbeat thread. +

+
+ + +

Deprecated since 6.0.0

+

Possible values are true or false
+ Value is inherited from Tomcat 5.5 and has no official meaning. + to configure logging, use the standard tomcat logging configuration. +

+
+ +

Deprecated since 6.0.0

+

+ Value is inherited from Tomcat 5.5 and has no official meaning. + to configure logging, use the standard tomcat logging configuration. +

+
+
+
+
+ +
diff --git a/webapps/docs/config/context.xml b/webapps/docs/config/context.xml new file mode 100644 index 000000000000..20d59e53ec39 --- /dev/null +++ b/webapps/docs/config/context.xml @@ -0,0 +1,947 @@ + + + +]> + + + &project; + + + Craig R. McClanahan + The Context Container + + + + +
+ +
+ +
+ +
+

The description below uses the variable name $CATALINA_BASE to refer the + base directory against which most relative paths are resolved. If you have + not configured Tomcat for multiple instances by setting a CATALINA_BASE + directory, then $CATALINA_BASE will be set to the value of $CATALINA_HOME, + the directory into which you have installed Tomcat.

+
+ +

The Context element represents a web + application, which is run within a particular virtual host. + Each web application is based on a Web Application Archive + (WAR) file, or a corresponding directory containing the corresponding + unpacked contents, as described in the Servlet Specification (version + 2.2 or later). For more information about web application archives, + you can download the + Servlet + Specification, and review the Tomcat + Application Developer's Guide.

+ +

The web application used to process each HTTP request is selected + by Catalina based on matching the longest possible prefix of the + Request URI against the context path of each defined Context. + Once selected, that Context will select an appropriate servlet to + process the incoming request, according to the servlet mappings defined + in the web application deployment descriptor file (which MUST + be located at /WEB-INF/web.xml within the web app's + directory hierarchy).

+ +

You may define as many Context elements as you + wish. Each such Context MUST have a unique context path. In + addition, a Context must be present with a context path equal to + a zero-length string. This Context becomes the default + web application for this virtual host, and is used to process all + requests that do not match any other Context's context path.

+ +

For the current versions of Tomcat, unlike Tomcat 4.x, + it is NOT recommended to place + <Context> elements directly in the server.xml file. This + is because it makes modifying the Context configuration + more invasive since the main conf/server.xml file cannot be + reloaded without restarting Tomcat.

+ +

Context elements may be explicitly defined: +

    +
  • In the $CATALINA_BASE/conf/context.xml file: + the Context element information will be loaded by all webapps.
  • +
  • In the + $CATALINA_BASE/conf/[enginename]/[hostname]/context.xml.default + file: the Context element information will be loaded by all webapps of that + host.
  • +
  • In individual files (with a ".xml" extension) in the + $CATALINA_BASE/conf/[enginename]/[hostname]/ directory. + The name of the file (less the .xml extension) will be used as the + context path. Multi-level context paths may be defined using #, e.g. + foo#bar.xml for a context path of /foo/bar. The + default web application may be defined by using a file called + ROOT.xml.
  • +
  • Only if a context file does not exist for the application in the + $CATALINA_BASE/conf/[enginename]/[hostname]/, in an individual + file at /META-INF/context.xml inside the application files. If + the web application is packaged as a WAR then + /META-INF/context.xml will be copied to + $CATALINA_BASE/conf/[enginename]/[hostname]/ and renamed to + match the application's context path. Once this file exists, it will not be + replaced if a new WAR with a newer /META-INF/context.xml is + placed in the host's appBase.
  • +
  • Inside a Host element in the main + conf/server.xml.
  • +
+

+ +

With the exception of server.xml, files that define Context + elements may only define a single Context element. +

+ +

In addition to explicitly specified Context elements, there are + several techniques by which Context elements can be created automatically + for you. See + Automatic Application Deployment and + User Web Applications + for more information.

+ +
+ + +
+ + + +

All implementations of Context + support the following attributes:

+ + + + +

This value represents the delay in seconds between the + invocation of the backgroundProcess method on this context and + its child containers, including all wrappers. + Child containers will not be invoked if their delay value is not + negative (which would mean they are using their own processing + thread). Setting this to a positive value will cause + a thread to be spawn. After waiting the specified amount of time, + the thread will invoke the backgroundProcess method on this host + and all its child containers. A context will use background + processing to perform session expiration and class monitoring for + reloading. If not specified, the default value for this attribute is + -1, which means the context will rely on the background processing + thread of its parent host.

+
+ + +

Java class name of the implementation to use. This class must + implement the org.apache.catalina.Context interface. + If not specified, the standard value (defined below) will be used.

+
+ + +

Set to true if you want cookies to be used for + session identifier communication if supported by the client (this + is the default). Set to false if you want to disable + the use of cookies for session identifier communication, and rely + only on URL rewriting by the application.

+
+ + +

Set to true if you want calls within this application + to ServletContext.getContext() to successfully return a + request dispatcher for other web applications running on this virtual + host. Set to false (the default) in security + conscious environments, to make getContext() always + return null.

+
+ + +

The Document Base (also known as the Context + Root) directory for this web application, or the pathname + to the web application archive file (if this web application is + being executed directly from the WAR file). You may specify + an absolute pathname for this directory or WAR file, or a pathname + that is relative to the appBase directory of the + owning Host.

+

The value of this field must not be set when the Context is + configured using a META-INF/context.xml file as it will be + inferred by the automatic deployment process.

+
+ + +

Set to true if you want the effective web.xml used for a + web application to be logged (at INFO level) when the application + starts. The effective web.xml is the result of combining the + application's web.xml with any defaults configured by Tomcat and any + web-fragment.xml files and annotations discovered. If not specified, the + default value of false is used.

+
+ + +

Set to true to ignore any settings in both the global + or Host default contexts. By default, settings + from a default context will be used but may be overridden by a setting + the same attribute explicitly for the Context.

+

If a symbolic link is used for docBase then changes to the + symbolic link will only be effective after a Tomcat restart or + by undeploying and redeploying the context. A context reload is not + sufficient.

+
+ + +

Set to true to allow this context to use container + servlets, like the manager servlet. Use of the privileged + attribute will change the context's parent class loader to be the + Server class loader rather than the Shared class + loader. Note that in a default installation, the Common class + loader is used for both the Server and the Shared + class loaders.

+
+ + +

The context path of this web application, which is + matched against the beginning of each request URI to select the + appropriate web application for processing. All of the context paths + within a particular Host must be unique. + If you specify a context path of an empty string (""), you are + defining the default web application for this Host, which + will process all requests not assigned to other Contexts.

+

The value of this field must not be set except when statically + defining a Context in server.xml, as it will be inferred from the + filenames used for either the .xml context file or the docBase.

+
+ + +

Set to true if you want Catalina to monitor classes in + /WEB-INF/classes/ and /WEB-INF/lib for + changes, and automatically reload the web application if a change + is detected. This feature is very useful during application + development, but it requires significant runtime overhead and is + not recommended for use on deployed production applications. That's + why the default setting for this attribute is false. You + can use the Manager web + application, however, to trigger reloads of deployed applications + on demand.

+
+ + +

The domain to be used for all session cookies created for this + context. If set, this overrides any domain set by the web application. + If not set, the value specified by the web application, if any, will be + used.

+
+ + +

The path to be used for all session cookies created for this + context. If set, this overrides any path set by the web application. + If not set, the value specified by the web application will be used, or + the context path used if the web application does not explicitly set + one. To configure all web application to use an empty path (this can be + useful for portlet specification implementations) set this attribute to + / in the global CATALINA_BASE/conf/context.xml + file.

+
+ + +

If the value of this flag is true, the TLD files + XML validation will be namespace-aware. If you turn this flag on, + you should probably also turn tldValidation on. If the + org.apache.catalina.STRICT_SERVLET_COMPLIANCE + system property is set to + true, the default value of this attribute will be + true, else the default value will be false. + Setting this attribute to true will incur a performance + penalty.

+
+ + +

If the value of this flag is true, the TLD files + will be XML validated on context startup. If the + org.apache.catalina.STRICT_SERVLET_COMPLIANCE + system property is set to + true, the default value of this attribute will be + true, else the default value will be false. + Setting this attribute to true will incur a performance + penalty.

+
+ + +

Java class name of the org.apache.catalina.Wrapper + implementation class that will be used for servlets managed by this + Context. If not specified, a standard default value will be used.

+
+ + +

Should the HttpOnly flag be set on session cookies to prevent client + side script from accessing the session ID? Defaults to + true.

+
+ + +

If the value of this flag is true, the validation of + XML files will be namespace-aware. If you turn this flag on, + you should probably also turn xmlValidation on. If + the org.apache.catalina.STRICT_SERVLET_COMPLIANCE + system property is set to + true, the default value of this attribute will be + true, else the default value will be false. + Setting this attribute to true will incur a performance + penalty.

+
+ + +

If the value of this flag is true, the XML files + will be validated on context startup. If the + org.apache.catalina.STRICT_SERVLET_COMPLIANCE + system property is set to + true, the default value of this attribute will be + true, else the default value will be false. + Setting this attribute to true will incur a performance + penalty.

+
+ + +
+ +
+ + + + +

The standard implementation of Context is + org.apache.catalina.core.StandardContext. + It supports the following additional attributes (in addition to the + common attributes listed above):

+ + + + +

This attribute provides a list of external locations from which to + load resources for this context. The list of aliases should be of + the form "/aliasPath1=docBase1,/aliasPath2=docBase2" where + aliasPathN must include a leading '/' and + docBaseN must be an absolute path to either a .war file or + a directory.

+

A resource will be searched for in the first docBaseN + for which aliasPathN is a leading path segment of the + resource. If there is no such alias, then the resource will be searched + in the usual way.

+

Using '/' as an aliasPath is not allowed. Consider using + docBase instead.

+

These external locations will not be emptied if the context + is un-deployed.

+
+ + +

If the value of this flag is true, symlinks will be + allowed inside the web application, pointing to resources outside the + web application base path. If not specified, the default value + of the flag is false.

+

NOTE: This flag MUST NOT be set to true on the Windows platform + (or any other OS which does not have a case sensitive filesystem), + as it will disable case sensitivity checks, allowing JSP source code + disclosure, among other security problems.

+
+ + +

If true, the Tomcat classloader will take extra measures to avoid + JAR file locking when resources are accessed inside JARs through URLs. + This will impact startup time of applications, but could prove to be useful + on platforms or configurations where file locking can occur. + If not specified, the default value is false.

+
+ + +

If true, Tomcat will prevent any file locking. + This will significantly impact startup time of applications, + but allows full webapp hot deploy and undeploy on platforms + or configurations where file locking can occur. + If not specified, the default value is false.

+ +

Please note that setting this to true has some side effects, + including the disabling of JSP reloading in a running server: see + Bugzilla 37668. +

+ +

+ Please note that setting this flag to true in applications that are + outside the appBase for the Host (the webapps directory + by default) will cause the application to be + deleted on Tomcat shutdown. You probably don't want to + do this, so think twice before setting antiResourceLocking=true on a webapp + that's outside the appBase for its Host. +

+
+ + +

Maximum size of the static resource cache in kilobytes. + If not specified, the default value is 10240 + (10 megabytes).

+
+ + +

Maximum size of the static resource that will be placed in the cache. + If not specified, the default value is 512 + (512 kilobytes). If this value is greater than + cacheMaxSize/20 it will be reduced to + cacheMaxSize/20.

+
+ + +

Amount of time in milliseconds between cache entries revalidation. + If not specified, the default value is 5000 + (5 seconds).

+
+ + +

If the value of this flag is true, the cache for static + resources will be used. If not specified, the default value + of the flag is true.

+
+ + +

If true, Tomcat attempts to null out any static or final + fields from loaded classes when a web application is stopped as a work + around for apparent garbage collection bugs and application coding + errors. There have been some issues reported with log4j when this + is true. Applications without memory leaks using recent + JVMs should operate correctly with this attribute set to + false. If not specified, the default value of + false will be used.

+
+ + +

If true, Tomcat attempts to terminate threads that have + been started by the web application. Stopping threads is performed via + the deprecated (for good reason) Thread.stop() method and + is likely to result in instability. As such, enabling this should be + viewed as an option of last resort in a development environment and is + not recommended in a production environment. If not specified, the + default value of false will be used.

+
+ + +

If true, Tomcat attempts to terminate + java.util.Timer threads that have been started by the web + application. Unlike standard threads, timer threads can be stopped + safely although there may still be side-effects for the application. If + not specified, the default value of false will be used.

+
+ + +

If true, Tomcat attempts to clear any ThreadLocal + objects that are instances of classes loaded by this class loader. + Failure to remove any such objects will result in a memory leak on web + application stop, undeploy or reload. If not specified, the default + value of false will be used since the clearing of the + ThreadLocal objects is not performed in a thread-safe manner.

+
+ + +

Whether the context should process TLDs on startup. The default + is true. The false setting is intended for special cases + that know in advance TLDs are not part of the webapp.

+
+ + +

If the value of this flag is true, the bytes output to + System.out and System.err by the web application will be redirected to + the web application logger. If not specified, the default value + of the flag is false.

+
+ + +

Number of ms that the container will wait for servlets to unload. + If not specified, the default value is 2000 ms.

+
+ + +

If true, Tomcat will unpack all compressed web applications before + running them. + If not specified, the default value is true.

+
+ + +

Set to true (the default) to have Catalina enable a + JNDI InitialContext for this web application that is + compatible with Java2 Enterprise Edition (J2EE) platform + conventions.

+
+ + +

Pathname to a scratch directory to be provided by this Context + for temporary read-write use by servlets within the associated web + application. This directory will be made visible to servlets in the + web application by a servlet context attribute (of type + java.io.File) named + javax.servlet.context.tempdir as described in the + Servlet Specification. If not specified, a suitable directory + underneath $CATALINA_BASE/work will be provided.

+
+ +
+ +
+ + +
+ + +
+ +

You can nest at most one instance of the following utility components + by nesting a corresponding element inside your Context + element:

+
    +
  • Loader - + Configure the web application class loader that will be used to load + servlet and bean classes for this web application. Normally, the + default configuration of the class loader will be sufficient.
  • +
  • Manager - + Configure the session manager that will be used to create, destroy, + and persist HTTP sessions for this web application. Normally, the + default configuration of the session manager will be sufficient.
  • +
  • Realm - + Configure a realm that will allow its + database of users, and their associated roles, to be utilized solely + for this particular web application. If not specified, this web + application will utilize the Realm associated with the owning + Host or Engine.
  • +
  • Resources - + Configure the resource manager that will be used to access the static + resources associated with this web application. Normally, the + default configuration of the resource manager will be sufficient.
  • +
  • WatchedResource - The auto deployer will monitor the + specified static resource of the web application for updates, and will + reload the web application if is is updated. The content of this element + must be a string.
  • +
+ +
+ + +
+ + + + +

A context is associated with the + org.apache.catalina.core.ContainerBase.[enginename].[hostname].[path] + log category. Note that the brackets are actually part of the name, don't omit them.

+ +
+ + + + +

When you run a web server, one of the output files normally generated + is an access log, which generates one line of information for + each request processed by the server, in a standard format. Catalina + includes an optional Valve implementation that + can create access logs in the same standard format created by web servers, + or in any number of custom formats.

+ +

You can ask Catalina to create an access log for all requests + processed by an Engine, + Host, or Context + by nesting a Valve element like this:

+ + +<Context path="/examples" ...> + ... + <Valve className="org.apache.catalina.valves.AccessLogValve" + prefix="localhost_access_log." suffix=".txt" + pattern="common"/> + ... +</Context> + + +

See Access Log Valve + for more information on the configuration attributes that are + supported.

+ +
+ + + + +

If you use the standard Context implementation, + the following configuration steps occur automatically when Catalina + is started, or whenever this web application is reloaded. No special + configuration is required to enable this feature.

+ +
    +
  • If you have not declared your own Loader + element, a standard web application class loader will be configured. +
  • +
  • If you have not declared your own Manager + element, a standard session manager will be configured.
  • +
  • If you have not declared your own Resources + element, a standard resources manager will be configured.
  • +
  • The web application properties listed in conf/web.xml + will be processed as defaults for this web application. This is used + to establish default mappings (such as mapping the *.jsp + extension to the corresponding JSP servlet), and other standard + features that apply to all web applications.
  • +
  • The web application properties listed in the + /WEB-INF/web.xml resource for this web application + will be processed (if this resource exists).
  • +
  • If your web application has specified security constraints that might + require user authentication, an appropriate Authenticator that + implements the login method you have selected will be configured.
  • +
+ +
+ + + + +

You can configure named values that will be made visible to the + web application as servlet context initialization parameters by nesting + <Parameter> elements inside this element. For + example, you can create an initialization parameter like this:

+ +<Context ...> + ... + <Parameter name="companyName" value="My Company, Incorporated" + override="false"/> + ... +</Context> + + +

This is equivalent to the inclusion of the following element in the + web application deployment descriptor (/WEB-INF/web.xml): +

+ +<context-param> + <param-name>companyName</param-name> + <param-value>My Company, Incorporated</param-value> +</context-param> + +

but does not require modification of the deployment descriptor + to customize this value.

+ +

The valid attributes for a <Parameter> element + are as follows:

+ + + + +

Optional, human-readable description of this context + initialization parameter.

+
+ + +

The name of the context initialization parameter to be created.

+
+ + +

Set this to false if you do not want + a <context-param> for the same parameter name, + found in the web application deployment descriptor, to override the + value specified here. By default, overrides are allowed.

+
+ + +

The parameter value that will be presented to the application + when requested by calling + ServletContext.getInitParameter().

+
+ +
+ +
+ + + + +

You can configure named values that will be made visible to the + web application as environment entry resources, by nesting + <Environment> entries inside this element. For + example, you can create an environment entry like this:

+ +<Context ...> + ... + <Environment name="maxExemptions" value="10" + type="java.lang.Integer" override="false"/> + ... +</Context> + + +

This is equivalent to the inclusion of the following element in the + web application deployment descriptor (/WEB-INF/web.xml): +

+ +<env-entry> + <env-entry-name>maxExemptions</param-name> + <env-entry-value>10</env-entry-value> + <env-entry-type>java.lang.Integer</env-entry-type> +</env-entry> + +

but does not require modification of the deployment descriptor + to customize this value.

+ +

The valid attributes for an <Environment> element + are as follows:

+ + + + +

Optional, human-readable description of this environment entry.

+
+ + +

The name of the environment entry to be created, relative to the + java:comp/env context.

+
+ + +

Set this to false if you do not want + an <env-entry> for the same environment entry name, + found in the web application deployment descriptor, to override the + value specified here. By default, overrides are allowed.

+
+ + +

The fully qualified Java class name expected by the web application + for this environment entry. Must be one of the legal values for + <env-entry-type> in the web application deployment + descriptor: java.lang.Boolean, + java.lang.Byte, java.lang.Character, + java.lang.Double, java.lang.Float, + java.lang.Integer, java.lang.Long, + java.lang.Short, or java.lang.String.

+
+ + +

The parameter value that will be presented to the application + when requested from the JNDI context. This value must be convertable + to the Java type defined by the type attribute.

+
+ +
+ +
+ + + + +

If you have implemented a Java object that needs to know when this + Context is started or stopped, you can declare it by + nesting a Listener element inside this element. The + class name you specify must implement the + org.apache.catalina.LifecycleListener interface, and + the class must be packaged in a jar and placed in the + $CATALINA_HOME/lib directory. + It will be notified about the occurrence of the corresponding + lifecycle events. Configuration of such a listener looks like this:

+ + +<Context path="/examples" ...> + ... + <Listener className="com.mycompany.mypackage.MyListener" ... > + ... +</Context> + + +

Note that a Listener can have any number of additional properties + that may be configured from this element. Attribute names are matched + to corresponding JavaBean property names using the standard property + method naming patterns.

+ +
+ + + + +

You can ask Catalina to check the IP address, or host name, on every + incoming request directed to the surrounding + Engine, Host, or + Context element. The remote address or name + will be checked against a configured list of "accept" and/or "deny" + filters, which are defined using the Regular Expression syntax supported + by the Jakarta Regexp + regular expression library. Requests that come from locations that are + not accepted will be rejected with an HTTP "Forbidden" error. + Example filter declarations:

+ + +<Context path="/examples" ...> + ... + <Valve className="org.apache.catalina.valves.RemoteHostValve" + allow="*.mycompany.com,www.yourcompany.com"/> + <Valve className="org.apache.catalina.valves.RemoteAddrValve" + deny="192.168.1.*"/> + ... +</Context> + + +

See Remote Address Filter + and Remote Host Filter for + more information about the configuration options that are supported.

+ +
+ + + + +

You can declare the characteristics of the resource + to be returned for JNDI lookups of <resource-ref> and + <resource-env-ref> elements in the web application + deployment descriptor. You MUST also define + the needed resource parameters as attributes of the Resource + element, to configure the object factory to be used (if not known to Tomcat + already), and the properties used to configure that object factory.

+ +

For example, you can create a resource definition like this:

+ +<Context ...> + ... + <Resource name="jdbc/EmployeeDB" auth="Container" + type="javax.sql.DataSource" + description="Employees Database for HR Applications"/> + ... +</Context> + + +

This is equivalent to the inclusion of the following element in the + web application deployment descriptor (/WEB-INF/web.xml):

+ +<resource-ref> + <description>Employees Database for HR Applications</description> + <res-ref-name>jdbc/EmployeeDB</res-ref-name> + <res-ref-type>javax.sql.DataSource</res-ref-type> + <res-auth>Container</res-auth> +</resource-ref> + + +

but does not require modification of the deployment + descriptor to customize this value.

+ +

The valid attributes for a <Resource> element + are as follows:

+ + + + +

Specify whether the web Application code signs on to the + corresponding resource manager programatically, or whether the + Container will sign on to the resource manager on behalf of the + application. The value of this attribute must be + Application or Container. This + attribute is required if the web application + will use a <resource-ref> element in the web + application deployment descriptor, but is optional if the + application uses a <resource-env-ref> instead.

+
+ + +

Optional, human-readable description of this resource.

+
+ + +

The name of the resource to be created, relative to the + java:comp/env context.

+
+ + +

Specify whether connections obtained through this resource + manager can be shared. The value of this attribute must be + Shareable or Unshareable. By default, + connections are assumed to be shareable.

+
+ + +

The fully qualified Java class name expected by the web + application when it performs a lookup for this resource.

+
+ +
+ + +
+ + + + +

This element is used to create a link to a global JNDI resource. Doing + a JNDI lookup on the link name will then return the linked global + resource.

+ +

For example, you can create a resource link like this:

+ +<Context ...> + ... + <ResourceLink name="linkToGlobalResource" + global="simpleValue" + type="java.lang.Integer" + ... +</Context> + + +

The valid attributes for a <ResourceLink> element + are as follows:

+ + + + +

The name of the linked global resource in the + global JNDI context.

+
+ + +

The name of the resource link to be created, relative to the + java:comp/env context.

+
+ + +

The fully qualified Java class name expected by the web + application when it performs a lookup for this resource link.

+
+ +
+ +
+ + + +

You can declare the characteristics of the UserTransaction + to be returned for JNDI lookup for java:comp/UserTransaction. + You MUST define an object factory class to instantiate + this object as well as the needed resource parameters as attributes of the + Transaction + element, and the properties used to configure that object factory.

+ +

The valid attributes for the <Transaction> element + are as follows:

+ + + + +

The class name for the JNDI object factory.

+
+ +
+ +
+ +
+ + + + + +
diff --git a/webapps/docs/config/engine.xml b/webapps/docs/config/engine.xml new file mode 100644 index 000000000000..687006ca1313 --- /dev/null +++ b/webapps/docs/config/engine.xml @@ -0,0 +1,258 @@ + + + +]> + + + &project; + + + Craig R. McClanahan + The Engine Container + + + + +
+ +
+ +
+ +

The Engine element represents the entire request + processing machinery associated with a particular Catalina + Service. It receives and processes + all requests from one or more Connectors, + and returns the completed response to the Connector for ultimate + transmission back to the client.

+ +

Exactly one Engine element MUST be nested inside + a Service element, following all of the + corresponding Connector elements associated with this Service.

+ +
+ + +
+ + + +

All implementations of Engine + support the following attributes:

+ + + + +

This value represents the delay in seconds between the + invocation of the backgroundProcess method on this engine and + its child containers, including all hosts and contexts. + Child containers will not be invoked if their delay value is not + negative (which would mean they are using their own processing + thread). Setting this to a positive value will cause + a thread to be spawn. After waiting the specified amount of time, + the thread will invoke the backgroundProcess method on this engine + and all its child containers. If not specified, the default value for + this attribute is 10, which represent a 10 seconds delay.

+
+ + +

Java class name of the implementation to use. This class must + implement the org.apache.catalina.Engine interface. + If not specified, the standard value (defined below) will be used.

+
+ + +

The default host name, which identifies the + Host that will process requests directed + to host names on this server, but which are not configured in + this configuration file. This name MUST match the name + attributes of one of the Host elements + nested immediately inside.

+
+ + +

Identifier which must be used in load balancing scenarios to enable + session affinity. The identifier, which must be unique across all + Tomcat servers which participate in the cluster, will be appended to + the generated session identifier, therefore allowing the front end + proxy to always forward a particular session to the same Tomcat + instance.

+
+ + +

Logical name of this Engine, used in log and error messages. When + using multiple Service elements in the same + Server, each Engine MUST be assigned a unique + name.

+
+ +
+ +
+ + + + +

The standard implementation of Engine is + org.apache.catalina.core.StandardEngine. + It supports the following additional attributes (in addition to the + common attributes listed above):

+ + + + + +
+ + +
+ + +
+ +

You can nest one or more Host elements inside + this Engine element, each representing a different virtual + host associated with this server. At least one Host + is required, and one of the nested Hosts MUST + have a name that matches the name specified for the + defaultHost attribute, listed above.

+ +

You can nest at most one instance of the following utility components + by nesting a corresponding element inside your Engine + element:

+
    +
  • Realm - + Configure a realm that will allow its + database of users, and their associated roles, to be shared across all + Hosts and Contexts + nested inside this Engine, unless overridden by a + Realm configuration at a lower level.
  • +
+ +
+ + +
+ + + + +

An engine is associated with the + org.apache.catalina.core.ContainerBase.[enginename] + log category. Note that the brackets are actually part of the name, + don't omit them.

+ +
+ + + + +

When you run a web server, one of the output files normally generated + is an access log, which generates one line of information for + each request processed by the server, in a standard format. Catalina + includes an optional Valve implementation that + can create access logs in the same standard format created by web servers, + or in any number of custom formats.

+ +

You can ask Catalina to create an access log for all requests + processed by an Engine, + Host, or Context + by nesting a Valve element like this:

+ + +<Engine name="Standalone" ...> + ... + <Valve className="org.apache.catalina.valves.AccessLogValve" + prefix="catalina_access_log." suffix=".txt" + pattern="common"/> + ... +</Engine> + + +

See Access Log Valve + for more information on the configuration attributes that are + supported.

+ +
+ + + + +

If you have implemented a Java object that needs to know when this + Engine is started or stopped, you can declare it by + nesting a Listener element inside this element. The + class name you specify must implement the + org.apache.catalina.LifecycleListener interface, and + it will be notified about the occurrence of the corresponding + lifecycle events. Configuration of such a listener looks like this:

+ + +<Engine name="Standalone" ...> + ... + <Listener className="com.mycompany.mypackage.MyListener" ... > + ... +</Engine> + + +

Note that a Listener can have any number of additional properties + that may be configured from this element. Attribute names are matched + to corresponding JavaBean property names using the standard property + method naming patterns.

+ +
+ + + + +

You can ask Catalina to check the IP address, or host name, on every + incoming request directed to the surrounding + Engine, Host, or + Context element. The remote address or name + will be checked against a configured list of "accept" and/or "deny" + filters, which are defined using the Regular Expression syntax supported + by the Jakarta Regexp + regular expression library. Requests that come from locations that are + not accepted will be rejected with an HTTP "Forbidden" error. + Example filter declarations:

+ + +<Engine name="Standalone" ...> + ... + <Valve className="org.apache.catalina.valves.RemoteHostValve" + allow="*.mycompany.com,www.yourcompany.com"/> + <Valve className="org.apache.catalina.valves.RemoteAddrValve" + deny="192.168.1.*"/> + ... +</Engine> + + +

See Remote Address Filter + and Remote Host Filter for + more information about the configuration options that are supported.

+ +
+ + +
+ + + + + +
diff --git a/webapps/docs/config/executor.xml b/webapps/docs/config/executor.xml new file mode 100644 index 000000000000..41fe73747f7c --- /dev/null +++ b/webapps/docs/config/executor.xml @@ -0,0 +1,118 @@ + + + +]> + + + &project; + + + Filip Hanik + The Executor (thread pool) + + + + +
+ +
+ +
+ +

The Executor represents a thread pool that can be shared + between components in Tomcat. Historically there has been a thread pool per + connector created but this allows you to share a thread pool, between (primarly) connector + but also other components when those get configured to support executors

+ + +

The executor has to implement the org.apache.catalina.Executor interface.

+ +

The executor is a nested element to the Service element. + And in order for it to be picked up by the connectors, the Executor element has to appear + prior to the Connector element in server.xml

+
+ + +
+ + + +

All implementations of Executor + support the following attributes:

+ + + + +

The class of the implementation. The implementation has to implement the + org.apache.catalina.Executor interface. + This interface ensures that the object can be referenced through its name attribute + and that implements Lifecycle, so that it can be started and stopped with the container. + The default value for the className is org.apache.catalina.core.StandardThreadExecutor

+
+ + +

The name used to reference this pool in other places in server.xml. + The name is required and must be unique.

+
+ +
+ +
+ + + +

+ The default implementation supports the following attributes:

+ + + + +

(int) The thread priority for threads in the executor, the default is Thread.NORM_PRIORITY

+
+ +

(boolean) Whether the threads should be daemon threads or not, the default is true

+
+ +

(String) The name prefix for each thread created by the executor. + The thread name for an individual thread will be namePrefix+threadNumber

+
+ +

(int) The max number of active threads in this pool, default is 200

+
+ +

(int) The minimum number of threads always kept alive, default is 25

+
+ +

(int) The number of milliseconds before an idle thread shutsdown, unless the number of active threads are less + or equal to minSpareThreads. Default value is 60000(1 minute)

+
+ +

(boolean) Whether minSpareThreads should be started when starting the Executor or not, + the default is false

+
+
+ + +
+
+ + + + +
diff --git a/webapps/docs/config/filter.xml b/webapps/docs/config/filter.xml new file mode 100644 index 000000000000..5cc11d861911 --- /dev/null +++ b/webapps/docs/config/filter.xml @@ -0,0 +1,1123 @@ + + + +]> + + + &project; + + + Container Provided Filters + + + + +
+ +
+ +
+ +

Tomcat provides a number of Filters which may be + configured for use with all web applications using + $CATALINA_BASE/conf/web.xml or may be configured for individual + web applications by configuring them in the application's + WEB-INF/web.xml. Each filter is described below.

+ +
+

This description uses the variable name $CATALINA_BASE to refer the + base directory against which most relative paths are resolved. If you have + not configured Tomcat for multiple instances by setting a CATALINA_BASE + directory, then $CATALINA_BASE will be set to the value of $CATALINA_HOME, + the directory into which you have installed Tomcat.

+
+ +
+ + +
+ + + +

The HTTP specification is clear that if no character set is specified for + media sub-types of the "text" media type, the ISO-8859-1 character set must + be used. However, browsers may attempt to auto-detect the character set. + This may be exploited by an attacker to perform an XSS attack. Internet + Explorer has this behaviour by default. Other browsers have an option to + enable it.

+ +

This filter prevents the attack by explicitly setting a character set. + Unless the provided character set is explicitly overridden by the user the + browser will adhere to the explicitly set character set, thus preventing the + XSS attack.

+ +
+ + + +

The filter class name for the Add Default Character Set Filter is + org.apache.catalina.filters.AddDefaultCharsetFilter + .

+ +
+ + + +

The Add Default Character Set Filter supports the following initialization + parameters:

+ + + + +

Name of the character set which should be set, if no other character set + was set explicitly by a Servlet. This parameter has two special values + default and system. A value of system + uses the JVM wide default character set, which is usually set by locale. + A value of default will use ISO-8859-1.

+
+ +
+ +
+ +
+ + +
+ + + +

This filter provides basic CSRF protection for a web application. The + filter assumes that it is mapped to /* and that all URLs + returned to the client are encoded via a call to + HttpServletResponse#encodeRedirectURL(String) or + HttpServletResponse#encodeURL(String).

+ +

This filter prevents CSRF by generating a nonce and storing it in the + session. URLs are also encoded with the same nonce. When the next request is + received the nonce in the request is compared to the nonce in the session + and only if they are the same is the request allowed to continue.

+ +
+ + + +

The filter class name for the CSRF Prevention Filter is + org.apache.catalina.filters.CsrfPreventionFilter + .

+ +
+ + + +

The CSRF Prevention Filter supports the following initialisation + parameters:

+ + + + +

A comma separated list of URLs that will not be tested for the + presence of a valid nonce. They are used to provide a way to navigate + back to a protected application after having navigated away from it. + Entry points will be limited to HTTP GET requests and should not trigger + any security sensitive actions.

+
+ + +

The number of previously issued nonces that will be cached on a LRU + basis to support parallel requests, limited use of the refresh and back + in the browser and similar behaviors that may result in the submission + of a previous nonce rather than the current one. If not set, the default + value of 5 will be used.

+
+ + +

The name of the class to use to generate nonces. The class must be an + instance of java.util.Random. If not set, the default value + of java.security.SecureRandom will be used.

+
+ +
+ +
+ +
+ +
+ + + +

+ ExpiresFilter is a Java Servlet API port of Apache + mod_expires. + This filter controls the setting of the Expires HTTP header and the + max-age directive of the Cache-Control HTTP header in + server responses. The expiration date can set to be relative to either the + time the source file was last modified, or to the time of the client access. +

+ +

+ These HTTP headers are an instruction to the client about the document's + validity and persistence. If cached, the document may be fetched from the + cache rather than from the source until this time has passed. After that, the + cache copy is considered "expired" and invalid, and a new copy must + be obtained from the source. +

+

+ To modify Cache-Control directives other than max-age (see + RFC + 2616 section 14.9), you can use other servlet filters or Apache Httpd + mod_headers module. +

+ +
+ + +

+ Basic configuration to add 'Expires' and 'Cache-Control: max-age=' + headers to images, css and javascript. +

+ + +<filter> + <filter-name>ExpiresFilter</filter-name> + <filter-class>org.apache.catalina.filters.ExpiresFilter</filter-class> + <init-param> + <param-name>ExpiresByType image</param-name> + <param-value>access plus 10 minutes</param-value> + </init-param> + <init-param> + <param-name>ExpiresByType text/css</param-name> + <param-value>access plus 10 minutes</param-value> + </init-param> + <init-param> + <param-name>ExpiresByType text/javascript</param-name> + <param-value>access plus 10 minutes</param-value> + </init-param> +</filter> +... +<filter-mapping> + <filter-name>ExpiresFilter</filter-name> + <url-pattern>/*</url-pattern> + <dispatcher>REQUEST</dispatcher> +</filter-mapping> + + + +
+ + +

+ The ExpiresDefault and ExpiresByType directives can also be + defined in a more readable syntax of the form: +

+ + +<init-param> + <param-name>ExpiresDefault</param-name> + <param-value><base> [plus] {<num> <type>}*</param-value> +</init-param> + +<init-param> + <param-name>ExpiresByType type</param-name> + <param-value><base> [plus] {<num> <type>}*</param-value> +</init-param> + +<init-param> + <param-name>ExpiresByType type;encoding</param-name> + <param-value><base> [plus] {<num> <type>}*</param-value> +</init-param> + +

+ where <base> is one of: +

    +
  • access
  • +
  • now (equivalent to 'access')
  • +
  • modification
  • +
+

+

+ The plus keyword is optional. <num> should be an + integer value (acceptable to Integer.parseInt()), and + <type> is one of: +

    +
  • years
  • +
  • months
  • +
  • weeks
  • +
  • days
  • +
  • hours
  • +
  • minutes
  • +
  • seconds
  • +
+ For example, any of the following directives can be used to make documents + expire 1 month after being accessed, by default: +

+ + +<init-param> + <param-name>ExpiresDefault</param-name> + <param-value>access plus 1 month</param-value> +</init-param> + +<init-param> + <param-name>ExpiresDefault</param-name> + <param-value>access plus 4 weeks</param-value> +</init-param> + +<init-param> + <param-name>ExpiresDefault</param-name> + <param-value>access plus 30 days</param-value> +</init-param> + +

+The expiry time can be fine-tuned by adding several ' +<num> <type>' clauses: +

+ + +<init-param> + <param-name>ExpiresByType text/html</param-name> + <param-value>access plus 1 month 15 days 2 hours</param-value> +</init-param> + +<init-param> + <param-name>ExpiresByType image/gif</param-name> + <param-value>modification plus 5 hours 3 minutes</param-value> +</init-param> + +

+ Note that if you use a modification date based setting, the Expires + header will not be added to content that does not come from + a file on disk. This is due to the fact that there is no modification time + for such content. +

+
+ + +

+ A response is eligible to be enriched by ExpiresFilter if : +

    +
  1. no expiration header is defined (Expires header or the + max-age directive of the Cache-Control header),
  2. +
  3. the response status code is not excluded by the directive + ExpiresExcludedResponseStatusCodes,
  4. +
  5. the Content-Type of the response matches one of the types + defined the in ExpiresByType directives or the + ExpiresDefault directive is defined.
  6. +
+

+

+ Note : If Cache-Control header contains other directives than + max-age, they are concatenated with the max-age directive + that is added by the ExpiresFilter. +

+ +
+ + +

+ The expiration configuration if elected according to the following algorithm: +

    +
  1. ExpiresByType matching the exact content-type returned by + HttpServletResponse.getContentType() possibly including the charset + (e.g. 'text/xml;charset=UTF-8'),
  2. +
  3. ExpiresByType matching the content-type without the charset if + HttpServletResponse.getContentType() contains a charset (e.g. ' + text/xml;charset=UTF-8' -> 'text/xml'),
  4. +
  5. ExpiresByType matching the major type (e.g. substring before + '/') of HttpServletResponse.getContentType() + (e.g. 'text/xml;charset=UTF-8' -> 'text + '),
  6. +
  7. ExpiresDefault
  8. +
+

+
+ + + +

The filter class name for the Expires Filter is + org.apache.catalina.filters.ExpiresFilter + .

+ +
+ + + +

The Expires Filter supports the following + initialisation parameters:

+ + + + +

+ This directive defines the http response status codes for which the + ExpiresFilter will not generate expiration headers. By default, the + 304 status code ("Not modified") is skipped. The + value is a comma separated list of http status codes. +

+

+ This directive is useful to ease usage of ExpiresDefault directive. + Indeed, the behavior of 304 Not modified (which does specify a + Content-Type header) combined with Expires and + Cache-Control:max-age= headers can be unnecessarily tricky to + understand. +

+

+ Sample : exclude response status codes 302, 500 and 503 +

+ + +<init-param> + <param-name>ExpiresExcludedResponseStatusCodes</param-name> + <param-value>302, 500, 503</param-value> +</init-param> + +
+ + +

+ This directive defines the value of the Expires header and the + max-age directive of the Cache-Control header generated for + documents of the specified type (e.g., text/html). The second + argument sets the number of seconds that will be added to a base time to + construct the expiration date. The Cache-Control: max-age is + calculated by subtracting the request time from the expiration date and + expressing the result in seconds. +

+

+ The base time is either the last modification time of the file, or the time + of the client's access to the document. Which should be used is + specified by the <code> field; M means that the + file's last modification time should be used as the base time, and + A means the client's access time should be used. The duration + is expressed in seconds. A2592000 stands for + access plus 30 days in alternate syntax. +

+

+ The difference in effect is subtle. If M (modification in + alternate syntax) is used, all current copies of the document in all caches + will expire at the same time, which can be good for something like a weekly + notice that's always found at the same URL. If A ( + access or now in alternate syntax) is used, the date of + expiration is different for each client; this can be good for image files + that don't change very often, particularly for a set of related + documents that all refer to the same images (i.e., the images will be + accessed repeatedly within a relatively short timespan). +

+

+ Note: When the content type includes a charset (e.g. + 'ExpiresByType text/xml;charset=utf-8'), Tomcat removes blank chars + between the ';' and the 'charset' keyword. Due to this, + configuration of an expiration with a charset must not include + such a space character. +

+

+ Sample: +

+ + +<init-param> + <param-name>ExpiresByType text/html</param-name> + <param-value>access plus 1 month 15 days 2 hours</param-value> +</init-param> + +<init-param> + <!-- 2592000 seconds = 30 days --> + <param-name>ExpiresByType image/gif</param-name> + <param-value>A2592000</param-value> +</init-param> + +

+ It overrides, for the specified MIME type only, any + expiration date set by the ExpiresDefault directive. +

+

+ You can also specify the expiration time calculation using an alternate + syntax, described earlier in this document. +

+
+ + +

+ This directive sets the default algorithm for calculating the + expiration time for all documents in the affected realm. It can be + overridden on a type-by-type basis by the ExpiresByType directive. See the + description of that directive for details about the syntax of the + argument, and the "alternate syntax" + description as well. +

+
+
+ +
+ + +

+ To troubleshoot, enable logging on the + org.apache.catalina.filters.ExpiresFilter. +

+

+ Extract of logging.properties +

+ + +org.apache.catalina.filters.ExpiresFilter.level = FINE + +

+ Sample of initialization log message: +

+ + +Mar 26, 2010 2:01:41 PM org.apache.catalina.filters.ExpiresFilter init +FINE: Filter initialized with configuration ExpiresFilter[ + excludedResponseStatusCode=[304], + default=null, + byType={ + image=ExpiresConfiguration[startingPoint=ACCESS_TIME, duration=[10 MINUTE]], + text/css=ExpiresConfiguration[startingPoint=ACCESS_TIME, duration=[10 MINUTE]], + text/javascript=ExpiresConfiguration[startingPoint=ACCESS_TIME, duration=[10 MINUTE]]}] + +

+ Sample of per-request log message where ExpiresFilter adds an + expiration date: +

+ + +Mar 26, 2010 2:09:47 PM org.apache.catalina.filters.ExpiresFilter onBeforeWriteResponseBody +FINE: Request "/tomcat.gif" with response status "200" content-type "image/gif", set expiration date 3/26/10 2:19 PM + +

+ Sample of per-request log message where ExpiresFilter does not add + an expiration date: +

+ + +Mar 26, 2010 2:10:27 PM org.apache.catalina.filters.ExpiresFilter onBeforeWriteResponseBody +FINE: Request "/docs/config/manager.html" with response status "200" content-type "text/html", no expiration configured + +
+ +
+ +
+ + + +

The Remote Address Filter allows you to compare the + IP address of the client that submitted this request against one or more + regular expressions, and either allow the request to continue + or refuse to process the request from this client.

+ +

The syntax for regular expressions is different than that for + 'standard' wildcard matching. Tomcat uses the java.util.regex + package. Please consult the Java documentation for details of the + expressions supported.

+ +
+ + + +

The filter class name for the Remote Address Filter is + org.apache.catalina.filters.RemoteAddrFilter + .

+ +
+ + + +

The Remote Address Filter supports the following + initialisation parameters:

+ + + + +

A comma-separated list of regular expression patterns + that the remote client's IP address is compared to. If this attribute + is specified, the remote address MUST match for this request to be + accepted. If this attribute is not specified, all requests will be + accepted UNLESS the remote address matches a deny + pattern.

+
+ + +

A comma-separated list of regular expression patterns + that the remote client's IP address is compared to. If this attribute + is specified, the remote address MUST NOT match for this request to be + accepted. If this attribute is not specified, request acceptance is + governed solely by the accept attribute.

+
+ +
+ +
+ +
+ + +
+ + + +

The Remote Host Filter allows you to compare the + hostname of the client that submitted this request against one or more + regular expressions, and either allow the request to continue + or refuse to process the request from this client.

+ +

The syntax for regular expressions is different than that for + 'standard' wildcard matching. Tomcat uses the java.util.regex + package. Please consult the Java documentation for details of the + expressions supported.

+ +
+ + + +

The filter class name for the Remote Address Filter is + org.apache.catalina.filters.RemoteHostFilter + .

+ +
+ + + +

The Remote Host Filter supports the following + initialisation parameters:

+ + + + +

A comma-separated list of regular expression patterns + that the remote client's hostname is compared to. If this attribute + is specified, the remote hostname MUST match for this request to be + accepted. If this attribute is not specified, all requests will be + accepted UNLESS the remote hostname matches a deny + pattern.

+
+ + +

A comma-separated list of regular expression patterns + that the remote client's hostname is compared to. If this attribute + is specified, the remote hostname MUST NOT match for this request to be + accepted. If this attribute is not specified, request acceptance is + governed solely by the accept attribute.

+
+ +
+ +
+ +
+ + +
+ + + +

Tomcat port of + mod_remoteip, + this filter replaces the apparent client remote IP address and hostname for + the request with the IP address list presented by a proxy or a load balancer + via a request headers (e.g. "X-Forwarded-For").

+ +

Another feature of this filter is to replace the apparent scheme + (http/https), server port and request.secure with the scheme presented + by a proxy or a load balancer via a request header + (e.g. "X-Forwarded-Proto").

+ +

If used in conjunction with Remote Address/Host filters then this filter + should be defined first to ensure that the correct client IP address is + presented to the Remote Address/Host filters.

+ +
+ + + +

The filter class name for the Remote IP Filter is + org.apache.catalina.filters.RemoteIpFilter + .

+ +
+ + +

+ The filter will process the x-forwarded-for http header. +

+ + <filter> + <filter-name>RemoteIpFilter</filter-name> + <filter-class>org.apache.catalina.filters.RemoteIpFilter</filter-class> + </filter> + + <filter-mapping> + <filter-name>RemoteIpFilter</filter-name> + <url-pattern>/*</url-pattern> + <dispatcher>REQUEST</dispatcher> + </filter-mapping> + +
+ + + +

+ The filter will process x-forwarded-for and + x-forwarded-proto http headers. Expected value for the + x-forwarded-proto header in case of SSL connections is + https (case insensitive).

+ + <filter> + <filter-name>RemoteIpFilter</filter-name> + <filter-class>org.apache.catalina.filters.RemoteIpFilter</filter-class> + <init-param> + <param-name>protocolHeader</param-name> + <param-value>x-forwarded-proto</param-value> + </init-param> + </filter> + + <filter-mapping> + <filter-name>RemoteIpFilter</filter-name> + <url-pattern>/*</url-pattern> + <dispatcher>REQUEST</dispatcher> + </filter-mapping> + +
+ + +

RemoteIpFilter configuration:

+ + <filter> + <filter-name>RemoteIpFilter</filter-name> + <filter-class>org.apache.catalina.filters.RemoteIpFilter</filter-class> + <init-param> + <param-name>allowedInternalProxies</param-name> + <param-value>192\.168\.0\.10, 192\.168\.0\.11</param-value> + </init-param> + <init-param> + <param-name>remoteIpHeader</param-name> + <param-value>x-forwarded-for</param-value> + </init-param> + <init-param> + <param-name>remoteIpProxiesHeader</param-name> + <param-value>x-forwarded-by</param-value> + </init-param> + <init-param> + <param-name>protocolHeader</param-name> + <param-value>x-forwarded-proto</param-value> + </init-param> + </filter> + +

Request values: + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
PropertyValue Before RemoteIpFilterValue After RemoteIpFilter
request.remoteAddr 192.168.0.10 140.211.11.130
request.header['x-forwarded-for'] 140.211.11.130, 192.168.0.10 null
request.header['x-forwarded-by'] null null
request.header['x-forwarded-proto'] https https
request.scheme http https
request.secure false true
request.serverPort 80 443
+

+

+ Note : x-forwarded-by header is null because only + internal proxies has been traversed by the request. + x-forwarded-for is null because all the proxies are + trusted or internal. +

+
+ + + +

RemoteIpFilter configuration:

+ + <filter> + <filter-name>RemoteIpFilter</filter-name> + <filter-class>org.apache.catalina.filters.RemoteIpFilter</filter-class> + <init-param> + <param-name>allowedInternalProxies</param-name> + <param-value>192\.168\.0\.10, 192\.168\.0\.11</param-value> + </init-param> + <init-param> + <param-name>remoteIpHeader</param-name> + <param-value>x-forwarded-for</param-value> + </init-param> + <init-param> + <param-name>remoteIpProxiesHeader</param-name> + <param-value>x-forwarded-by</param-value> + </init-param> + <init-param> + <param-name>trustedProxies</param-name> + <param-value>proxy1, proxy2</param-value> + </init-param> + </filter> + +

Request values: + + + + + + + + + + + + + + + + + + + + +
PropertyValue Before RemoteIpFilterValue After RemoteIpFilter
request.remoteAddr 192.168.0.10 140.211.11.130
request.header['x-forwarded-for'] 140.211.11.130, proxy1, proxy2 null
request.header['x-forwarded-by'] null proxy1, proxy2
+

+

+ Note : proxy1 and proxy2 are both trusted proxies that + come in x-forwarded-for header, they both are migrated in + x-forwarded-by header. x-forwarded-for is null + because all the proxies are trusted or internal. +

+
+ + +

RemoteIpFilter configuration:

+ + <filter> + <filter-name>RemoteIpFilter</filter-name> + <filter-class>org.apache.catalina.filters.RemoteIpFilter</filter-class> + <init-param> + <param-name>allowedInternalProxies</param-name> + <param-value>192\.168\.0\.10, 192\.168\.0\.11</param-value> + </init-param> + <init-param> + <param-name>remoteIpHeader</param-name> + <param-value>x-forwarded-for</param-value> + </init-param> + <init-param> + <param-name>remoteIpProxiesHeader</param-name> + <param-value>x-forwarded-by</param-value> + </init-param> + <init-param> + <param-name>trustedProxies</param-name> + <param-value>proxy1, proxy2</param-value> + </init-param> + </filter> + +

Request values: + + + + + + + + + + + + + + + + + + + + +
PropertyValue Before RemoteIpFilterValue After RemoteIpFilter
request.remoteAddr 192.168.0.10 140.211.11.130
request.header['x-forwarded-for'] 140.211.11.130, proxy1, proxy2, 192.168.0.10 null
request.header['x-forwarded-by'] null proxy1, proxy2
+

+

+ Note : proxy1 and proxy2 are both trusted proxies that + come in x-forwarded-for header, they both are migrated in + x-forwarded-by header. As 192.168.0.10 is an internal + proxy, it does not appear in x-forwarded-by. + x-forwarded-for is null because all the proxies are + trusted or internal. +

+
+ + + +

RemoteIpFilter configuration:

+ + <filter> + <filter-name>RemoteIpFilter</filter-name> + <filter-class>org.apache.catalina.filters.RemoteIpFilter</filter-class> + <init-param> + <param-name>allowedInternalProxies</param-name> + <param-value>192\.168\.0\.10, 192\.168\.0\.11</param-value> + </init-param> + <init-param> + <param-name>remoteIpHeader</param-name> + <param-value>x-forwarded-for</param-value> + </init-param> + <init-param> + <param-name>remoteIpProxiesHeader</param-name> + <param-value>x-forwarded-by</param-value> + </init-param> + <init-param> + <param-name>trustedProxies</param-name> + <param-value>proxy1, proxy2</param-value> + </init-param> + </filter> + +

Request values: + + + + + + + + + + + + + + + + + + + + +
PropertyValue Before RemoteIpFilterValue After RemoteIpFilter
request.remoteAddr 192.168.0.10 untrusted-proxy
request.header['x-forwarded-for'] 140.211.11.130, untrusted-proxy, proxy1 140.211.11.130
request.header['x-forwarded-by'] null proxy1
+

+

+ Note : x-forwarded-by holds the trusted proxy proxy1. + x-forwarded-by holds 140.211.11.130 because + untrusted-proxy is not trusted and thus, we can not trust that + untrusted-proxy is the actual remote ip. + request.remoteAddr is untrusted-proxy that is an IP + verified by proxy1. +

+
+ + + +

The Remote IP Filter supports the + following initialisation parameters:

+ + + + +

Name of the HTTP Header read by this valve that holds the list of + traversed IP addresses starting from the requesting client. If not + specified, the default of x-forwarded-for is used.

+
+ + +

List of internal proxies' IP addresses as comma separated regular + expressions. If they appear in the remoteIpHeader + value, they will be trusted and will not appear in the + proxiesHeader value. If not specified the default value + of 10\.\d{1,3}\.\d{1,3}\.\d{1,3}, 192\.168\.\d{1,3}\.\d{1,3}, + 169\.254\.\d{1,3}\.\d{1,3}, 127\.\d{1,3}\.\d{1,3}\.\d{1,3} will + be used.

+
+ + +

Name of the HTTP header created by this valve to hold the list of + proxies that have been processed in the incoming + remoteIpHeader. If not specified, the default of + x-forwarded-by is used.

+
+ + +

List of trusted proxies' IP addresses as comma separated regular + expressions. If they appear in the remoteIpHeader + value, they will be trusted and will appear in the + proxiesHeader value. If not specified, no proxies will + be trusted.

+
+ + +

Name of the HTTP Header read by this valve that holds the protocol + used by the client to connect to the proxy. If not specified, the + default of null is used.

+
+ + +

Value of the protocolHeader to indicate that it is + an HTTPS request. If not specified, the default of https is + used.

+
+ + +

Value returned by ServletRequest.getServerPort() + when the protocolHeader indicates http + protocol. If not specified, the default of 80 is + used.

+
+ + +

Value returned by ServletRequest.getServerPort() + when the protocolHeader indicates https + protocol. If not specified, the default of 443 is + used.

+
+ +
+ + +
+ +
+ + +
+ + + +

The Request Dumper Filter logs information from the request and response + objects and is intended to be used for debugging purposes. When using this + Filter, it is recommended that the + org.apache.catalina.filter.RequestDumperFilter logger is + directed to a dedicated file and that the + org.apache.juli.VerbatimFormmater is used.

+ +

WARNING: Using this filter has side-effects. The + output from this filter includes any parameters included with the request. + The parameters will be decoded using the default platform encoding. Any + subsequent calls to request.setCharacterEncoding() within + the web application will have no effect.

+ +
+ + + +

The filter class name for the Request Dumper Filter is + org.apache.catalina.filters.RequestDumperFilter + .

+ +
+ + + +

The Request Dumper Filter does not support any initialization + parameters.

+ +
+ + + +

The following entries in a web application's web.xml would enable the + Request Dumper filter for all requests for that web application. If the + entries were added to CATALINA_BASE/conf/web.xml, the Request + Dumper Filter would be enabled for all web applications.

+ +<filter> + <filter-name>requestdumper</filter-name> + <filter-class> + org.apache.catalina.filters.RequestDumperFilter + </filter-class> +</filter> +<filter-mapping> + <filter-name>requestdumper</filter-name> + <url-pattern>*</url-pattern> +</filter-mapping> + + +

The following entries in CATALINA_BASE/conf/logging.properties would + create a separate log file for the Request Dumper Filter output.

+ +# To this configuration below, 1request-dumper.org.apache.juli.FileHandler +# also needs to be added to the handlers property near the top of the file +1request-dumper.org.apache.juli.FileHandler.level = INFO +1request-dumper.org.apache.juli.FileHandler.directory = ${catalina.base}/logs +1request-dumper.org.apache.juli.FileHandler.prefix = request-dumper. +1request-dumper.org.apache.juli.FileHandler.formatter = org.apache.juli.VerbatimFormatter +org.apache.catalina.filters.RequestDumperFilter.level = INFO +org.apache.catalina.filters.RequestDumperFilter.handlers = 1request-dumper.org.apache.juli.FileHandler + +
+
+ + +
+ + + +

Microsoft operating systems have two WebDAV clients. One is used with + port 80, the other is used for all other ports. The implementation used with + port 80 does not adhere to the WebDAV specification and fails when trying to + communicate with the Tomcat WebDAV Servlet. This Filter provides a fix for + this by forcing the use of the WebDAV implementation that works, even when + connecting via port 80.

+ +
+ + + +

The filter class name for the WebDAV Fix Filter is + org.apache.catalina.filters.WebdavFixFilter + .

+ +
+ + + +

The WebDAV Fix Filter does not support any initialization parameters.

+ +
+ +
+ + + + + +
diff --git a/webapps/docs/config/globalresources.xml b/webapps/docs/config/globalresources.xml new file mode 100644 index 000000000000..7f148449598f --- /dev/null +++ b/webapps/docs/config/globalresources.xml @@ -0,0 +1,272 @@ + + + +]> + + + &project; + + + Remy Maucherat + Yoav Shapira + The GlobalNamingResources Component + + + + +
+ +
+ +
+ +

The GlobalNamingResources element defines the global + JNDI resources for the Server.

+ +

These resources are listed in the server's global JNDI resource context. + This context is distinct from the per-web-application JNDI contexts + described in + the JNDI Resources HOW-TO. + The resources defined in this element are not visible in + the per-web-application contexts unless you explicitly link them with + <ResourceLink> elements. +

+ +
+ + +
+ +
+ + +
+ +
+ + +
+ + + + +

You can configure named values that will be made visible to all + web applications as environment entry resources by nesting + <Environment> entries inside this element. For + example, you can create an environment entry like this:

+ +<GlobalNamingResources ...> + ... + <Environment name="maxExemptions" value="10" + type="java.lang.Integer" override="false"/> + ... +</GlobalNamingResources> + + +

This is equivalent to the inclusion of the following element in the + web application deployment descriptor (/WEB-INF/web.xml): +

+ +<env-entry> + <env-entry-name>maxExemptions</env-entry-name> + <env-entry-value>10</env-entry-value> + <env-entry-type>java.lang.Integer</env-entry-type> +</env-entry> + +

but does not require modification of the deployment descriptor + to customize this value.

+ +

The valid attributes for an <Environment> element + are as follows:

+ + + + +

Optional, human-readable description of this environment entry.

+
+ + +

The name of the environment entry to be created, relative to the + java:comp/env context.

+
+ + +

Set this to false if you do not want + an <env-entry> for the same environment entry name, + found in the web application deployment descriptor, to override the + value specified here. By default, overrides are allowed.

+
+ + +

The fully qualified Java class name expected by the web application + for this environment entry. Must be one of the legal values for + <env-entry-type> in the web application deployment + descriptor: java.lang.Boolean, + java.lang.Byte, java.lang.Character, + java.lang.Double, java.lang.Float, + java.lang.Integer, java.lang.Long, + java.lang.Short, or java.lang.String.

+
+ + +

The parameter value that will be presented to the application + when requested from the JNDI context. This value must be convertable + to the Java type defined by the type attribute.

+
+ +
+ +
+ + + + +

You can declare the characteristics of resources + to be returned for JNDI lookups of <resource-ref> and + <resource-env-ref> elements in the web application + deployment descriptor by defining them in this element and then linking + them with <ResourceLink> + elements + in the <Context> element. + + You MUST also define any other needed parameters using + attributes on the Resource element, to configure + the object factory to be used (if not known to Tomcat already), and + the properties used to configure that object factory.

+ +

For example, you can create a resource definition like this:

+ +<GlobalNamingResources ...> + ... + <Resource name="jdbc/EmployeeDB" auth="Container" + type="javax.sql.DataSource" + description="Employees Database for HR Applications"/> + ... +</GlobalNamingResources> + + +

This is equivalent to the inclusion of the following element in the + web application deployment descriptor (/WEB-INF/web.xml):

+ +<resource-ref> + <description>Employees Database for HR Applications</description> + <res-ref-name>jdbc/EmployeeDB</res-ref-name> + <res-ref-type>javax.sql.DataSource</res-ref-type> + <res-auth>Container</res-auth> +</resource-ref> + + +

but does not require modification of the deployment + descriptor to customize this value.

+ +

The valid attributes for a <Resource> element + are as follows:

+ + + + +

Specify whether the web Application code signs on to the + corresponding resource manager programmatically, or whether the + Container will sign on to the resource manager on behalf of the + application. The value of this attribute must be + Application or Container. This + attribute is required if the web application + will use a <resource-ref> element in the web + application deployment descriptor, but is optional if the + application uses a <resource-env-ref> instead.

+
+ + +

Optional, human-readable description of this resource.

+
+ + +

The name of the resource to be created, relative to the + java:comp/env context.

+
+ + +

Specify whether connections obtained through this resource + manager can be shared. The value of this attribute must be + Shareable or Unshareable. By default, + connections are assumed to be shareable.

+
+ + +

The fully qualified Java class name expected by the web + application when it performs a lookup for this resource.

+
+ +
+ + +
+ + +

Use <ResourceLink> + elements to link resources from the global context into + per-web-application contexts. Here is an example of making a custom + factory available to an application, based on the example definition in the + + JNDI Resource HOW-TO: +

+ + + + + + ]]> + + +
+ + + +

You can declare the characteristics of the UserTransaction + to be returned for JNDI lookup for java:comp/UserTransaction. + You MUST define an object factory class to instantiate + this object as well as the needed resource parameters as attributes of the + Transaction + element, and the properties used to configure that object factory.

+ +

The valid attributes for the <Transaction> element + are as follows:

+ + + + +

The class name for the JNDI object factory.

+
+ +
+ +
+ +
+ + + + + +
diff --git a/webapps/docs/config/host.xml b/webapps/docs/config/host.xml new file mode 100644 index 000000000000..57d93be653ea --- /dev/null +++ b/webapps/docs/config/host.xml @@ -0,0 +1,645 @@ + + + +]> + + + &project; + + + Craig R. McClanahan + Remy Maucherat + Yoav Shapira + The Host Container + + + + +
+ +
+ +
+ +

The Host element represents a virtual host, + which is an association of a network name for a server (such as + "www.mycompany.com" with the particular server on which Catalina is + running. In order to be effective, this name must be registered in the + Domain Name Service (DNS) server that manages the Internet + domain you belong to - contact your Network Administrator for more + information.

+ +

In many cases, System Administrators wish to associate more than + one network name (such as www.mycompany.com and + company.com) with the same virtual host and applications. + This can be accomplished using the Host + Name Aliases feature discussed below.

+ +

One or more Host elements are nested inside an + Engine element. Inside the Host element, you + can nest Context elements for the web + applications associated with this virtual host. Exactly one of the Hosts + associated with each Engine MUST have a name matching the + defaultHost attribute of that Engine.

+ +
+

The description below uses the variable name $CATALINA_BASE to refer the + base directory against which most relative paths are resolved. If you have + not configured Tomcat for multiple instances by setting a CATALINA_BASE + directory, then $CATALINA_BASE will be set to the value of $CATALINA_HOME, + the directory into which you have installed Tomcat.

+
+ +
+ + +
+ + + +

All implementations of Host + support the following attributes:

+ + + + +

The Application Base directory for this virtual host. + This is the pathname of a directory that may contain web applications + to be deployed on this virtual host. You may specify an + absolute pathname, or a pathname that is relative to the + $CATALINA_BASE directory. See + Automatic Application + Deployment for more information on automatic recognition and + deployment of web applications. If not specified, the default of + webapps will be used.

+
+ + +

The XML Base directory for this virtual host. + This is the pathname of a directory that may contain context XML + descriptors to be deployed on this virtual host. You may specify an + absolute pathname for this directory, or a pathname that is relative + to the $CATALINA_BASE directory. See + Automatic Application + Deployment for more information on automatic recognition and + deployment of web applications. If not specified the default of + [engine_name]/[host_name] will be used.

+
+ + +

If set to true, Tomcat will attempt to create the directories defined + by the attributes appBase and xmlBase during + the startup phase. The default value is true. If set to + true, and directory creation fails, an error message will be printed out + but will not halt the startup sequence.

+
+ + +

This flag value indicates if Tomcat should check periodically for new + or updated web applications while Tomcat is running. If true, Tomcat + periodically checks the appBase and xmlBase + directories and deploys any new web applications or context XML + descriptors found. Updated web applications or context XML descriptors + will trigger a reload of the web application. The flag's value defaults + to true. See + Automatic Application + Deployment for more information.

+
+ + +

This value represents the delay in seconds between the + invocation of the backgroundProcess method on this host and + its child containers, including all contexts. + Child containers will not be invoked if their delay value is not + negative (which would mean they are using their own processing + thread). Setting this to a positive value will cause + a thread to be spawn. After waiting the specified amount of time, + the thread will invoke the backgroundProcess method on this host + and all its child containers. A host will use background processing to + perform live web application deployment related tasks. If not + specified, the default value for this attribute is -1, which means + the host will rely on the background processing thread of its parent + engine.

+
+ + +

Java class name of the implementation to use. This class must + implement the org.apache.catalina.Host interface. + If not specified, the standard value (defined below) will be used.

+
+ + +

This flag value indicates if web applications from this host should + be automatically deployed when Tomcat starts. The flag's value defaults + to true. See + Automatic Application + Deployment for more information.

+
+ + +

Network name of this virtual host, as registered in your + Domain Name Service server. Regardless of the case used to + specify the hostname, Tomcat will convert it to lower case internally. + One of the Hosts nested within an Engine MUST + have a name that matches the defaultHost setting for that + Engine. See Host Name Aliases for + information on how to assign more than one network name to the same + virtual host.

+
+ +
+ +
+ + + + +

The standard implementation of Host is + org.apache.catalina.core.StandardHost. + It supports the following additional attributes (in addition to the + common attributes listed above):

+ + + + +

Set to true if you want a context XML descriptor + embedded inside the application (located at + /META-INF/context.xml) to be copied to xmlBase + when the application is deployed. On subsequent starts, the copied + context XML descriptor will be used in preference to any context XML + descriptor embedded inside the application even if the descriptor + embedded inside the application is more recent. The flag's value + defaults to false. Note if deployXML + is false, this attribute will have no effect.

+
+ + +

Set to false if you want to disable parsing the context + XML descriptor embedded inside the application (located at + /META-INF/context.xml). Security conscious environments + should set this to false to prevent applications from + interacting with the container's configuration. The administrator will + then be responsible for providing an external context configuration + file, and putting it in the location defined by the + xmlBase attribute. The flag's value defaults to + true.

+
+ + +

Java class name of the error reporting valve which will be used + by this Host. The responsibility of this valve is to output error + reports. Setting this property allows to customize the look of the + error pages which will be generated by Tomcat. This class must + implement the + org.apache.catalina.Valve interface. If none is specified, + the value org.apache.catalina.valves.ErrorReportValve + will be used by default.

+
+ + +

Set to true if you want web applications that are + placed in the appBase directory as web application + archive (WAR) files to be unpacked into a corresponding disk directory + structure, false to run such web applications directly + from a WAR file. WAR files located outside of the Host's + appBase will not be expanded. See + Automatic Application + Deployment for more information.

+
+ + +

Pathname to a scratch directory to be used by applications for + this Host. Each application will have its own sub directory with + temporary read-write use. Configuring a Context workDir will override + use of the Host workDir configuration. This directory will be made + visible to servlets in the web application by a servlet context + attribute (of type java.io.File) named + javax.servlet.context.tempdir as described in the + Servlet Specification. If not specified, a suitable directory + underneath $CATALINA_BASE/work will be provided.

+
+ +
+ +
+ + +
+ + +
+ +

You can nest one or more Context elements + inside this Host element, each representing a different web + application associated with this virtual host.

+ +

You can nest at most one instance of the following utility components + by nesting a corresponding element inside your Host + element:

+
    +
  • Realm - + Configure a realm that will allow its + database of users, and their associated roles, to be shared across all + Contexts nested inside this Host (unless + overridden by a Realm configuration + at a lower level).
  • +
+ +
+ + +
+ + + + +

A host is associated with the + org.apache.catalina.core.ContainerBase.[engine_name].[host_name] + log category. Note that the brackets are part of the name, + don't omit them.

+ +
+ + + + +

When you run a web server, one of the output files normally generated + is an access log, which generates one line of information for + each request processed by the server, in a standard format. Catalina + includes an optional Valve implementation that + can create access logs in the same standard format created by web servers, + or in any number of custom formats.

+ +

You can ask Catalina to create an access log for all requests + processed by an Engine, + Host, or Context + by nesting a Valve element like this:

+ + +<Host name="localhost" ...> + ... + <Valve className="org.apache.catalina.valves.AccessLogValve" + prefix="localhost_access_log." suffix=".txt" + pattern="common"/> + ... +</Host> + + +

See Access Log Valve + for more information on the configuration attributes that are + supported.

+ +
+ + + + +

If you are using the standard Host implementation, + the following actions take place automatically when Catalina is first + started, if the deployOnStartup property is set to + true (which is the default value):

+
    +
  • Any XML file in the Host's xmlBase directory (by + default $CATALINA_BASE/conf/[engine_name]/[host_name]) is + assumed to be a context XML descriptor containing a + Context element (and its associated + sub-elements) for a single web application. The web applications + associated with each of these context XML descriptor files will be + deployed first.
    + The docBase attribute of this <Context> + element must only be set if the docBase is outside the Host's + appBase. For web applications located inside the Host's + appBase, the docBase will be the name of the + XML file with ".xml" replaced with ".war" for a web application archive + or the name of the XML file with ".xml" removed for a directory.
    + The path attribute must not be set. The context path used + will be a slash character ("/") followed by the name of the XML file + (less the .xml extension). Multi-level context paths may be defined + using #, e.g. foo#bar.xml for a context path of + /foo/bar. The default web application that has a context + path of / may be defined by using a file called + ROOT.xml.
  • +
  • Any web application archive file within the Host's appBase + directory that has not already been deployed as a result of a context + XML descriptor and does not have a corresponding directory of the same + name (without the ".war" extension) will be deployed next. The context + path used will be a slash character ("/") followed by the web + application archive name less the ".war" extension. The one exception to + this rule is that a web application archive named "ROOT.war" will be + deployed with a context path of /. Multi-level contexts may + be defined by using #, e.g. use a WAR named foo#bar.war for + a context path of /foo/bar.
    + If the unpackWARs attribute is true, the web + application archive file will be expanded to a directory of the same + name (without the ".war" extension".
    + Note: If you re-deploy an updated WAR file while Tomcat is stopped, be + sure to delete the associated expanded directory before restarting + Tomcat, so that the updated WAR file will be re-expanded when Tomcat + restarts.
    + If copyXml is true (it is false + by default), any web application archive file within the Hosts's + appBase directory that does not have a corresponding + context XML descriptor (with a ".xml" extension rather than a ".war" + extension) in the Host's xmlBase will be scanned to see + if it contains a context XML descriptor (located at + /META-INF/context.xml) and if one is found the descriptor + will be copied to the xmlBase directory and renamed. +
  • +
  • Finally, any sub-directory within the Host's appBase that + has not already been deployed as a result of a context XML descriptor + will be deployed. The context path used will be a slash character + ("/") followed by the directory name, unless the directory name is ROOT, + in which case the context path will /. Multi-level contexts + may be defined by using #, e.g. use a directory named + foo#bar for a context path of /foo/bar.
    + If copyXml is true (it is false + by default), any directory within the Hosts's appBase + directory that does not have a corresponding context XML descriptor in + the Host's xmlBase will be scanned to see if it contains + a context XML descriptor (located at /META-INF/context.xml) + and if one is found the descriptor will be copied to the + xmlBase directory and renamed. +
  • +
+ +

In addition to the automatic deployment that occurs at startup time, + you can also request that new XML configuration files, WAR files, or + sub-directories that are dropped in to the appBase (or + xmlBase in the case of an XML configuration file) directory + while Tomcat is running will be automatically deployed, according to the + rules described above. The auto deployer will also track web applications + for the following changes: +

    +
  • An update to the WEB-INF/web.xml file will trigger a reload of the + web application
  • +
  • Deleting a WAR file will trigger an undeploy of the application with + the removal of any associated expanded directory, context file and + work directory. Any current user sessions will not be persisted.
  • +
  • Deleting a directory will trigger an undeploy of the application + with the removal of any associated context file and work directory. + Any current user sessions will not be persisted. If there is an + associated WAR file, it will not be deleted and the application will + be redeployed from the WAR file the next time the auto deployer checks + for changes.
  • +
  • Deleting a context file will trigger an undeploy of the application + with the removal of any associated work directory. Any current user + sessions will not be persisted. If there is an associated WAR file + and/or directory, they will not be deleted and the application will be + redeployed from the WAR file (or from directory if there is no WAR + file) the next time the auto deployer checks for changes.
  • +
  • Updating a WAR file will trigger an undeploy of the application with + the removal of any associated expanded directory, context file and + work directory. Any current user sessions will not be persisted.
  • +
  • Updating a directory (not the directory contents) will trigger an + undeploy of the application with the removal of any associated context + file and work directory. Any current user sessions will not be + persisted. The application will be redeployed the next time the auto + deployer checks for changes.
  • +
  • Updating a context file will trigger an undeploy of the application + with the removal of any associated work directory. Any current user + sessions will not be persisted. The application will be redeployed the + next time the auto deployer checks for changes.
  • +
+

+ +

When using automatic deployment, the docBase defined by + an XML Context file should be outside of the + appBase directory. If this is not the case difficulties + may be experienced deploying the web application or the application may + be deployed twice.

+ +

Finally, note that if you are defining contexts explicitly in server.xml, + you should probably turn off automatic application deployment. Otherwise, + the web applications will each be deployed twice, and that may cause + problems for the applications. +

+ +
+ + + + +

In many server environments, Network Administrators have configured + more than one network name (in the Domain Name Service (DNS) + server), that resolve to the IP address of the same server. Normally, + each such network name would be configured as a separate + Host element in conf/server.xml, each + with its own set of web applications.

+ +

However, in some circumstances, it is desirable that two or more + network names should resolve to the same virtual host, + running the same set of applications. A common use case for this + scenario is a corporate web site, where it is desirable that users + be able to utilize either www.mycompany.com or + company.com to access exactly the same content and + applications.

+ +

This is accomplished by utilizing one or more Alias + elements nested inside your Host element. For + example:

+ +<Host name="www.mycompany.com" ...> + ... + <Alias>mycompany.com</Alias> + ... +</Host> + + +

In order for this strategy to be effective, all of the network names + involved must be registered in your DNS server to resolve to the + same computer that is running this instance of Catalina.

+ +
+ + + + +

If you have implemented a Java object that needs to know when this + Host is started or stopped, you can declare it by + nesting a Listener element inside this element. The + class name you specify must implement the + org.apache.catalina.LifecycleListener interface, and + it will be notified about the occurrence of the corresponding + lifecycle events. Configuration of such a listener looks like this:

+ + +<Host name="localhost" ...> + ... + <Listener className="com.mycompany.mypackage.MyListener" ... > + ... +</Host> + + +

Note that a Listener can have any number of additional properties + that may be configured from this element. Attribute names are matched + to corresponding JavaBean property names using the standard property + method naming patterns.

+ +
+ + + + +

You can ask Catalina to check the IP address, or host name, on every + incoming request directed to the surrounding + Engine, Host, or + Context element. The remote address or name + will be checked against a configured list of "accept" and/or "deny" + filters, which are defined using the Regular Expression syntax supported + by the Jakarta Regexp + regular expression library. Requests that come from locations that are + not accepted will be rejected with an HTTP "Forbidden" error. + Example filter declarations:

+ + +<Host name="localhost" ...> + ... + <Valve className="org.apache.catalina.valves.RemoteHostValve" + allow="*.mycompany.com,www.yourcompany.com"/> + <Valve className="org.apache.catalina.valves.RemoteAddrValve" + deny="192.168.1.*"/> + ... +</Host> + + +

See Remote Address Filter + and Remote Host Filter for + more information about the configuration options that are supported.

+ +
+ + + + +

In many environments, but particularly in portal environments, it + is desireable to have a user challenged to authenticate themselves only + once over a set of web applications deployed on a particular virtual + host. This can be accomplished by nesting an element like this inside + the Host element for this virtual host:

+ + +<Host name="localhost" ...> + ... + <Valve className="org.apache.catalina.authenticator.SingleSignOn" + debug="0"/> + ... +</Host> + + +

The Single Sign On facility operates according to the following rules: +

+
    +
  • All web applications configured for this virtual host must share the + same Realm. In practice, that means you can + nest the Realm element inside this Host element (or the surrounding + Engine element), but not inside a + Context element for one of the involved + web applications.
  • +
  • As long as the user accesses only unprotected resources in any of the + web applications on this virtual host, they will not be challenged + to authenticate themselves.
  • +
  • As soon as the user accesses a protected resource in + any web application associated with this virtual + host, the user will be challenged to authenticate himself or herself, + using the login method defined for the web application currently + being accessed.
  • +
  • Once authenticated, the roles associated with this user will be + utilized for access control decisions across all + of the associated web applications, without challenging the user + to authenticate themselves to each application individually.
  • +
  • As soon as the user logs out of one web application (for example, + by invalidating the corresponding session if form + based login is used), the user's sessions in all + web applications will be invalidated. Any subsequent attempt to + access a protected resource in any application will require the + user to authenticate himself or herself again.
  • +
  • The Single Sign On feature utilizes HTTP cookies to transmit a token + that associates each request with the saved user identity, so it can + only be utilized in client environments that support cookies.
  • +
+ +
+ + + + +

Many web servers can automatically map a request URI starting with + a tilde character ("~") and a username to a directory (commonly named + public_html) in that user's home directory on the server. + You can accomplish the same thing in Catalina by using a special + Listener element like this (on a Unix system that + uses the /etc/passwd file to identify valid users):

+ + +<Host name="localhost" ...> + ... + <Listener className="org.apache.catalina.startup.UserConfig" + directoryName="public_html" + userClass="org.apache.catalina.startup.PasswdUserDatabase"/> + ... +</Host> + + +

On a server where /etc/passwd is not in use, you can + request Catalina to consider all directories found in a specified base + directory (such as c:\Homes in this example) to be + considered "user home" directories for the purposes of this directive:

+ + +<Host name="localhost" ...> + ... + <Listener className="org.apache.catalina.startup.UserConfig" + directoryName="public_html" + homeBase=c:\Homes" + userClass="org.apache.catalina.startup.HomesUserDatabase"/> + ... +</Host> + + +

If a user home directory has been set up for a user named + craigmcc, then its contents will be visible from a + client browser by making a request to a URL like:

+ + +http://www.mycompany.com:8080/~craigmcc + + +

Successful use of this feature requires recognition of the following + considerations:

+
    +
  • Each user web application will be deployed with characteristics + established by the global and host level default context settings.
  • +
  • It is legal to include more than one instance of this Listener + element. This would only be useful, however, in circumstances + where you wanted to configure more than one "homeBase" directory.
  • +
  • The operating system username under which Catalina is executed + MUST have read access to each user's web application directory, + and all of its contents.
  • +
+ +
+ + +
+ + + + + +
diff --git a/webapps/docs/config/http.xml b/webapps/docs/config/http.xml new file mode 100644 index 000000000000..3454fdf90ad0 --- /dev/null +++ b/webapps/docs/config/http.xml @@ -0,0 +1,1091 @@ + + + +]> + + + &project; + + + Craig R. McClanahan + Yoav Shapira + The HTTP Connector + + + + +
+ +
+ +
+ +

The HTTP Connector element represents a + Connector component that supports the HTTP/1.1 protocol. + It enables Catalina to function as a stand-alone web server, in addition + to its ability to execute servlets and JSP pages. A particular instance + of this component listens for connections on a specific TCP port number + on the server. One or more such Connectors can be + configured as part of a single Service, each + forwarding to the associated Engine to perform + request processing and create the response.

+ +

If you wish to configure the Connector that is used + for connections to web servers using the AJP protocol (such as the + mod_jk 1.2.x connector for Apache 1.3), see + here instead.

+ +

Each incoming request requires + a thread for the duration of that request. If more simultaneous requests + are received than can be handled by the currently available request + processing threads, additional threads will be created up to the + configured maximum (the value of the maxThreads attribute). + If still more simultaneous requests are received, they are stacked up + inside the server socket created by the Connector, up to + the configured maximum (the value of the acceptCount + attribute. Any further simultaneous requests will receive "connection + refused" errors, until resources are available to process them.

+ +
+ + +
+ + + +

All implementations of Connector + support the following attributes:

+ + + + +

A boolean value which can be used to enable or disable the TRACE + HTTP method. If not specified, this attribute is set to false.

+
+ + +

The default timeout for asynchronous requests in milliseconds. If not + specified, this attribute is set to 10000 (10 seconds).

+
+ + +

Set to true if you want calls to + request.getRemoteHost() to perform DNS lookups in + order to return the actual host name of the remote client. Set + to false to skip the DNS lookup and return the IP + address in String form instead (thereby improving performance). + By default, DNS lookups are enabled.

+
+ + +

The maximum size in bytes of the POST which will be handled by + the container FORM URL parameter parsing. The limit can be disabled by + setting this attribute to a value less than or equal to 0. + If not specified, this attribute is set to 2097152 (2 megabytes).

+
+ + +

The maximum size in bytes of the POST which will be saved/buffered by + the container during FORM or CLIENT-CERT authentication. For both types + of authentication, the POST will be saved/buffered before the user is + authenticated. For CLIENT-CERT authentication, the POST is buffered for + the duration of the SSL handshake and the buffer emptied when the request + is processed. For FORM authentication the POST is saved whilst the user + is re-directed to the login form and is retained until the user + successfully authenticates or the session associated with the + authentication request expires. The limit can be disabled by setting this + attribute to -1. Setting the attribute to zero will disable the saving of + POST data during authentication. If not specified, this attribute is set + to 4096 (4 kilobytes).

+
+ + +

The TCP port number on which this Connector + will create a server socket and await incoming connections. Your + operating system will allow only one server application to listen + to a particular port number on a particular IP address.

+
+ + +

Sets the protocol to handle incoming traffic. The default value is + HTTP/1.1 which uses an auto-switching mechanism to select + either a blocking Java based connector or an APR/native based connector. + If the PATH (Windows) or LD_LIBRARY_PATH (on + most unix systems) environment variables contain the Tomcat native + library, the native/APR connector will be used. If the native library + cannot be found, the blocking Java based connector will be used. Note + that the native/APR connector has different settings for HTTPS than the + Java connectors.
+ To use an explicit protocol rather than rely on the auto-switching + mechanism described above, the following values may be used:
+ org.apache.coyote.http11.Http11Protocol - + blocking Java connector
+ org.apache.coyote.http11.Http11NioProtocol - + non blocking Java connector
+ org.apache.coyote.http11.Http11AprProtocol - + the APR/native connector.
+ Custom implementations may also be used.
+ Take a look at our Connector + Comparison chart. The configuration for both Java connectors is + identical, for http and https.
+ For more information on the APR connector and APR specific SSL settings + please visit the APR documentation +

+
+ + +

If this Connector is being used in a proxy + configuration, configure this attribute to specify the server name + to be returned for calls to request.getServerName(). + See Proxy Support for more + information.

+
+ + +

If this Connector is being used in a proxy + configuration, configure this attribute to specify the server port + to be returned for calls to request.getServerPort(). + See Proxy Support for more + information.

+
+ + +

If this Connector is supporting non-SSL + requests, and a request is received for which a matching + <security-constraint> requires SSL transport, + Catalina will automatically redirect the request to the port + number specified here.

+
+ + +

Set this attribute to the name of the protocol you wish to have + returned by calls to request.getScheme(). For + example, you would set this attribute to "https" + for an SSL Connector. The default value is "http". +

+
+ + +

Set this attribute to true if you wish to have + calls to request.isSecure() to return true + for requests received by this Connector. You would want this on an + SSL Connector or a non SSL connector that is receiving data from a + SSL accelerator, like a crypto card, a SSL appliance or even a webserver. + The default value is false.

+
+ + +

This specifies the character encoding used to decode the URI bytes, + after %xx decoding the URL. If not specified, ISO-8859-1 will be used. +

+
+ + +

This specifies if the encoding specified in contentType should be used + for URI query parameters, instead of using the URIEncoding. This + setting is present for compatibility with Tomcat 4.1.x, where the + encoding specified in the contentType, or explicitly set using + Request.setCharacterEncoding method was also used for the parameters from + the URL. The default value is false. +

+
+ + +

Set this attribute to true to cause Tomcat to use + the IP address that the request was received on to determine the Host + to send the request to. The default value is false.

+
+ + +

Set this attribute to true to cause Tomcat to advertise + support for the Servlet specification using the header recommended in the + specification. The default value is false.

+
+ +
+ +
+ + + +

The standard HTTP connectors (BIO, NIO and APR/native) all support the + following attributes in addition to the common Connector attributes listed + above.

+ + + + +

The maximum queue length for incoming connection requests when + all possible request processing threads are in use. Any requests + received when the queue is full will be refused. The default + value is 100.

+
+ + +

The number of threads to be used to accept connections. Increase this + value on a multi CPU machine, although you would never really need more + than 2. Also, with a lot of non keep alive connections, you + might want to increase this value as well. Default value is + 1.

+
+ + +

For servers with more than one IP address, this attribute + specifies which address will be used for listening on the specified + port. By default, this port will be used on all IP addresses + associated with the server.

+
+ + +

The value is a comma separated list of MIME types for which HTTP + compression may be used. + The default value is text/html,text/xml,text/plain.

+
+ + +

The Connector may use HTTP/1.1 GZIP compression in + an attempt to save server bandwidth. The acceptable values for the + parameter is "off" (disable compression), "on" (allow compression, which + causes text data to be compressed), "force" (forces compression in all + cases), or a numerical integer value (which is equivalent to "on", but + specifies the minimum amount of data before the output is compressed). If + the content-length is not known and compression is set to "on" or more + aggressive, the output will also be compressed. If not specified, this + attribute is set to "off".

+
+ + +

If compression is set to "on" then this attribute + may be used to specify the minimum amount of data before the output is + compressed. If not specified, this attribute is defaults to "2048".

+
+ + +

The number of milliseconds during which the sockets used by this + Connector will linger when they are closed. + The default value -1 which disables this option.

+
+ + +

The number of milliseconds this Connector will wait, + after accepting a connection, for the request URI line to be + presented. The default value is 60000 (i.e. 60 seconds).

+
+ + +

This flag allows the servlet container to use a different, longer + connection timeout while a servlet is being executed, which in the end + allows either the servlet a longer amount of time to complete its + execution, or a longer timeout during data upload. If not specified, + this attribute is set to "true".

+
+ + +

A reference to the name in an Executor + element. If this attribute is set, and the named executor exists, the + connector will use the executor, and all the other thread attributes will + be ignored. Note that if a shared executor is not specified for a + connector then the connector will use a private, internal executor to + provide the thread pool.

+
+ + +

The number of milliseconds this Connector will wait + for another HTTP request before closing the connection. The default value + is to use the value that has been set for the + connectionTimeout attribute.

+
+ + +

The maximum size of the request and response HTTP header, specified + in bytes. If not specified, this attribute is set to 8192 (8 KB).

+
+ + +

The maximum number of HTTP requests which can be pipelined until + the connection is closed by the server. Setting this attribute to 1 will + disable HTTP/1.0 keep-alive, as well as HTTP/1.1 keep-alive and + pipelining. Setting this to -1 will allow an unlimited amount of + pipelined or keep-alive HTTP requests. + If not specified, this attribute is set to 100.

+
+ + +

The maximum number of request processing threads to be created + by this Connector, which therefore determines the + maximum number of simultaneous requests that can be handled. If + not specified, this attribute is set to 200. If an executor is associated + with this connector, this attribute is ignored as the connector will + execute tasks using the executor rather than an internal thread pool.

+
+ + +

The minimum number of threads always kept running. If not specified, + the default of 10 is used.

+
+ + +

The value is a comma separated list of regular expressions matching + user-agents of HTTP clients for which compression should not be used, + because these clients, although they do advertise support for the + feature, have a broken implementation. + The default value is an empty String (regexp matching disabled).

+
+ + +

The protocol handler caches Processor objects to speed up performance. + This setting dictates how many of these objects get cached. + -1 means unlimited, default is 200. Set this + value somewhere close to your maxThreads value.

+
+ + +

The value is a comma separated list of regular expressions matching + user-agents of HTTP clients for which HTTP/1.1 or HTTP/1.0 keep alive + should not be used, even if the clients advertise support for these + features. + The default value is an empty String (regexp matching disabled).

+
+ + +

Overrides the Server header for the http response. If set, the value + for this attribute overrides the Tomcat default and any Server header set + by a web application. If not set, any value specified by the application + is used. If the application does not specify a value then + Apache-Coyote/1.1 is used. Unless you are paranoid, you won't + need this feature. +

+
+ + +

The size (in bytes) of the buffer to be provided for socket + output buffering. -1 can be specified to disable the use of a buffer. + By default, a buffers of 9000 bytes will be used.

+
+ + +

Use this attribute to enable SSL traffic on a connector. + To turn on SSL handshake/encryption/decryption on a connector + set this value to true. + The default value is false. + When turning this value true you will want to set the + scheme and the secure attributes as well + to pass the correct request.getScheme() and + request.isSecure() values to the servlets + See SSL Support for more information. +

+
+ + +

If set to true, the TCP_NO_DELAY option will be + set on the server socket, which improves performance under most + circumstances. This is set to true by default.

+
+ + +

The priority of the request processing threads within the JVM. + The default value is java.lang.Thread#NORM_PRIORITY. + See the JavaDoc for the java.lang.Thread class for more details on + what this priority means. +

+
+ +
+ +
+ + + +

The BIO and NIO implementation support the following Java TCP socket + attributes in addition to the common Connector and HTTP attributes listed + above.

+ + + +

(int)The socket receive buffer (SO_RCVBUF) size in bytes. JVM default + used if not set.

+
+ +

(int)The socket send buffer (SO_SNDBUF) size in bytes. JVM default + used if not set.

+
+ +

(bool)This is equivalent to standard attribute + tcpNoDelay.

+
+ +

(bool)Boolean value for the socket's keep alive setting + (SO_KEEPALIVE). JVM default used if not set.

+
+ +

(bool)Boolean value for the socket OOBINLINE setting. JVM default + used if not set.

+
+ +

(bool)Boolean value for the sockets reuse address option + (SO_REUSEADDR). JVM default used if not set.

+
+ +

(bool)Boolean value for the sockets so linger option (SO_LINGER). + A value for the standard attribute connectionLinger + that is >=0 is equivalent to setting this to true. + A value for the standard attribute connectionLinger + that is <0 is equivalent to setting this to false. + Both this attribute and soLingerTime must be set else the + JVM defaults will be used for both.

+
+ +

(int)Value in seconds for the sockets so linger option (SO_LINGER). + This is equivalent to standard attribute + connectionLinger. + Both this attribute and soLingerOn must be set else the + JVM defaults will be used for both.

+
+ +

This is equivalent to standard attribute + connectionTimeout.

+
+ +

(byte)Value between 0 and 255 for the + traffic class on the socket. JVM default used if not set.

+

NoteOn some JDK versions, setting + soTrafficClass causes a problem. A work around for this + is to add the -Djava.net.preferIPv4Stack=true value to your + JVM options.

+
+ +

(int)The first value for the performance settings. See + Socket Performance Options + All three performance attributes must be set else the JVM defaults will + be used for all three.

+
+ +

(int)The second value for the performance settings. See + Socket Performance Options + All three performance attributes must be set else the JVM defaults will + be used for all three.

+
+ +

(int)The third value for the performance settings. See + Socket Performance Options + All three performance attributes must be set else the JVM defaults will + be used for all three.

+
+ +

(int) The timeout for a socket unlock. When a connector is stopped, it will try to release the acceptor thread by opening a connector to itself. + The default value is 250 and the value is in milliseconds

+
+
+
+ + + +

There are no BIO specific configuration settings.

+ +
+ + + +

The following attributes are specific to the NIO connector.

+ + + + +

(int)The priority of the acceptor threads. The threads used to accept + new connections. The default value is + java.lang.Thread#NORM_PRIORITY. See the JavaDoc for the + java.lang.Thread class for more details on what this priority means.

+
+ + +

(int)The number of threads to be used to run for the polling events. + Default value is 1 per processor. Can't see a reason to go + above that. But experiment and find your own results.

+
+ + +

(int)The priority of the poller threads. The default value is + java.lang.Thread#NORM_PRIORITY. See the JavaDoc for the + java.lang.Thread class for more details on what this priority means.

+
+ + +

(int)The time in milliseconds to timeout on a select() for the + poller. This value is important, since connection clean up is done on + the same thread, so do not set this value to an extremely high one. The + default value is 1000 milliseconds.

+
+ + +

(bool)Whether to allow comet servlets or not. Default value is + true.

+
+ + +

(bool)Use this attribute to enable or disable sendfile capability. + The default value is true.

+
+ + +

(bool)Boolean value, whether to use direct ByteBuffers or java mapped + ByteBuffers. Default is false.
+ When you are using direct buffers, make sure you allocate the + appropriate amount of memory for the direct memory space. On Sun's JDK + that would be something like -XX:MaxDirectMemorySize=256m. +

+
+ + +

(int)Each connection that is opened up in Tomcat get associated with + a read ByteBuffer. This attribute controls the size of this buffer. By + default this read buffer is sized at 8192 bytes. For lower + concurrency, you can increase this to buffer more data. For an extreme + amount of keep alive connections, decrease this number or increase your + heap size.

+
+ + +

(int)Each connection that is opened up in Tomcat get associated with + a write ByteBuffer. This attribute controls the size of this buffer. By + default this write buffer is sized at 8192 bytes. For low + concurrency you can increase this to buffer more response data. For an + extreme amount of keep alive connections, decrease this number or + increase your heap size.
+ The default value here is pretty low, you should up it if you are not + dealing with tens of thousands concurrent connections.

+
+ + +

(int)The NIO connector uses a class called NioChannel that holds + elements linked to a socket. To reduce garbage collection, the NIO + connector caches these channel objects. This value specifies the size of + this cache. The default value is 500, and represents that + the cache will hold 500 NioChannel objects. Other values are + -1 for unlimited cache and 0 for no cache.

+
+ + +

(int)The NioChannel pool can also be size based, not used object + based. The size is calculated as follows:
+ NioChannel + buffer size = read buffer size + write buffer size
+ SecureNioChannel buffer size = application read buffer size + + application write buffer size + network read buffer size + + network write buffer size
+ The value is in bytes, the default value is 1024*1024*100 + (100MB).

+
+ + +

(int)Tomcat will cache SocketProcessor objects to reduce garbage + collection. The integer value specifies how many objects to keep in the + cache at most. The default is 500. Other values are + -1 for unlimited cache and 0for no cache.

+
+ + +

(int)Tomcat will cache KeyAttachment objects to reduce garbage + collection. The integer value specifies how many objects to keep in the + cache at most. The default is 500. Other values are + -1 for unlimited cache and 0for no cache.

+
+ + +

(int)Tomcat will cache PollerEvent objects to reduce garbage + collection. The integer value specifies how many objects to keep in the + cache at most. The default is 500. Other values are + -1 for unlimited cache and 0for no cache.

+
+ + +

(int)The max selectors to be used in the pool, to reduce selector + contention. Use this option when the command line + org.apache.tomcat.util.net.NioSelectorShared value is set + to false. Default value is 200.

+
+ + +

(int)The max spare selectors to be used in the pool, to reduce + selector contention. When a selector is returned to the pool, the system + can decide to keep it or let it be GC'd. Use this option when the + command line org.apache.tomcat.util.net.NioSelectorShared + value is set to false. Default value is -1 (unlimited).

+
+ + +

The following command line options are available for the NIO + connector:
+ -Dorg.apache.tomcat.util.net.NioSelectorShared=true|false + - default is true. Set this value to false if you wish to + use a selector for each thread. If you do set it to false, you can + control the size of the pool of selectors by using the + selectorPool.maxSelectors attribute.

+
+ + +

(int)The NIO connector implements an OutOfMemoryError strategy called + parachute. It holds a chunk of data as a byte array. In case of an OOM, + this chunk of data is released and the error is reported. This will give + the VM enough room to clean up. The oomParachute represents + the size in bytes of the parachute(the byte array). The default value is + 1024*1024(1MB). Please note, this only works for OOM errors + regarding the Java Heap space, and there is absolutely no guarantee + that you will be able to recover at all. If you have an OOM outside of + the Java Heap, then this parachute trick will not help. +

+
+
+
+ + + +

The following attributes are specific to the APR/native connector.

+ + + + +

Sets the TCP_DEFER_ACCEPT flag on the listening socket + for this connector. The default value is true where + TCP_DEFER_ACCEPT is supported by the operating system, + otherwise it is false.

+
+ + +

Amount of sockets that the poller responsible for polling kept alive + connections can hold at a given time. Extra connections will be closed + right away. The default value is 8192, corresponding to 8192 keep-alive + connections.

+
+ + +

Number of threads used to poll kept alive connections. On Windows the + default is chosen so that the sockets managed by each thread is + less than 1024. For Linux the default is 1. Changing the default on + Windows is likely to have a negative performance impact.

+
+ + +

Duration of a poll call. Lowering this value will slightly decrease + latency of connections being kept alive in some cases, but will use more + CPU as more poll calls are being made. The default value is 2000 (5ms). +

+
+ + +

Amount of sockets that the poller responsible for sending static + files asynchronously can hold at a given time. Extra connections will be + closed right away without any data being sent (resulting in a zero + length file on the client side). Note that in most cases, sendfile is a + call that will return right away (being taken care of "synchronously" by + the kernel), and the sendfile poller will not be used, so the amount of + static files which can be sent concurrently is much larger than the + specified amount. The default value is 1024.

+
+ + +

Number of threads used service sendfile sockets. On Windows the + default is chosen so that the sockets managed by each thread is + less than 1024. For Linux the default is 1. Changing the default on + Windows is likely to have a negative performance impact.

+
+ + +

(int)The priority of the acceptor and poller threads. The default + value is java.lang.Thread#NORM_PRIORITY. See the JavaDoc + for the java.lang.Thread class for more details on what this priority + means.

+
+ + +

(bool)Whether to allow comet servlets or not. Default value is + true.

+
+ + +

(bool)Use this attribute to enable or disable sendfile capability. + The default value is true.

+
+ +
+ +
+ +
+ + +
+ +

None at this time.

+ +
+ + +
+ + + + +

This Connector supports all of the required features + of the HTTP/1.1 protocol, as described in RFC 2616, including persistent + connections, pipelining, expectations and chunked encoding. If the client + (typically a browser) supports only HTTP/1.0, the + Connector will gracefully fall back to supporting this + protocol as well. No special configuration is required to enable this + support. The Connector also supports HTTP/1.0 + keep-alive.

+ +

RFC 2616 requires that HTTP servers always begin their responses with + the highest HTTP version that they claim to support. Therefore, this + Connector will always return HTTP/1.1 at + the beginning of its responses.

+ +
+ + + + +

The proxyName and proxyPort attributes can + be used when Tomcat is run behind a proxy server. These attributes + modify the values returned to web applications that call the + request.getServerName() and request.getServerPort() + methods, which are often used to construct absolute URLs for redirects. + Without configuring these attributes, the values returned would reflect + the server name and port on which the connection from the proxy server + was received, rather than the server name and port to whom the client + directed the original request.

+ +

For more information, see the + Proxy Support HOW-TO.

+ +
+ + + + + +

You can enable SSL support for a particular instance of this + Connector by setting the SSLEnabled attribute to + true.

+ +

You will also need to set the scheme and secure + attributes to the values https and true + respectively, to pass correct information to the servlets.

+ +

The BIO and NIO connectors used the JSSE SSL whereas the APR/native + connector uses OpenSSL. Therefore, in addition to using different attributes + to configure SSL, the APR/native connector also requires keys and certificates + to be provided in a different format.

+ +

The BIO and NIO connectors use the following attributes to configure SSL: +

+ + + + +

The certificate encoding algorithm to be used. This defaults to + KeyManagerFactory.getDefaultAlgorithm() which returns + SunX509 for Sun JVMs. IBM JVMs return + IbmX509. For other vendors, consult the JVM + documentation for the default value.

+
+ + +

Is unsafe legacy TLS renegotiation allowed which is likely to expose + users to CVE-2009-3555, a man-in-the-middle vulnerability in the TLS + protocol that allows an attacker to inject arbitrary data into the user's + request. If not specified, a default of false is used.

+
+ + +

The comma separated list of encryption ciphers that this socket is + allowed to use. By default, the default ciphers for the JVM will be used. + Note that this usually means that the weak export grade ciphers will be + included in the list of available ciphers. The ciphers are specified using + the JSSE cipher naming convention. The special value of ALL + will enable all supported ciphers. This will include many that are not + secure. ALL is intended for testing purposes only.

+
+ + +

Set to true if you want the SSL stack to require a + valid certificate chain from the client before accepting a connection. + Set to want if you want the SSL stack to request a client + Certificate, but not fail if one isn't presented. A false + value (which is the default) will not require a certificate chain + unless the client requests a resource protected by a security + constraint that uses CLIENT-CERT authentication.

+
+ + +

The certificate revocation list to be used to verify client + certificates. If not defined, client certificates will not be checked + against a certificate revocation list.

+
+ + +

The alias used to for the server certificate in the keystore. If not + specified the first key read in the keystore will be used.

+
+ + +

The password used to access the server certificate from the + specified keystore file. The default value is "changeit". +

+
+ + +

The pathname of the keystore file where you have stored the + server certificate to be loaded. By default, the pathname is + the file ".keystore" in the operating system home + directory of the user that is running Tomcat. If your + keystoreType doesn't need a file use "" + (empty string) for this parameter.

+
+ + +

The password used to access the specified keystore file. The default + value is the value of the keyPass attribute. +

+
+ + +

The name of the keystore provider to be used for the server + certificate. If not specified, the list of registered providers is + traversed in preference order and the first provider that supports the + keystoreType is used. +

+
+ + +

The type of keystore file to be used for the server certificate. + If not specified, the default value is "JKS".

+
+ + +

The number of SSL sessions to maintain in the session cache. Use 0 to + specify an unlimited cache size. If not specified, a default of 0 is + used.

+
+ + +

The time, in seconds, after the creation of an SSL session that it will + timeout. Use 0 to specify an unlimited timeout. If not specified, a + default of 86400 (24 hours) is used.

+
+ + +

NIO only. The version of the SSL protocols to use. If + not specified, the default is "TLSv1,SSLv3,SSLv2Hello".

+
+ + +

The version of the SSL protocol to use. If not specified, + the default is "TLS".

+
+ + +

The maximum number of intermediate certificates that will be allowed + when validating client certificates. If not specified, the default value + of 5 will be used.

+
+ + +

The algorithm to use for truststore. If not specified, the default + value returned by + javax.net.ssl.TrustManagerFactory.getDefaultAlgorithm() is + used.

+
+ + +

The trust store file to use to validate client certificates. The + default is the value of the javax.net.ssl.trustStore system + property. If neither this attribute nor the default system property is + set, no trust store will be configured.

+
+ + +

The password to access the trust store. The default is the value of the + javax.net.ssl.trustStorePassword system property. If that + property is null, no trust store password will be configured. If an + invalid trust store password is specified, a warning will be logged and an + attempt will be made to access the trust store without a password which + will skip validation of the trust store contents.

+
+ + +

The name of the truststore provider to be used for the server + certificate. The default is the value of the + javax.net.ssl.trustStoreProvider system property. If + that property is null, the value of keystoreProvider is used + as the default. If neither this attribute, the default system property nor + keystoreProvideris set, the list of registered providers is + traversed in preference order and the first provider that supports the + truststoreType is used. +

+
+ + +

The type of key store used for the trust store. The default is the + value of the javax.net.ssl.trustStoreType system property. If + that property is null, the value of keystoreType is used as + the default.

+
+ +
+ +

When APR/native is enabled, the HTTPS connector will use a socket poller + for keep-alive, increasing scalability of the server. It also uses OpenSSL, + which may be more optimized than JSSE depending on the processor being used, + and can be complemented with many commercial accelerator components. Unlike + the HTTP connector, the HTTPS connector cannot use sendfile to optimize static + file processing.

+ +

The HTTPS APR/native connector has the same attributes than the HTTP + APR/native connector, but adds OpenSSL specific ones. For the full details on + using OpenSSL, please refer to OpenSSL documentations and the many books + available for it (see the Official OpenSSL + website). The SSL specific attributes for the APR/native connector are: +

+ + + + +

See + the mod_ssl documentation.

+
+ + +

See + the mod_ssl documentation.

+
+ + +

See + the mod_ssl documentation.

+
+ + +

See + the mod_ssl documentation.

+
+ + +

See + the mod_ssl documentation.

+
+ + +

Name of the file that contains the concatenated certificates for the + trusted certificate authorities. The format is PEM-encoded.

+
+ + +

Name of the directory that contains the certificates for the trusted + certificate authorities. The format is PEM-encoded.

+
+ + +

Name of the file that contains the concatenated certificate revocation + lists for the certificate authorities. The format is PEM-encoded.

+
+ + +

Name of the directory that contains the certificate revocation lists + for the certificate authorities. The format is PEM-encoded.

+
+ + +

Name of the file that contains concatenated certifcates for the + certificate authorities which form the certifcate chain for the server + certificate. The format is PEM-encoded.

+
+ + +

Name of the file that contains the server certificate. The format is + PEM-encoded.

+
+ + +

Name of the file that contains the server private key. The format is + PEM-encoded. The default value is the value of "SSLCertificateFile" and in + this case both certificate and private key have to be in this file (NOT + RECOMMENDED).

+
+ + +

Ciphers which may be used for communicating with clients. The default + is "ALL", with other acceptable values being a list of ciphers, with ":" + used as the delimiter (see OpenSSL documentation for the list of ciphers + supported).

+
+ + +

Pass phrase for the encrypted private key. If "SSLPassword" is not + provided, the callback function should prompt for the pass phrase.

+
+ + +

Protocol which may be used for communicating with clients. The default + is "all", with other acceptable values being "SSLv2", "SSLv3", "TLSv1" + and "SSLv2+SSLv3".

+
+ + +

Ask client for certificate. The default is "none", meaning the client + will not have the opportunity to submit a certificate. Other acceptable + values include "optional", "require" and "optionalNoCA".

+
+ + +

Maximum verification depth for client certificates. The default is + "10".

+
+ +
+ +

For more information, see the + SSL Configuration HOW-TO.

+ +
+ + +

Below is a small chart that shows how the connectors differentiate.

+ + Java Blocking Connector Java Nio Blocking Connector APR Connector + Classname Http11Protocol Http11NioProtocol Http11AprProtocol + Tomcat Version 3.x 4.x 5.x 6.x 6.x 5.5.x 6.x + Support Polling NO YES YES + Polling Size N/A Unlimited - Restricted by mem Unlimited - Configurable + Read HTTP Request Blocking Non Blocking Blocking + Read HTTP Body Blocking Sim Blocking Blocking + Write HTTP Response Blocking Sim Blocking Blocking + SSL Support Java SSL Java SSL OpenSSL + SSL Handshake Blocking Non blocking Blocking + Max Connections maxThreads See polling size See polling size + + + + +
+
+ + + + +
diff --git a/webapps/docs/config/index.xml b/webapps/docs/config/index.xml new file mode 100644 index 000000000000..d99e3a15b699 --- /dev/null +++ b/webapps/docs/config/index.xml @@ -0,0 +1,95 @@ + + + +]> + + + &project; + + + Craig R. McClanahan + Overview + + + + + +
+ +

This manual contains reference information about all of the configuration +directives that can be included in a conf/server.xml file to +configure the behavior of the Tomcat 7 Servlet/JSP container. It does not +attempt to describe which configuration directives should be used to perform +specific tasks - for that, see the various HOW-TO documents on the +main index page.

+ +

The Tomcat configuration files support Apache Ant style variable +substitution. A system property with the name propname may be +used in a configuration file using the syntax ${propname}. All +system properties are available including those set using the -D +syntax, those automatically made available by the JVM and those configured in +the $CATALINA_BASE/conf/catalina.properties file. +

+ +

The configuration element descriptions are organized into the following +major categories:

+
    +
  • Top Level Elements - <Server> is the + root element of the entire configuration file, while + <Service> represents a group of Connectors that is + associated with an Engine.
  • +
  • Connectors - Represent the interface between external + clients sending requests to (and receiving responses from) a particular + Service.
  • +
  • Containers - Represent components whose function is to + process incoming requests, and create the corresponding responses. + An Engine handles all requests for a Service, a Host handles all requests + for a particular virtual host, and a Context handles all requests for a + specific web application.
  • +
  • Nested Components - Represent elements that can be + nested inside the element for a Container. Some elements can be nested + inside any Container, while others can only be nested inside a + Context.
  • +
+ +

For each element, the corresponding documentation follows this general +outline:

+
    +
  • Introduction - Overall description of this particular + component. There will be a corresponding Java interface (in + the org.apache.catalina package) that is implemented by one + or more standard implementations.
  • +
  • Attributes - The set of attributes that are legal for + this element. Generally, this will be subdivided into Common + attributes that are supported by all implementations of the corresponding + Java interface, and Standard Implementation attributes that are + specific to a particular Java class that implements this interface. + The names of required attributes are bolded.
  • +
  • Nested Components - Enumerates which of the Nested + Components can be legally nested within this element.
  • +
  • Special Features - Describes the configuration of a large + variety of special features (specific to each element type) that are + supported by the standard implementation of this interface.
  • +
+ +
+ + + +
diff --git a/webapps/docs/config/jar-scanner.xml b/webapps/docs/config/jar-scanner.xml new file mode 100644 index 000000000000..91d8128c8776 --- /dev/null +++ b/webapps/docs/config/jar-scanner.xml @@ -0,0 +1,118 @@ + + + +]> + + + &project; + + + The Jar Scanner Component + + + + +
+ +
+ +
+ +

The Jar Scanner element represents the component that is + used to scan the web application for JAR files. It is typically used during + web application start to identify configuration files such as TLDs or + web-fragment.xml files that must be processed as part of the web application + initialisation.

+ +

A Jar Scanner element MAY be nested inside a + Context component. If it is not included, + a default Jar Scanner configuration will be created automatically, which + is sufficient for most requirements.

+ +
+ + +
+ + + +

All implementations of Jar Scanner + support the following attributes:

+ + + + +

Java class name of the implementation to use. This class must + implement the org.apache.tomcat.JarScanner interface. + If not specified, the standard value (defined below) will be used.

+
+ +
+ +
+ + + + +

The standard implementation of Jar Scanner is + org.apache.tomcat.util.scan.StandardJarScanner. + It supports the following additional attributes (in addition to the + common attributes listed above):

+ + + + +

If true, the full web application classpath, including the shared and + common classloaders will be scanned for Jar files in addition to the + web application. The default is true.

+
+ + +

If true, any files found on the classpath will be checked to see if + they are Jar files rather than relying on the file extension being + .jar. The default is false

+
+ + +

If true, any directories found on the classpath will be checked to see + if are expanded Jar files. The default is false

+
+ +
+ +
+ + +
+ + +
+

No components may be nested inside a Jar Scanner element. +

+
+ + +
+

No special features are associated with a Jar Scanner + element.

+
+ + + +
diff --git a/webapps/docs/config/listeners.xml b/webapps/docs/config/listeners.xml new file mode 100644 index 000000000000..289091946ff7 --- /dev/null +++ b/webapps/docs/config/listeners.xml @@ -0,0 +1,325 @@ + + + +]> + + + &project; + + + The LifeCycle Listener Component + + + + +
+ +
+ +
+ +

A Listener element defines a component that performs + actions when specific events occur, usually Tomcat starting or Tomcat + stopping.

+ +

Listeners may be nested inside a Server, + Engine, Host or + Context. Some Listeners are only intended to be + nested inside specific elements. These constraints are noted in the + documentation below.

+ +
+ +
+ + + +

All implementations of Listener + support the following attributes:

+ + + + +

Java class name of the implementation to use. This class must + implement the org.apache.catalina.LifecycleListener + interface.

+
+ +
+ +
+ + + +

Unlike most Catalina components, there are several standard + Listener implementations available. As a result, + the className attribute MUST be used to select the + implementation you wish to use.

+ +

APR Lifecycle Listener (org.apache.catalina.core.AprLifecycleListener)

+ +

The APR Lifecycle Listener checks for the presence of + the APR/native library and loads the library if it is present. For more + information see the APR/native guide.

+ +

This listener must only be nested within Server + elements.

+ +

The following additional attributes are supported by the APR + Lifecycle Listener:

+ + + + +

Name of the SSLEngine to use. off: Do not use SSL, on: Use SSL but no + specific ENGINE. The default value is on. This initializes the + native SSL engine, which must be enabled in the APR/native connector by + the use of the SSLEnabled attribute.

+

See the Official OpenSSL website + for more details on supported SSL hardware engines and manufacturers. +

+
+ + +

Entropy source used to seed the SSLEngine's PRNG. The default value + is builtin. On development systems, you may want to set + this to /dev/urandom to allow quicker start times.

+
+ +
+ +

Jasper Listener (org.apache.catalina.core.JasperListener)

+ +

The Jasper Listener initializes the Jasper 2 JSP engine + before any web applications that may use it are loaded. For more + information on the Jasper 2 JSP engine see the + Jasper How To.

+ +

This listener must only be nested within Server + elements.

+ +

No additional attributes are supported by the Jasper Listener + .

+ +

Server Lifecycle Listener + (org.apache.catalina.mbeans.ServerLifecycleListener)

+ +

The Server Lifecycle Listener initializes the + MBeanServer for the MBeans that may be used to manager Tomcat via JMX. + Without this listener, none of the Tomcat MBeans will be available.

+ +

This listener must only be nested within Server + elements.

+ +

No additional attributes are supported by the Server Lifecycle + Listener.

+ +

Global Resources Lifecycle Listener + (org.apache.catalina.mbeans.GlobalResourcesLifecycleListener)

+ +

The Global Resources Lifecycle Listener initializes the + Global JNDI resources defined in server.xml as part of the Global Resources element. Without this + listener, none of the Global Resources will be available.

+ +

This listener must only be nested within Server + elements.

+ +

No additional attributes are supported by the Global Resources + Lifecycle Listener.

+ +

JMX Remote Lifecycle Listener + (org.apache.catalina.mbeans.JmxRemoteLifecycleListener)

+ +

This listener requires catalina-jmx-remote.jar to be placed + in $CATALINA_HOME/lib. This jar may be found in the extras + directory of the binary download area.

+ +

The JMX Remote Lifecycle Listener fixes the ports used by + the JMX/RMI Server making things much simpler if you need to connect + jconsole or a similar tool to a remote Tomcat instance that is running + behind a firewall. Only these ports are configured via the listener. The + remainder of the configuration is via the standard system properties for + configuring JMX. For further information on configuring JMX see + + Monitoring and Management Using JMX included with the Java SDK + documentation.

+ +

If this listener was configured in server.xml as: + +<Listener className="org.apache.catalina.mbeans.JmxRemoteLifecycleListener" + rmiRegistryPortPlatform="10001" rmiServerPortPlatform="10002" /> + + with the following system properties set (e.g. in setenv.sh): + +-Dcom.sun.management.jmxremote.password.file=$CATALINA_BASE/conf/jmxremote.password +-Dcom.sun.management.jmxremote.access.file=$CATALINA_BASE/conf/jmxremote.access +-Dcom.sun.management.jmxremote.ssl=false + + $CATALINA_BASE/conf/jmxremote.password containing: + +admin letmein + + $CATALINA_BASE/conf/jmxremote.access containing: + +admin readwrite + + then opening ports 10001 (RMI Registry) and 10002 (JMX/RMI Server) in your + firewall would enable jconsole to connect to a Tomcat instance running + behind a firewall using a connection string of the form: + +service:jmx:rmi://<hostname>:10002/jndi/rmi://<hostname>:10001/jmxrmi + + with a user name of admin and a password of + letmein. +

+ +

Note that the example above does not use SSL. JMX access should + be considered equivalent to administrative access and secured accordingly. +

+ +

This listener must only be nested within a Server + element.

+ +

The following additional attributes are supported by the JMX Remote + Lifecycle Listener:

+ + + + +

The port to be used by the JMX/RMI registry for the Platform MBeans. + The replaces the use of the + com.sun.management.jmxremote.port system property that + should not be set when using this valve.

+
+ + +

The port to be used by the Platform JMX/RMI server.

+
+ + +

Should any clients using these ports be forced to use local ports to + connect to the the JMX/RMI server. This is useful when tunnelling + connections over SSH or similar. Defaults to false.

+
+ +
+ +

JRE Memory Leak Prevention Listener + (org.apache.catalina.core.JreMemoryLeakPreventionListener)

+ +

The JRE Memory Leak Prevention Listener provides + work-arounds for known places where the Java Runtime environment uses + the context class loader to load a singleton as this will cause a memory + leak if a web application class loader happens to be the context class + loader at the time. The work-around is to initialise these singletons when + this listener starts as Tomcat's common class loader is the context class + loader at that time. It also provides work-arounds for known issues that + can result in locked JAR files.

+ +

This listener must only be nested within Server + elements.

+ +

The following additional attributes are supported by the JRE + Memory Leak Prevention Listener:

+ + + + +

Enables protection so that calls to + sun.awt.AppContext.getAppContext() triggered by a web + application do not result in a memory leak. Note that a call to this + method will be triggered as part of the web application stop process so + it is strongly recommended that this protection is enabled. The default + is true.

+
+ + +

Enables protection so that calls to + sun.misc.GC.requestLatency(long) triggered by a web + application do not result in a memory leak. Use of RMI is likely to + trigger a call to this method. A side effect of enabling this protection + is the creation of a thread named "GC Daemon". The protection uses + reflection to access internal Sun classes and may generate errors on + startup on non-Sun JVMs. The default is true.

+
+ + +

Enables protection so that the KeepAlive thread started by + sun.net.www.http.HttpClient does not result in a memory + leak. The thread is started the first time the HttpClient + class is used. Without this protection, if a web application uses this + class the KeepAlive thread will be configured with the thread's context + class loader set to the web application class loader which in turn will + trigger a memory leak on reload. Defaults to true.

+
+ + +

Enables protection so that usage of + javax.security.auth.Policy by a web application does not + result in a memory leak. The first access of this class will trigger the + static initializer that will retain a static reference to the context + class loader. The protection calls the getPolicy() method + of this class to ensure that the static initializer is not triggered by + a web application. Defaults to true.

+
+ + +

Enables protection so that any token poller thread initialized by + sun.security.pkcs11.SunPKCS11.initToken() does not + result in a memory leak. The thread is started depending on various + conditions as part of the initialization of the Java Cryptography + Architecture. Without the protection this can happen during Webapp + deployment when the MessageDigest for generating session IDs is + initialized. As a result the thread has the Webapp class loader as its + thread context class loader. Enabling the protection initializes JCA + early during Tomcat startup. Defaults to true.

+
+ + +

Enables protection so that reading resources from JAR files using + java.net.URLConnections does not result in the JAR file + being locked. Note that enabling this protection disables caching by + default for all resources obtained via + java.net.URLConnections. Caching may be re-enabled on a + case by case basis as required. Defaults to true.

+
+ + +

Enables protection so that parsing XML files within a web application + does not result in a memory leak. Note that memory profilers may not + display the GC root associated with this leak making it particularly + hard to diagnose. Defaults to true.

+
+ +
+ +
+ +
+ +
+ +

No element may be nested inside a Listener.

+ +
+ + + +
diff --git a/webapps/docs/config/loader.xml b/webapps/docs/config/loader.xml new file mode 100644 index 000000000000..635c9b19b234 --- /dev/null +++ b/webapps/docs/config/loader.xml @@ -0,0 +1,198 @@ + + + +]> + + + &project; + + + Craig R. McClanahan + The Loader Component + + + + +
+ +
+ +
+ +

The Loader element represents the web + application class loader that will be used to load Java + classes and resources for your web application. Such + a class loader must follow the requirements of the Servlet + Specification, and load classes from the following locations:

+
    +
  • From the /WEB-INF/classes directory inside your + web application.
  • +
  • From JAR files in the /WEB-INF/lib directory + inside your web application.
  • +
  • From resources made available by Catalina to all web + applications globally.
  • +
+ +

A Loader element MAY be nested inside a Context + component. If it is not included, a default Loader configuration will be + created automatically, which is sufficient for most requirements.

+ +

For a more in-depth description of the class loader hierarchy + that is implemented by Catalina, see the ClassLoader HowTo.

+ +
+

The description below uses the variable name $CATALINA_BASE to refer the + base directory against which most relative paths are resolved. If you have + not configured Tomcat for multiple instances by setting a CATALINA_BASE + directory, then $CATALINA_BASE will be set to the value of $CATALINA_HOME, + the directory into which you have installed Tomcat.

+
+ +
+ + +
+ + + +

All implementations of Loader + support the following attributes:

+ + + + +

Java class name of the implementation to use. This class must + implement the org.apache.catalina.Loader interface. + If not specified, the standard value (defined below) will be used.

+
+ + +

Set to true if you want the class loader to follow + the standard Java2 delegation model, and attempt to load classes from + parent class loaders before looking inside the web + application. Set to false (the default) to have the + class loader look inside the web application first, before asking + parent class loaders to find requested classes or resources.

+
+ + +

Set to true if you want Catalina to monitor classes in + /WEB-INF/classes/ and /WEB-INF/lib for + changes, and automatically reload the web application if a change + is detected. This feature is very useful during application + development, but it requires significant runtime overhead and is + not recommended for use on deployed production applications. You + can use the Manager web + application, however, to trigger reloads of deployed applications + on demand.

+ +

NOTE - The value for this property will be + inherited from the reloadable attribute you set on + the surrounding Context component, + and any value you explicitly set here will be replaced.

+
+ +
+ +
+ + + + +

The standard implementation of Loader is + org.apache.catalina.loader.WebappLoader. + It supports the following additional attributes (in addition to the + common attributes listed above):

+ + + + +

Java class name of the java.lang.ClassLoader + implementation class to use. If not specified, the default value is + org.apache.catalina.loader.WebappClassLoader. Custom + loaderClass implementations must extend + org.apache.catalina.loader.WebappClassLoader.

+
+ + +

Set to true if you want repositories outside + of WEB-INF/classes and WEB-INF/lib to + be searched first. Default value is false.

+
+ +
+ +
+ + + +

This implementation of Loader is + org.apache.catalina.loader.VirtualWebappLoader. + It extends WebappLoader and supports the following + additional attributes

+ + + + +

Additional repositories to search for resources. + Multiple elements can be joined using ; + as a separator.

+

Example: virtualClasspath="${catalina_base}/myapp_config"

+
+ + +

Set to true if you want the virtual + class path to be searched before + WEB-INF/classes and WEB-INF/lib. + Default value is false.

+

If searched before, resources located in the virtual + class path take precendence over resources with the same + name contained in the webapp.

+
+ +
+ +
+ + +
+ + +
+ +

No components may be nested inside a Loader element.

+ +
+ + +
+ + + +

A loader is associated with the log category based on its classname.

+ +
+ +
+ + + + + +
diff --git a/webapps/docs/config/manager.xml b/webapps/docs/config/manager.xml new file mode 100644 index 000000000000..140db6b157bc --- /dev/null +++ b/webapps/docs/config/manager.xml @@ -0,0 +1,478 @@ + + + +]> + + + &project; + + + Craig R. McClanahan + Yoav Shapira + The Manager Component + + + + +
+ +
+ +
+ +

The Manager element represents the session + manager that will be used to create and maintain HTTP sessions + as requested by the associated web application.

+ +

A Manager element MAY be nested inside a + Context component. If it is not included, + a default Manager configuration will be created automatically, which + is sufficient for most requirements.

+ +
+ + +
+ + + +

All implementations of Manager + support the following attributes:

+ + + + +

Java class name of the implementation to use. This class must + implement the org.apache.catalina.Manager interface. + If not specified, the standard value (defined below) will be used.

+
+ + +

Set to true to ask the session manager to enforce + the restrictions described in the Servlet Specification on + distributable applications (primarily, this would mean that all + session attributes must implement java.io.Serializable). + Set to false (the default) to not enforce these + restrictions.

+ +

NOTE - The value for this property is inherited + automatically based on the presence or absence of the + <distributable> element in the web application + deployment descriptor (/WEB-INF/web.xml).

+
+ +
+ +
+ + + + +

Tomcat provides two standard implementations of Manager + for use - the default one stores active sessions, while the optional one + stores active sessions that have been swapped out (in addition to saving + sessions across a restart of Tomcat) in a storage location that is selected + via the use of an appropriate Store nested element.

+ +

Standard Manager Implementation

+ +

The standard implementation of Manager is + org.apache.catalina.session.StandardManager. + It supports the following additional attributes (in addition to the + common attributes listed above):

+ + + + +

Name of the Message Digest algorithm used to calculate + session identifiers produced by this Manager. This value must + be supported by the java.security.MessageDigest class. + If not specified, the default value is "MD5".

+
+ + +

A String value that is utilized when seeding the random number + generator used to create session identifiers for this Manager. + If not specified, a semi-useful value is calculated, but a long + String value should be specified in security-conscious + environments.

+
+ + +

The maximum number of active sessions that will be created by + this Manager, or -1 (the default) for no limit.

+
+ + +

The initial maximum time interval, in seconds, + between client requests before a session is invalidated. A negative value + will result in sessions never timing out. If the attribute is not provided, + a default of 60 seconds is used.

+ +

This attribute provides the initial value whenever a + new session is created, but the interval may be dynamically + varied by a servlet via the + setMaxInactiveInterval method of the HttpSession object.

+
+ + +

Absolute or relative (to the work directory for this Context) + pathname of the file in which session state will be preserved + across application restarts, if possible. The default is + "SESSIONS.ser". See Restart + Persistence for more information. Restart persistence may be + disabled by setting this attribute to an empty string.

+
+ + +

Frequency of the session expiration, and related manager operations. + Manager operations will be done once for the specified amount of + backgrondProcess calls (i.e., the lower the amount, the more often the + checks will occur). The minimum value is 1, and the default value is 6. +

+
+ + +

Java class name of the java.util.Random + implementation class to use. If not specified, the default value is + java.security.SecureRandom.

+
+ + +

The length of session ids created by this Manager, excluding any + JVM route information used for load balancing. + The default is 16.

+
+ +
+ +

Persistent Manager Implementation

+ +

NOTE: You must set either the + org.apache.catalina.session.StandardSession.ACTIVITY_CHECK or + org.apache.catalina.STRICT_SERVLET_COMPLIANCE + system properties to true for + the persistent manager to work correctly.

+ +

The persistent implementation of Manager is + org.apache.catalina.session.PersistentManager. In + addition to the usual operations of creating and deleting sessions, a + PersistentManager has the capability to swap active (but + idle) sessions out to a persistent storage mechanism, as well as to save + all sessions across a normal restart of Tomcat. The actual persistent + storage mechanism used is selected by your choice of a + Store element nested inside the Manager + element - this is required for use of PersistentManager.

+ +

This implementation of Manager supports the following attributes in + addition to the Common Attributes + described earlier.

+ + + + +

Name of the Message Digest algorithm used to calculate + session identifiers produced by this Manager. This value must + be supported by the java.security.MessageDigest class. + If not specified, the default value is "MD5".

+
+ + +

Java class name of the implementation to use. This class must + implement the org.apache.catalina.Manager interface. + You must specify + org.apache.catalina.session.PersistentManager to use + this manager implementation.

+
+ + +

A String value that is utilized when seeding the random number + generator used to create session identifiers for this Manager. + If not specified, a semi-useful value is calculated, but a long + String value should be specified in security-conscious + environments.

+
+ + +

The maximum number of active sessions that will be created by + this Manager, or -1 (the default) for no limit.

+
+ + +

The time interval (in seconds) since the last access to a session + before it is eligible for being persisted to the session store, or + -1 to disable this feature. By default, this feature is + disabled.

+
+ + +

The time interval (in seconds) since the last access to a session + before it should be persisted to the session store, and + passivated out of the server's memory, or -1 to disable + this feature. If this feature is enabled, the time interval specified + here should be equal to or longer than the value specified for + maxIdleBackup. By default, this feature is disabled.

+
+ + +

The time interval (in seconds) since the last access to a session + before it will be eligible to be persisted to the session store, and + passivated out of the server's memory, or -1 for this + swapping to be available at any time. If specified, this value should + be less than that specified by maxIdleSwap. By default, + this value is set to -1.

+
+ + +

The initial maximum time interval, in seconds, + between client requests before a session is invalidated. A negative value + will result in sessions never timing out. If the attribute is not provided, + a default of 60 seconds is used.

+ +

This attribute provides the initial value whenever a + new session is created, but the interval may be dynamically + varied by a servlet via the + setMaxInactiveIntervalmethod of the HttpSession object.

+
+ + +

Java class name of the java.util.Random + implementation class to use. If not specified, the default value is + java.security.SecureRandom.

+
+ + +

Should all sessions be persisted and reloaded when Tomcat is shut + down and restarted (or when this application is reloaded)? By default, + this attribute is set to true.

+
+ + +

The length of session ids created by this Manager, excluding any + JVM route information used for load balancing. + The default is 16.

+
+ +
+ +

In order to successfully use a PersistentManager, you must nest inside + it a <Store> element, as described below.

+ +
+ + +
+ + +
+ +

Standard Manager Implementation

+ +

If you are using the Standard Manager Implementation + as described above, no elements may be nested inside your + <Manager> element.

+ +

Persistent Manager Implementation

+ +

If you are using the Persistent Manager Implementation + as described above, you MUST nest a + <Store> element inside, which defines the + characteristics of the persistent data storage. Two implementations + of the <Store> element are currently available, + with different characteristics, as described below.

+ +
File Based Store
+ +

The File Based Store implementation saves swapped out + sessions in individual files (named based on the session identifier) + in a configurable directory. Therefore, you are likely to encounter + scalability problems as the number of active sessions increases, and + this should primarily be considered a means to easily experiment.

+ +

To configure this, add a <Store> nested inside + your <Manager> element with the following attributes: +

+ + + + +

The interval (in seconds) between checks for expired sessions + among those sessions that are currently swapped out. By default, + this interval is set to 60 seconds (one minute).

+
+ + +

Java class name of the implementation to use. This class must + implement the org.apache.catalina.Store interface. You + must specify + org.apache.catalina.session.FileStore + to use this implementation.

+
+ + +

Absolute or relative (to the temporary work directory for this web + application) pathname of the directory into which individual session + files are written. If not specified, the temporary work directory + assigned by the container is utilized.

+
+ +
+ + +
JDBC Based Store
+ +

The JDBC Based Store implementation saves swapped out + sessions in individual rows of a preconfigured table in a database + that is accessed via a JDBC driver. With large numbers of swapped out + sessions, this implementation will exhibit improved performance over + the File Based Store described above.

+ +

To configure this, add a <Store> nested inside + your <Manager> element with the following attributes: +

+ + + + +

The interval (in seconds) between checks for expired sessions + among those sessions that are currently swapped out. By default, + this interval is set to 60 seconds (one minute).

+
+ + +

Java class name of the implementation to use. This class must + implement the org.apache.catalina.Store interface. You + must specify + org.apache.catalina.session.JDBCStore + to use this implementation.

+
+ + +

The connection URL that will be handed to the configured JDBC + driver to establish a connection to the database containing our + session table.

+
+ + +

Java class name of the JDBC driver to be used.

+
+ + +

Name of the database column, contained in the specified session + table, that contains the Engine, Host, and Web Application Context + name in the format /Engine/Host/Context.

+
+ + +

Name of the database column, contained in the specified + session table, that contains the serialized form of all session + attributes for a swapped out session. The column type must accept + a binary object (typically called a BLOB).

+
+ + +

Name of the database column, contained in the specified + session table, that contains the session identifier of the + swapped out session. The column type must accept character + string data of at least as many characters as are contained + in session identifiers created by Tomcat (typically 32).

+
+ + +

Name of the database column, contained in the specified + session table, that contains the lastAccessedTime + property of this session. The column type must accept a + Java long (64 bits).

+
+ + +

Name of the database column, contained in the specified + session table, that contains the maxInactiveInterval + property of this session. The column type must accept a + Java integer (32 bits).

+
+ + +

Name of the database table to be used for storing swapped out + sessions. This table must contain (at least) the database columns + that are configured by the other attributes of this element.

+
+ + +

Name of the database column, contained in the specified + session table, that contains a flag indicating whether this + swapped out session is still valid or not. The column type + must accept a single character.

+
+ +
+ +

Before attempting to use the JDBC Based Store for the first time, + you must create the table that will be used to store swapped out sessions. + Detailed SQL commands vary depending on the database you are using, but + a script like this will generally be required:

+ + +create table tomcat_sessions ( + session_id varchar(100) not null primary key, + valid_session char(1) not null, + max_inactive int not null, + last_access bigint not null, + app_name varchar(255), + session_data mediumblob, + KEY kapp_name(app_name) +); + + +

In order for the JDBC Based Store to successfully connect to your + database, the JDBC driver you configure must be visible to Tomcat's + internal class loader. Generally, that means you must place the JAR + file containing this driver into the $CATALINA_HOME/lib + directory.

+ +
+ + +
+ + + + +

Whenever Catalina is shut down normally and restarted, or when an + application reload is triggered, the standard Manager implementation + will attempt to serialize all currently active sessions to a disk + file located via the pathname attribute. All such saved + sessions will then be deserialized and activated (assuming they have + not expired in the mean time) when the application reload is completed.

+ +

In order to successfully restore the state of session attributes, + all such attributes MUST implement the java.io.Serializable + interface. You MAY cause the Manager to enforce this restriction by + including the <distributable> element in your web + application deployment descriptor (/WEB-INF/web.xml).

+ +
+ +
+ + + + + +
diff --git a/webapps/docs/config/project.xml b/webapps/docs/config/project.xml new file mode 100644 index 000000000000..f400f6cce593 --- /dev/null +++ b/webapps/docs/config/project.xml @@ -0,0 +1,86 @@ + + + + + Apache Tomcat 7 Configuration Reference + + + The Apache Tomcat Servlet/JSP Container + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/webapps/docs/config/realm.xml b/webapps/docs/config/realm.xml new file mode 100644 index 000000000000..1204be4b189d --- /dev/null +++ b/webapps/docs/config/realm.xml @@ -0,0 +1,740 @@ + + + +]> + + + &project; + + + Craig R. McClanahan + The Realm Component + + + + +
+ +
+ +
+ +

A Realm element represents a "database" of usernames, + passwords, and roles (similar to Unix groups) assigned + to those users. Different implementations of Realm allow Catalina to be + integrated into environments where such authentication information is already + being created and maintained, and then utilize that information to implement + Container Managed Security as described in the Servlet + Specification.

+ +

You may nest a Realm inside any Catalina container + Engine, Host, or + Context). In addition, Realms associated with + an Engine or a Host are automatically inherited by lower-level + containers, unless explicitly overridden.

+ +

For more in-depth information about container managed security in web + applications, as well as more information on configuring and using the + standard realm component implementations, please see the + Container-Managed Security Guide. +

+ +
+

The description below uses the variable name $CATALINA_BASE to refer the + base directory against which most relative paths are resolved. If you have + not configured Tomcat for multiple instances by setting a CATALINA_BASE + directory, then $CATALINA_BASE will be set to the value of $CATALINA_HOME, + the directory into which you have installed Tomcat.

+
+ +
+ + +
+ + + +

All implementations of Realm + support the following attributes:

+ + + + +

Java class name of the implementation to use. This class must + implement the org.apache.catalina.Realm interface.

+
+ +
+ +
+ + + + +

Unlike most Catalina components, there are several standard + Realm implementations available. As a result, + the className attribute MUST be used to select the + implementation you wish to use.

+ +

JDBC Database Realm (org.apache.catalina.realm.JDBCRealm)

+ +

The JDBC Database Realm connects Catalina to + a relational database, accessed through an appropriate JDBC driver, + to perform lookups of usernames, passwords, and their associated + roles. Because the lookup is done each time that it is required, + changes to the database will be immediately reflected in the + information used to authenticate new logins.

+ +

A rich set of additional attributes lets you configure the required + connection to the underlying database, as well as the table and + column names used to retrieve the required information:

+ + + + +

The database username to use when establishing the JDBC + connection.

+
+ + +

The database password to use when establishing the JDBC + connection.

+
+ + +

The connection URL to be passed to the JDBC driver when + establishing a database connection.

+
+ + +

The name of the MessageDigest algorithm used + to encode user passwords stored in the database. If not specified, + user passwords are assumed to be stored in clear-text.

+
+ + +

The charset for encoding digests. If not specified, the platform + default will be used.

+
+ + +

Fully qualified Java class name of the JDBC driver to be + used to connect to the authentication database.

+
+ + +

Name of the column, in the "user roles" table, which contains + a role name assigned to the corresponding user.

+
+ + +

Name of the column, in the "users" table, which contains + the user's credentials (i.e. password(. If a value for the + digest attribute is specified, this component + will assume that the passwords have been encoded with the + specified algorithm. Otherwise, they will be assumed to be + in clear text.

+
+ + +

Name of the column, in the "users" and "user roles" table, + that contains the user's username.

+
+ + +

Name of the "user roles" table, which must contain columns + named by the userNameCol and roleNameCol + attributes.

+
+ + +

Name of the "users" table, which must contain columns named + by the userNameCol and userCredCol + attributes.

+
+ +
+ +

See the Container-Managed Security Guide for more + information on setting up container managed security using the + JDBC Database Realm component.

+ + +

+ DataSource Database Realm (org.apache.catalina.realm.DataSourceRealm) +

+ +

The DataSource Database Realm connects Catalina to + a relational database, accessed through a JNDI named JDBC DataSource + to perform lookups of usernames, passwords, and their associated + roles. Because the lookup is done each time that it is required, + changes to the database will be immediately reflected in the + information used to authenticate new logins.

+ +

The JDBC Realm uses a single db connection. This requires that + realm based authentication be synchronized, i.e. only one authentication + can be done at a time. This could be a bottleneck for applications + with high volumes of realm based authentications.

+ +

The DataSource Database Realm supports simultaneous realm based + authentications and allows the underlying JDBC DataSource to + handle optimizations like database connection pooling.

+ +

A rich set of additional attributes lets you configure the name + of the JNDI JDBC DataSource, as well as the table and + column names used to retrieve the required information:

+ + + + +

The name of the JNDI JDBC DataSource for this Realm.

+
+ + +

The name of the MessageDigest algorithm used + to encode user passwords stored in the database. If not specified, + user passwords are assumed to be stored in clear-text.

+
+ + +

When the realm is nested inside a Context element, this allows the + realm to use a DataSource defined for the Context rather than a global + DataSource. If not specified, the default is false: use a + global DataSource.

+
+ + +

Name of the column, in the "user roles" table, which contains + a role name assigned to the corresponding user.

+
+ + +

Name of the column, in the "users" table, which contains + the user's credentials (i.e. password(. If a value for the + digest attribute is specified, this component + will assume that the passwords have been encoded with the + specified algorithm. Otherwise, they will be assumed to be + in clear text.

+
+ + +

Name of the column, in the "users" and "user roles" table, + that contains the user's username.

+
+ + +

Name of the "user roles" table, which must contain columns + named by the userNameCol and roleNameCol + attributes.

+
+ + +

Name of the "users" table, which must contain columns named + by the userNameCol and userCredCol + attributes.

+
+ +
+ +

See the + DataSource Realm HOW-TO for more information on setting up container + managed security using the DataSource Database Realm component.

+ + +

JNDI Directory Realm (org.apache.catalina.realm.JNDIRealm)

+ + +

The JNDI Directory Realm connects Catalina to + an LDAP Directory, accessed through an appropriate JNDI driver, + that stores usernames, passwords, and their associated + roles. Changes to the directory are immediately reflected in the + information used to authenticate new logins.

+ + +

The directory realm supports a variety of approaches to using + LDAP for authentication:

+ +
    +
  • The realm can either use a pattern to determine the + distinguished name (DN) of the user's directory entry, or search + the directory to locate that entry. +
  • + +
  • The realm can authenticate the user either by binding to the + directory with the DN of the user's entry and the password + presented by the user, or by retrieving the password from the + user's entry and performing a comparison locally. +
  • + +
  • Roles may be represented in the directory as explicit entries + found by a directory search (e.g. group entries of which the user + is a member), as the values of an attribute in the user's entry, + or both. +
  • +
+ +

A rich set of additional attributes lets you configure the + required behaviour as well as the connection to the underlying + directory and the element and attribute names used to retrieve + information from the directory:

+ + + + +

Microsoft Active Directory often returns referrals. + When iterating over NamingEnumerations these lead to + PartialResultExceptions. If you want us to ignore those exceptions, + set this attribute to "true". Unfortunately there's no stable way + to detect, if the Exceptions really come from an AD referral. + The default value is "false".

+
+ + +

If a socket connection can not be made to the provider at + the connectionURL an attempt will be made to use the + alternateURL.

+
+ + +

A string specifying the type of authentication to use. + "none", "simple", "strong" or a provider specific definition + can be used. If no value is given the providers default is used.

+
+ + +

A role name assigned to each successfully authenticated user in + addition to the roles retrieved from LDAP. If not specified, only + the roles retrieved via LDAP are used.

+
+ + +

The directory username to use when establishing a + connection to the directory for LDAP search operations. If not + specified an anonymous connection is made, which is often + sufficient unless you specify the userPassword + property.

+
+ + +

The directory password to use when establishing a + connection to the directory for LDAP search operations. If not + specified an anonymous connection is made, which is often + sufficient unless you specify the userPassword + property.

+
+ + +

The timeout in milliseconds to use when establishing the connection + to the LDAP directory. If not specified, a value of 5000 (5 seconds) is + used.

+
+ + +

The connection URL to be passed to the JNDI driver when + establishing a connection to the directory.

+
+ + +

Fully qualified Java class name of the factory class used + to acquire our JNDI InitialContext. By default, + assumes that the standard JNDI LDAP provider will be utilized.

+
+ + +

A string specifying how aliases are to be dereferenced during + search operations. The allowed values are "always", "never", + "finding" and "searching". If not specified, "always" is used.

+
+ + +

The digest algorithm to apply to the plaintext password offered + by the user before comparing it with the value retrieved from the + directory. Valid values are those accepted for the algorithm name + by the java.security.MessageDigest class. If not + specified the plaintext password is assumed to be retrieved. Not + required unless userPassword is specified

+
+ + +

A string specifying the security protocol to use. If not given + the providers default is used.

+
+ + +

How do we handle JNDI referrals? Allowed values are + "ignore", "follow", or "throw" (see javax.naming.Context.REFERRAL + for more information). + Microsoft Active Directory often returns referrals. + If you need to follow them set referrals to "follow". + Caution: if your DNS is not part of AD, the LDAP client lib might try + to resolve your domain name in DNS to find another LDAP server.

+
+ + +

The base directory entry for performing role searches. If + not specified the top-level element in the directory context + will be used.

+
+ + +

The name of the attribute that contains role names in the + directory entries found by a role search. In addition you can + use the userRoleName property to specify the name + of an attribute, in the user's entry, containing additional + role names. If roleName is not specified a role + search does not take place, and roles are taken only from the + user's entry.

+
+ + +

The LDAP filter expression used for performing role + searches. Use {0} to substitute the + distinguished name (DN) of the user, and/or {1} to + substitute the username. If not specified a role search does + not take place and roles are taken only from the attribute in + the user's entry specified by the userRoleName + property.

+
+ + +

Set to true if you want to search the entire + subtree of the element specified by the roleBase + property for role entries associated with the user. The + default value of false causes only the top level + to be searched.

+
+ + +

The base element for user searches performed using the + userSearch expression. Not used if you are using + the userPattern expression.

+
+ + +

Name of the attribute in the user's entry containing the + user's password. If you specify this value, JNDIRealm will + bind to the directory using the values specified by + connectionName and + connectionPassword properties, and retrieve the + corresponding attribute for comparison to the value specified + by the user being authenticated. If you do + not specify this value, JNDIRealm will + attempt a simple bind to the directory using the DN of the + user's entry and the password presented by the user, with a + successful bind being interpreted as an authenticated + user.

+
+ + +

Pattern for the distinguished name (DN) of the user's + directory entry, with {0} marking where the + actual username should be inserted. You can use this property + instead of userSearch, userSubtree + and userBase when the distinguished name contains + the username and is otherwise the same for all users.

+
+ + +

The name of an attribute in the user's directory entry + containing zero or more values for the names of roles assigned + to this user. In addition you can use the + roleName property to specify the name of an + attribute to be retrieved from individual role entries found + by searching the directory. If userRoleName is + not specified all the roles for a user derive from the role + search.

+
+ + +

The LDAP filter expression to use when searching for a + user's directory entry, with {0} marking where + the actual username should be inserted. Use this property + (along with the userBase and + userSubtree properties) instead of + userPattern to search the directory for the + user's entry.

+
+ + +

Set to true if you want to search the entire + subtree of the element specified by the userBase + property for the user's entry. The default value of + false causes only the top level to be searched. + Not used if you are using the userPattern + expression.

+
+ +
+ +

See the Container-Managed Security Guide for more + information on setting up container managed security using the + JNDI Directory Realm component.

+ + +

UserDatabase Realm (org.apache.catalina.realm.UserDatabaseRealm)

+ +

The UserDatabase Realm is a Realm implementation + that is based on a UserDatabase resource made available through the global + JNDI resources configured for this Tomcat instance.

+ +

The Memory Based Realm implementation supports the following + additional attributes:

+ + + + +

The name of the resource that this realm will use for user, password + and role information.

+
+ +
+ +

See the + Container-Managed Security Guide for more + information on setting up container managed security using the UserDatabase + Realm component and the + JNDI resources how-to for more + information on how to configure a UserDatabase resource.

+ +

Memory Based Realm (org.apache.catalina.realm.MemoryRealm)

+ +

The Memory Based Realm is a simple Realm implementation + that reads user information from an XML format, and represents it as a + collection of Java objects in memory. This implementation is intended + solely to get up and running with container managed security - it is NOT + intended for production use. As such, there are no mechanisms for + updating the in-memory collection of users when the content of the + underlying data file is changed.

+ +

The Memory Based Realm implementation supports the following + additional attributes:

+ + + + +

The digest algorithm used to store passwords in non-plaintext + formats. Valid values are those accepted for the algorithm name by the + java.security.MessageDigest class. If not specified, + passwords are stored in clear text.

+
+ + +

Absolute or relative (to $CATALINA_BASE) pathname to the XML file + containing our user information. See below for details on the + XML element format required. If no pathname is specified, the + default value is conf/tomcat-users.xml.

+
+ +
+ +

The XML document referenced by the pathname attribute must + conform to the following requirements:

+
    +
  • The root (outer) element must be <tomcat-users>. +
  • +
  • Each authorized user must be represented by a single XML element + <user>, nested inside the root element.
  • +
  • Each <user> element must have the following + attributes: +
      +
    • name - Username of this user (must be unique + within this file).
    • +
    • password - Password of this user (in + clear text).
    • +
    • roles - Comma-delimited list of the role names + assigned to this user.
    • +
  • +
+ +

See the Container-Managed Security Guide for more + information on setting up container managed security using the + Memory Based Realm component.

+ +

JAAS Realm (org.apache.catalina.realm.JAASRealm)

+ +

JAASRealm is an implementation of the Tomcat + Realm interface that authenticates users through the Java + Authentication & Authorization Service (JAAS) framework which is now + provided as part of the standard J2SE API.

+ +

Using JAASRealm gives the developer the ability to combine practically + any conceivable security realm with Tomcat's CMA.

+ +

JAASRealm is prototype for Tomcat of the JAAS-based J2EE authentication + framework for J2EE v1.4, based on the JCP Specification Request + 196 to enhance container-managed security and promote 'pluggable' + authentication mechanisms whose implementations would be + container-independent.

+ +

Based on the JAAS login module and principal + (see javax.security.auth.spi.LoginModule and + javax.security.Principal), you can develop your own security + mechanism or wrap another third-party mechanism for integration with the CMA + as implemented by Tomcat.

+ +

The JAAS Realm implementation supports the following additional + attributes:

+ + + + +

The name of the application as configured in your login configuration + file + (JAAS LoginConfig).

+
+ + +

A comma-separated list of the names of the classes that you have made + for your user Principals.

+
+ + +

A comma-separated list of the names of the classes that you have made + for your role Principals.

+
+ + +

Instructs JAASRealm to use the context class loader for loading the + user-specified LoginModule class and associated + Principal classes. The default value is true, + which is backwards-compatible with the way Tomcat 5 works. To load + classes using the container's classloader, specify + false.

+
+ +
+ +

See the Container-Managed Security + Guide for more information on setting up container managed security + using the JAAS Realm component.

+ +

Combined Realm (org.apache.catalina.realm.CombinedRealm)

+ +

CombinedRealm is an implementation of the Tomcat + Realm interface that authenticates users through one or more + sub-Realms.

+ +

Using CombinedRealm gives the developer the ability to combine multiple + Realms of the same or different types. This can be used to authenticate + against different sources, provide fall back in case one Realm fails or for + any other purpose that requires multiple Realms.

+ +

Sub-realms are defined by nesting Realm elements inside the + Realm element that defines the CombinedRealm. Authentication + will be attempted against each Realm in the order they are + listed. Authentication against any Realm will be sufficient to authenticate + the user.

+ +

The CombinedRealm implementation does not support any additional + attributes.

+ +

See the Container-Managed Security + Guide for more information on setting up container managed security + using the CombinedRealm component.

+ +

LockOut Realm (org.apache.catalina.realm.LockOutRealm)

+ +

LockOutRealm is an implementation of the Tomcat + Realm interface that extends the CombinedRealm to provide lock + out functionality to provide a user lock out mechanism if there are too many + failed authentication attempts in a given period of time.

+ +

To ensure correct operation, there is a reasonable degree of + synchronization in this Realm.

+ +

This Realm does not require modification to the underlying Realms or the + associated user storage mechanisms. It achieves this by recording all failed + logins, including those for users that do not exist. To prevent a DOS by + deliberating making requests with invalid users (and hence causing this + cache to grow) the size of the list of users that have failed authentication + is limited.

+ +

Sub-realms are defined by nesting Realm elements inside the + Realm element that defines the LockOutRealm. Authentication + will be attempted against each Realm in the order they are + listed. Authentication against any Realm will be sufficient to authenticate + the user.

+ +

The LockOutRealm implementation supports the following additional + attributes.

+ + + + +

If a failed user is removed from the cache because the cache is too + big before it has been in the cache for at least this period of time (in + seconds) a warning message will be logged. Defaults to 3600 (1 hour).

+
+ + +

Number of users that have failed authentication to keep in cache. Over + time the cache will grow to this size and may not shrink. Defaults to + 1000.

+
+ + +

The number of times in a row a user has to fail authentication to be + locked out. Defaults to 5.

+
+ + +

The time (in seconds) a user is locked out for after too many + authentication failures. Defaults to 300 (5 minutes).

+
+ +
+ +

See the Container-Managed Security + Guide for more information on setting up container managed security + using the LockOutRealm component.

+ +
+ + +
+ + +
+ +

CombinedRealm Implementation

+ +

If you are using the CombinedRealm Implementation or a Realm + that extends the CombinedRealm, e.g. the LockOutRealm, + <Realm> elements may be nested inside it.

+ +

Other Realm Implementations

+ +

No other Realm implementation supports nested components.

+ +
+ + +
+ +

See Single Sign On for information about + configuring Single Sign On support for a virtual host.

+ +
+ + + + + +
diff --git a/webapps/docs/config/resources.xml b/webapps/docs/config/resources.xml new file mode 100644 index 000000000000..3ce7ec32ea2e --- /dev/null +++ b/webapps/docs/config/resources.xml @@ -0,0 +1,119 @@ + + + +]> + + + &project; + + + Remy Maucherat + The Resources Component + + + + +
+ +
+ +
+ +

The Resources element represents the web + application static resources, from which classes will be loaded, + HTML, JSP and the other static files will be served. This allows the webapp + to reside on various mediums other than the filesystem, like compressed + in a WAR file, in a JDBC database, or in a more advanced versioning + repository.

+ +

A unified caching engine is provided for all accesses to the webapp + resources made by the servlet container and web applications which use the + container provided mechanisms to access such resources, such as classloader + access, access through the ServletContext interface, or native + access through the DirectoryContext interface.

+ +

Note: Running a webapp with non-filesystem based + Resources implementations is only possible when the webapp does not + rely on direct filesystem access to its own resources, and uses the methods + in the ServletContext interface to access them.

+ +

A Resources element MAY be nested inside a + Context component. If it is not included, + a default filesystem based Resources will be created automatically, + which is sufficient for most requirements.

+ +
+ + +
+ + + +

All implementations of Resources + support the following attributes:

+ + + + +

Java class name of the implementation to use. This class must + implement the javax.naming.directory.DirContext interface. + It is recommended for optimal functionality and performance, + but not mandatory, that the class extend + org.apache.naming.resources.BaseDirContext, as well as + use the special object types provided in the + org.apache.naming.resources for returned objects. + If not specified, the standard value (defined below) will be used.

+
+ +
+ +
+ + + + +

The standard implementation of Resources is + org.apache.naming.resources.FileDirContext, and + is configured by its parent Context element.

+ +
+ + +
+ + +
+ +

No components may be nested inside a Resources element.

+ +
+ + +
+ +

No special features are associated with a Resources + element.

+ +
+ + + + + +
diff --git a/webapps/docs/config/server.xml b/webapps/docs/config/server.xml new file mode 100644 index 000000000000..42e979afe923 --- /dev/null +++ b/webapps/docs/config/server.xml @@ -0,0 +1,124 @@ + + + +]> + + + &project; + + + Craig R. McClanahan + The Server Component + + + + +
+ +
+ +
+ +

A Server element represents the entire Catalina + servlet container. Therefore, it must be the single outermost element + in the conf/server.xml configuration file. Its attributes + represent the characteristics of the servlet container as a whole.

+ +
+ + +
+ + + +

All implementations of Server + support the following attributes:

+ + + + +

Java class name of the implementation to use. This class must + implement the org.apache.catalina.Server interface. + If no class name is specified, the standard implementation will + be used.

+
+ + +

The TCP/IP address on which this server waits for a shutdown + command. If no address is specified, localhost is used.

+
+ + +

The TCP/IP port number on which this server waits for a shutdown + command. Set to -1 to disable the shutdown port. Note: + Disabling the shutdown port will prevent shutdown.bat and catalina.bat + from stopping the Tomcat process on Windows operating systems. Operating + systems that use the *.sh scripts will not be affected by disabling the + shutdown port.

+
+ + +

The command string that must be received via a TCP/IP connection + to the specified port number, in order to shut down Tomcat.

+
+ +
+ +
+ + + +

The standard implementation of Server is + org.apache.catalina.core.StandardServer. + It supports the following additional attributes (in addition to the + common attributes listed above):

+ + + + +
+ +
+ + +
+ +

The following components may be nested inside a Server + element:

+ + +
+ + +
+ +

There are no special features associated with a Server. +

+ +
+ + + + +
diff --git a/webapps/docs/config/service.xml b/webapps/docs/config/service.xml new file mode 100644 index 000000000000..68d6deeb2ea1 --- /dev/null +++ b/webapps/docs/config/service.xml @@ -0,0 +1,110 @@ + + + +]> + + + &project; + + + Craig R. McClanahan + The Service Component + + + + +
+ +
+ +
+ +

A Service element represents the combination of one or + more Connector components that share a single + Engine component for processing incoming + requests. One or more Service elements may be nested + inside a Server element.

+ +
+ + +
+ + + +

All implementations of Service + support the following attributes:

+ + + + +

Java class name of the implementation to use. This class must + implement the org.apache.catalina.Service interface. + If no class name is specified, the standard implementation will + be used.

+
+ + +

The display name of this Service, which will + be included in log messages if you utilize standard Catalina + components. The name of each Service that is + associated with a particular Server + must be unique.

+
+ +
+ +
+ + + +

The standard implementation of Service is + org.apache.catalina.core.StandardService. + It supports the following additional attributes (in addition to the + common attributes listed above):

+ + + + + +
+ +
+ + +
+ +

The only components that may be nested inside a Service + element are one or more Connector elements, + followed by exactly one Engine element.

+ +
+ + +
+ +

There are no special features associated with a Service. +

+ +
+ + + + +
diff --git a/webapps/docs/config/systemprops.xml b/webapps/docs/config/systemprops.xml new file mode 100644 index 000000000000..591bc7c2f6f4 --- /dev/null +++ b/webapps/docs/config/systemprops.xml @@ -0,0 +1,511 @@ + + + +]> + + + &project; + + + System Properties + + + + +
+ +
+ +
+

The following sections list the system properties that may be set to modify + the default Tomcat behaviour.

+
+ +
+ + +

Set this to a fully qualified name of a class that implements + org.apache.tomcat.util.IntrospectionUtils.PropertySource. + Required to have a public constructor with no arguments.

+

Use this to add a property source, that will be invoked when ${parameter} + denoted parameters are found in the XML files that Tomcat parses.

+
+
+ +
+ +
+ + + +

If true, the clustering module will attempt to use DNS to + resolve any host names provided in the cluster configuration. If not + specified, the default value of false will be used.

+
+ +
+ +
+ +
+ + + +

If true, when coercing expressions to numbers + "" and null will be coerced to zero as required + by the specification. If not specified, the default value of + true will be used.

+
+ + +

If true, when parsing expressions, identifiers will not be + checked to ensure that they conform to the Java Language Specification for + Java identifiers. If not specified, the default value of + false will be used.

+
+ +
+
+ +
+ + + +

The name of the variable to use for the expression language expression + factory. If not specified, the default value of + _el_expressionfactory will be used.

+
+ + +

The name of the variable to use for the instance manager factory. If + not specified, the default value of _jsp_instancemanager will + be used.

+
+ + +

If true, the requirement to have the object referenced in + jsp:getProperty action to be previously "introduced" + to the JSP processor, as specified in the chapter JSP.5.3 of JSP 2.0 and + later specifications, is enforced. If not specified, the specification + compliant default of true will be used.

+
+ + +

If false the requirements for escaping quotes in JSP + attributes will be relaxed so that an unescaped quote will not + cause an error. If not specified, the specification compliant default of + true will be used.

+
+ + +

If true, any tag buffer that expands beyond + org.apache.jasper.Constants.DEFAULT_TAG_BUFFER_SIZE will be + destroyed and a new buffer created of the default size. If not specified, + the default value of false will be used.

+
+ + +

If true, a ThreadLocal PageContext pool will + be used. If not specified, the default value of true will be + used.

+
+ + +

The size of the ThreadLocal PageContext. If not specified, + the default value of 8 will be used.

+
+ + +

The base class of the Servlets generated from the JSPs. If not + specified, the default value of + org.apache.jasper.runtime.HttpJspBase will be used.

+
+ + +

The name of the service method called by the base class. If not + specified, the default value of _jspService will be used.

+
+ + +

The name of the ServletContext attribute that provides the classpath + for the JSP. If not specified, the default value of + org.apache.catalina.jsp_classpath will be used.

+
+ + +

The name of the request attribute for <jsp-file> + element of a servlet definition. If present on a request, this overrides + the value returned by request.getServletPath() to select the + JSP page to be executed. If not specified, the default value of + org.apache.catalina.jsp_file will be used.

+
+ + +

The name of the query parameter that causes the JSP engine to just + pregenerate the servlet but not invoke it. If not specified, the default + value of org.apache.catalina.jsp_precompile will be used.

+
+ + +

The default package name for compiled jsp pages. If not specified, the + default value of org.apache.jsp will be used.

+
+ + +

The default package name for tag handlers generated from tag files. If + not specified, the default value of org.apache.jsp.tag will + be used.

+
+ + +

The servlet context attribute under which the alternate deployment + descriptor for this web application is stored. If not specified, the + default value of org.apache.catalina.deploy.alt_dd will + be used.

+
+ + +

Prefix to use for generated temporary variable names. If not specified, + the default value of _jspx_temp will be used.

+
+ + +

If true, the instance manager is used to obtain tag + handler instances. If not specified, false will be used.

+
+ +
+ +
+ + +
+ + + + +

If this is true or if a security manager is in use a new + facade object will be created for each request. If not specified, the + default value of false will be used.

+
+ + +

If this is true the '\' character will be permitted as a + path delimiter. If not specified, the default value of false + will be used.

+
+ + +

If this is true '%2F' and '%5C' will be permitted as path + delimiters. If not specified, the default value of false will + be used.

+
+ +
+ +
+ + +
+ + + + +

If this is true the default values will be changed for: +

    +
  • org.apache.catalina.core.ApplicationContext.GET_RESOURCE_REQUIRE_SLASH
  • +
  • org.apache.catalina.core.ApplicationDispatcher.WRAP_SAME_OBJECT
  • +
  • org.apache.catalina.core.StandardHostValve.ACCESS_SESSION
  • +
  • org.apache.catalina.session.StandardSession.ACTIVITY_CHECK
  • +
  • org.apache.catalina.session.StandardSession.LAST_ACCESS_AT_START
  • +
  • org.apache.tomcat.util.http.ServerCookie.ALWAYS_ADD_EXPIRES.
  • +
  • org.apache.tomcat.util.http.ServerCookie.FWD_SLASH_IS_SEPARATOR.
  • +
  • org.apache.tomcat.util.http.ServerCookie.STRICT_NAMING.
  • +
  • The tldNamespaceAware attribute of any + Context element.
  • +
  • The tldValidation attribute of any + Context element.
  • +
  • The xmlNamespaceAware attribute of any + Context element.
  • +
  • The xmlValidation attribute of any + Context element.
  • +
+

+

Note that changing a number of the above defaults is likely to break + the majority of systems as some browsers are unable to correctly handle + the cookie headers that result from a strict adherence to the + specifications. Defaults, regardless of whether or not they have been + changed by setting + org.apache.catalina.STRICT_SERVLET_COMPLIANCE can always be + overridden by explicitly setting the appropriate system property or element + attribute.

+
+ + +

If this is true then + a call to Response.getWriter() if no character encoding + has been specified will result in subsequent calls to + Response.getCharacterEncoding() returning + ISO-8859-1 and the Content-Type response header + will include a charset=ISO-8859-1 component. (SRV.15.2.22.1) +
+ If not specified, the default specification compliant value of + true will be used.

+
+ + +

If this is true then the path passed to + ServletContext.getResource() or + ServletContext.getResourceAsStream() must start with + "/". If false, code like + getResource("myfolder/myresource.txt") will work. If + org.apache.catalina.STRICT_SERVLET_COMPLIANCE is set to + true, the default of this setting will be true, + else the default value will be false.

+
+ + +

If this is true then any wrapped request or response + object passed to an application dispatcher will be checked to ensure that + it has wrapped the original request or response. If + org.apache.catalina.STRICT_SERVLET_COMPLIANCE is set to + true, the default of this setting will be true, + else the default value will be false.

+
+ + +

If this is true Tomcat will allow = + characters when parsing unquoted cookie values. If false, + cookie values containing = will be terminated when the + = is encountered and the remainder of the cookie value will + be dropped. If not specified, the default value specification compliant + value of false will be used.

+
+ + +

If this is true Tomcat will allow HTTP separators in + cookie names and values. If not specified, the default specification + compliant value of false will be used.

+
+ + +

If this is true Tomcat will always add an expires + parameter to a SetCookie header even for cookies with version greater than + zero. This is to work around a known IE6 and IE7 bug that causes IE to + ignore the Max-Age parameter in a SetCookie header. If not specified, the + default value will be used. If + org.apache.catalina.STRICT_SERVLET_COMPLIANCE is set to + true, the default of this setting will be false, + else the default value will be true.

+
+ + +

If this is true then the / (forward slash) character will + be treated as a separator. Note that this character is frequently used in + cookie path attributes and some browsers will fail to process a cookie if + the path attribute is quoted as is required by a strict adherence to the + specifications. This is highly likely to break session tracking using + cookies. If not specified, the default value will be used. If + org.apache.catalina.STRICT_SERVLET_COMPLIANCE is set to + true, the default of this setting will be true, + else the default value will be false.

+
+ + +

If this is true then the requirements of the Servlet specification + that Cookie names must adhere to RFC2109 (no use of separators) will be + enforced. If not specified, the default value will be used. If + org.apache.catalina.STRICT_SERVLET_COMPLIANCE is set to + true, the default of this setting will be true, + else the default value will be false.

+
+ +
+ +
+ + +
+ + + + +

An alternative name for the single sign on session cookie. Defaults to + JSESSIONIDSSO.

+
+ + +

If this is true, every request that is associated with a + session will cause the session's last accessed time to be updated + regardless of whether or not the request explicitly accesses the session. + If org.apache.catalina.STRICT_SERVLET_COMPLIANCE is set to + true, the default of this setting will be true, + else the default value will be false.

+
+ + +

If this is true, Tomcat will track the number of active + requests for each session. When determining if a session is valid, any + session with at least one active request will always be considered valid. + If org.apache.catalina.STRICT_SERVLET_COMPLIANCE is set to + true, the default of this setting will be true, + else the default value will be false.

+
+ + +

If this is true, the last accessed time for sessions will + be calculated from the beginning of the previous request. If + false, the last accessed time for sessions will be calculated + from the end of the previous request. This also affects how the idle time + is calculated. If + org.apache.catalina.STRICT_SERVLET_COMPLIANCE is set to + true, the default of this setting will be true, + else the default value will be false.

+
+ +
+ +
+ +
+ + + + +

When the memory limit of records has been reached the system needs to determine what action to take. + Currently there are three actions that can be taken: +

    +
  • int OVERFLOW_DROP_LAST = 1 - the record that caused the overflow will be dropped and not logged
  • +
  • int OVERFLOW_DROP_FIRST = 2 - the record that is next in line to be logged will be dropped to make room for the latest record on the queue
  • +
  • int OVERFLOW_DROP_FLUSH = 3 - suspend the thread while the queue empties out and flushes the entries to the write buffer
  • +
  • int OVERFLOW_DROP_CURRENT = 4 - drop the current log entry
  • +
+ Default value is 1 (OVERFLOW_DROP_LAST). +

+
+ + +

The max number of log records that the async logger will keep in memory. When this limit is reached and a new record is being logged by the + JULI framework the system will take an action based on the org.apache.juli.AsyncOverflowDropType setting. + The default value is 10000 records.
+ This number represents the global number of records, not on a per handler basis. +

+
+ + +

The poll interval in milliseconds for the asynchronous logger thread in milliseconds. + If the log queue is empty, the async thread will issue a poll(poll interval) + in order to not wake up to often. + The default value is 1000 milliseconds. +

+
+ +
+ +
+ +
+ + + +

If this is + true, custom HTTP status messages will be used within HTTP + headers. If a custom message is specified that is not valid for use in an + HTTP header (as defined by RFC2616) then the custom message will be + ignored and the default message used. If not specified, the default value + of false will be used.

+
+ + +

If this is false it will override the + useNaming attribute for all + Context elements.

+
+ + +

Provides a default value for the jvmRoute attribute of the + Engine element. It does not override the value + configured on the Engine element.

+
+ + +

The URL for the catalina.properties configuration file.

+
+ + +

If true, the String cache is enabled for + ByteChunk. If not specified, the default value of + false will be used.

+
+ + +

If true, the String cache is enabled for + CharChunk. If not specified, the default value of + false will be used.

+
+ + +

The number of times toString() must be called before the + cache is activated. If not specified, the default value of + 20000 will be used.

+
+ + +

The size of the String cache. If not specified, the default value of + 200 will be used.

+
+ + +

The maximum length of String that will be cached. If not specified, the + default value of 128 will be used.

+
+ + +

The size of the cache to use parsed and formatted date value. If not + specified, the default value of 1000 will be used.

+
+ + +

If true, use a shared selector for servlet write/read. If + not specified, the default value of true will be used.

+
+ + +

If true, the server will exit if an exception happens + during the server initialization phase. The default is false.

+
+ + +
+ +
+ + + +
diff --git a/webapps/docs/config/valve.xml b/webapps/docs/config/valve.xml new file mode 100644 index 000000000000..d4d3a9c74d50 --- /dev/null +++ b/webapps/docs/config/valve.xml @@ -0,0 +1,735 @@ + + + +]> + + + &project; + + + Craig R. McClanahan + The Valve Component + + + + +
+ +
+ +
+ +

A Valve element represents a component that will be + inserted into the request processing pipeline for the associated + Catalina container (Engine, + Host, or Context). + Individual Valves have distinct processing capabilities, and are + described individually below.

+ +
+

The description below uses the variable name $CATALINA_BASE to refer the + base directory against which most relative paths are resolved. If you have + not configured Tomcat for multiple instances by setting a CATALINA_BASE + directory, then $CATALINA_BASE will be set to the value of $CATALINA_HOME, + the directory into which you have installed Tomcat.

+
+ +
+ + +
+ + + +

The Access Log Valve creates log files in the same + format as those created by standard web servers. These logs can later + be analyzed by standard log analysis tools to track page hit counts, + user session activity, and so on. The files produces by this Valve + are rolled over nightly at midnight. This Valve + may be associated with any Catalina container (Context, + Host, or Engine), and + will record ALL requests processed by that container.

+ +

Some requests may be handled by Tomcat before they are passed to a + container. These include redirects from /foo to /foo/ and the rejection of + invalid requests. Where Tomcat can identify the Context that + would have handled the request, the request/response will be logged in the + AccessLog(s) associated Context, Host + and Engine. Where Tomcat cannot identify the + Context that would have handled the request, e.g. in cases + where the URL is invalid, Tomcat will look first in the Engine, + then the default Host for the Engine and finally + the ROOT (or default) Context for the default Host + for an AccessLog implementation. Tomcat will use the first + AccessLog implementation found to log those requests that are + rejected before they are passed to a container.

+ +
+ + + +

The Access Log Valve supports the following + configuration attributes:

+ + + + +

Java class name of the implementation to use. This MUST be set to + org.apache.catalina.valves.AccessLogValve to use the + default access log valve.

+
+ + +

Absolute or relative pathname of a directory in which log files + created by this valve will be placed. If a relative path is + specified, it is interpreted as relative to $CATALINA_BASE. If + no directory attribute is specified, the default value is "logs" + (relative to $CATALINA_BASE).

+
+ + +

A formatting layout identifying the various information fields + from the request and response to be logged, or the word + common or combined to select a + standard format. See below for more information on configuring + this attribute. Note that the optimized access does only support + common and combined as the value for this + attribute.

+
+ + +

The prefix added to the start of each log file's name. If not + specified, the default value is "access_log.". To specify no prefix, + use a zero-length string.

+
+ + +

Set to true to convert the IP address of the remote + host into the corresponding host name via a DNS lookup. Set to + false to skip this lookup, and report the remote IP + address instead.

+
+ + +

The suffix added to the end of each log file's name. If not + specified, the default value is "". To specify no suffix, + use a zero-length string.

+
+ + +

Flag to determine if log rotation should occur. + If set to false, then this file is never rotated and + fileDateFormat is ignored. Use with caution! + Default value: true +

+
+ + +

Turns on conditional logging. If set, requests will be + logged only if ServletRequest.getAttribute() is + null. For example, if this value is set to + junk, then a particular request will only be logged + if ServletRequest.getAttribute("junk") == null. + The use of Filters is an easy way to set/unset the attribute + in the ServletRequest on many different requests. +

+
+ + +

Allows a customized date format in the access log file name. + The date format also decides how often the file is rotated. + If you wish to rotate every hour, then set this value + to: yyyy-MM-dd.HH +

+
+ + +

Flag to determine if logging will be buffered. + If set to false, then access logging will be written after each + request. Default value: true +

+
+ +
+ +

Values for the pattern attribute are made up of literal + text strings, combined with pattern identifiers prefixed by the "%" + character to cause replacement by the corresponding variable value from + the current request and response. The following pattern codes are + supported:

+
    +
  • %a - Remote IP address
  • +
  • %A - Local IP address
  • +
  • %b - Bytes sent, excluding HTTP headers, or '-' if zero
  • +
  • %B - Bytes sent, excluding HTTP headers
  • +
  • %h - Remote host name (or IP address if + resolveHosts is false)
  • +
  • %H - Request protocol
  • +
  • %l - Remote logical username from identd (always returns + '-')
  • +
  • %m - Request method (GET, POST, etc.)
  • +
  • %p - Local port on which this request was received
  • +
  • %q - Query string (prepended with a '?' if it exists)
  • +
  • %r - First line of the request (method and request URI)
  • +
  • %s - HTTP status code of the response
  • +
  • %S - User session ID
  • +
  • %t - Date and time, in Common Log Format
  • +
  • %u - Remote user that was authenticated (if any), else '-'
  • +
  • %U - Requested URL path
  • +
  • %v - Local server name
  • +
  • %D - Time taken to process the request, in millis
  • +
  • %T - Time taken to process the request, in seconds
  • +
  • %I - current request thread name (can compare later with stacktraces)
  • +
+ +

+ There is also support to write information from the cookie, incoming + header, the Session or something else in the ServletRequest. + It is modeled after the apache syntax: +

    +
  • %{xxx}i for incoming headers
  • +
  • %{xxx}o for outgoing response headers
  • +
  • %{xxx}c for a specific cookie
  • +
  • %{xxx}r xxx is an attribute in the ServletRequest
  • +
  • %{xxx}s xxx is an attribute in the HttpSession
  • +
+

+ + +

The shorthand pattern name common (which is also the + default) corresponds to '%h %l %u %t "%r" %s %b'.

+ +

The shorthand pattern name combined appends the + values of the Referer and User-Agent headers, + each in double quotes, to the common pattern + described in the previous paragraph.

+ +
+ +
+ + +
+ + + +

The Remote Address Filter allows you to compare the + IP address of the client that submitted this request against one or more + regular expressions, and either allow the request to continue + or refuse to process the request from this client. A Remote Address + Filter can be associated with any Catalina container + (Engine, Host, or + Context), and must accept any request + presented to this container for processing before it will be passed on.

+ +

The syntax for regular expressions is different than that for + 'standard' wildcard matching. Tomcat uses the java.util.regex + package. Please consult the Java documentation for details of the + expressions supported.

+ +
+ + + +

The Remote Address Filter supports the following + configuration attributes:

+ + + + +

Java class name of the implementation to use. This MUST be set to + org.apache.catalina.valves.RemoteAddrValve.

+
+ + +

A comma-separated list of regular expression patterns + that the remote client's IP address is compared to. If this attribute + is specified, the remote address MUST match for this request to be + accepted. If this attribute is not specified, all requests will be + accepted UNLESS the remote address matches a deny + pattern.

+
+ + +

A comma-separated list of regular expression patterns + that the remote client's IP address is compared to. If this attribute + is specified, the remote address MUST NOT match for this request to be + accepted. If this attribute is not specified, request acceptance is + governed solely by the accept attribute.

+
+ +
+ +
+ +
+ + +
+ + + +

The Remote Host Filter allows you to compare the + hostname of the client that submitted this request against one or more + regular expressions, and either allow the request to continue + or refuse to process the request from this client. A Remote Host + Filter can be associated with any Catalina container + (Engine, Host, or + Context), and must accept any request + presented to this container for processing before it will be passed on.

+ +

The syntax for regular expressions is different than that for + 'standard' wildcard matching. Tomcat uses the java.util.regex + package. Please consult the Java documentation for details of the + expressions supported.

+ +
+ + + +

The Remote Host Filter supports the following + configuration attributes:

+ + + + +

Java class name of the implementation to use. This MUST be set to + org.apache.catalina.valves.RemoteHostValve.

+
+ + +

A comma-separated list of regular expression patterns + that the remote client's hostname is compared to. If this attribute + is specified, the remote hostname MUST match for this request to be + accepted. If this attribute is not specified, all requests will be + accepted UNLESS the remote hostname matches a deny + pattern.

+
+ + +

A comma-separated list of regular expression patterns + that the remote client's hostname is compared to. If this attribute + is specified, the remote hostname MUST NOT match for this request to be + accepted. If this attribute is not specified, request acceptance is + governed solely by the accept attribute.

+
+ +
+ +
+ +
+ + +
+ + + +

The Single Sign On Vale is utilized when you wish to give users + the ability to sign on to any one of the web applications associated with + your virtual host, and then have their identity recognized by all other + web applications on the same virtual host.

+ +

See the Single Sign On special + feature on the Host element for more information.

+ +
+ + + + +

The Single Sign On Valve supports the following + configuration attributes:

+ + + + +

Java class name of the implementation to use. This MUST be set to + org.apache.catalina.authenticator.SingleSignOn.

+
+ + +

Default false. Flag to determine whether each request needs to be + reauthenticated to the security Realm. If "true", this + Valve uses cached security credentials (username and password) to + reauthenticate to the Realm each request associated + with an SSO session. If "false", the Valve can itself authenticate + requests based on the presence of a valid SSO cookie, without + rechecking with the Realm.

+
+ + +

Sets the host domain to be used for sso cookies.

+
+ +
+ +
+ + +
+ + +
+ + + +

The Basic Authenticator Valve is automatically added to + any Context that is configured to use BASIC + authentication.

+ +

If any non-default settings are required, the valve may be configured + within Context element with the required + values.

+ +
+ + + +

The Basic Authenticator Valve supports the following + configuration attributes:

+ + + + +

Java class name of the implementation to use. This MUST be set to + org.apache.catalina.authenticator.BasicAuthenticator.

+
+ + +

Controls if the session ID is changed if a session exists at the + point where users are authenticated. This is to prevent session fixation + attacks. If not set, the default value of true will be + used.

+
+ + +

Controls the caching of pages that are protected by security + constraints. Setting this to false may help work around + caching issues in some browsers but will also cause secured pages to be + cached by proxies which will almost certainly be a security issue. + securePagesWithPragma offers an alternative, secure, + workaround for browser caching issues. If not set, the default value of + true will be used.

+
+ + +

Controls the caching of pages that are protected by security + constraints. Setting this to false may help work around + caching issues in some browsers by using + Cache-Control: private rather than the default of + Pragma: No-cache and Cache-control: No-cache. + If not set, the default value of true will be used.

+
+ +
+ +
+ +
+ + +
+ + + +

The Digest Authenticator Valve is automatically added to + any Context that is configured to use DIGEST + authentication.

+ +

If any non-default settings are required, the valve may be configured + within Context element with the required + values.

+ +
+ + + +

The Digest Authenticator Valve supports the following + configuration attributes:

+ + + + +

Java class name of the implementation to use. This MUST be set to + org.apache.catalina.authenticator.DigestAuthenticator.

+
+ + +

Controls if the session ID is changed if a session exists at the + point where users are authenticated. This is to prevent session fixation + attacks. If not set, the default value of true will be + used.

+
+ + +

Controls the caching of pages that are protected by security + constraints. Setting this to false may help work around + caching issues in some browsers but will also cause secured pages to be + cached by proxies which will almost certainly be a security issue. + securePagesWithPragma offers an alternative, secure, + workaround for browser caching issues. If not set, the default value of + true will be used.

+
+ + +

Controls the caching of pages that are protected by security + constraints. Setting this to false may help work around + caching issues in some browsers by using + Cache-Control: private rather than the default of + Pragma: No-cache and Cache-control: No-cache. + If not set, the default value of true will be used.

+
+ +
+ +
+ +
+ + +
+ + + +

The Form Authenticator Valve is automatically added to + any Context that is configured to use FORM + authentication.

+ +

If any non-default settings are required, the valve may be configured + within Context element with the required + values.

+ +
+ + + +

The Form Authenticator Valve supports the following + configuration attributes:

+ + + + +

Java class name of the implementation to use. This MUST be set to + org.apache.catalina.authenticator.FormAuthenticator.

+
+ + +

Controls if the session ID is changed if a session exists at the + point where users are authenticated. This is to prevent session fixation + attacks. If not set, the default value of true will be + used.

+
+ + +

Character encoding to use to read the username and password parameters + from the request. If not set, the encoding of the request body will be + used.

+
+ + +

Controls the caching of pages that are protected by security + constraints. Setting this to false may help work around + caching issues in some browsers but will also cause secured pages to be + cached by proxies which will almost certainly be a security issue. + securePagesWithPragma offers an alternative, secure, + workaround for browser caching issues. If not set, the default value of + true will be used.

+
+ + +

Controls the caching of pages that are protected by security + constraints. Setting this to false may help work around + caching issues in some browsers by using + Cache-Control: private rather than the default of + Pragma: No-cache and Cache-control: No-cache. + If not set, the default value of true will be used.

+
+ +
+ +
+ +
+ + +
+ + + +

The SSL Authenticator Valve is automatically added to + any Context that is configured to use SSL + authentication.

+ +

If any non-default settings are required, the valve may be configured + within Context element with the required + values.

+ +
+ + + +

The SSL Authenticator Valve supports the following + configuration attributes:

+ + + + +

Java class name of the implementation to use. This MUST be set to + org.apache.catalina.authenticator.SSLAuthenticator.

+
+ + +

Controls if the session ID is changed if a session exists at the + point where users are authenticated. This is to prevent session fixation + attacks. If not set, the default value of true will be + used.

+
+ + +

Controls the caching of pages that are protected by security + constraints. Setting this to false may help work around + caching issues in some browsers but will also cause secured pages to be + cached by proxies which will almost certainly be a security issue. + securePagesWithPragma offers an alternative, secure, + workaround for browser caching issues. If not set, the default value of + true will be used.

+
+ + +

Controls the caching of pages that are protected by security + constraints. Setting this to false may help work around + caching issues in some browsers by using + Cache-Control: private rather than the default of + Pragma: No-cache and Cache-control: No-cache. + If not set, the default value of true will be used.

+
+ +
+ +
+ +
+ + +
+ + + +

Tomcat port of + mod_remoteip, + this valve replaces the apparent client remote IP address and hostname for + the request with the IP address list presented by a proxy or a load balancer + via a request headers (e.g. "X-Forwarded-For").

+ +

Another feature of this valve is to replace the apparent scheme + (http/https), server port and request.secure with the scheme presented + by a proxy or a load balancer via a request header + (e.g. "X-Forwarded-Proto").

+ +

This Valve may be used at the Engine, Host or + Context level as required. Normally, this Valve would be used + at the Engine level.

+ +

If used in conjunction with Remote Address/Host valves then this valve + should be defined first to ensure that the correct client IP address is + presented to the Remote Address/Host valves.

+ +
+ + + +

The Remote IP Valve supports the + following configuration attributes:

+ + + + +

Java class name of the implementation to use. This MUST be set to + org.apache.catalina.valves.RemoteIpValve.

+
+ + +

Name of the HTTP Header read by this valve that holds the list of + traversed IP addresses starting from the requesting client. If not + specified, the default of x-forwarded-for is used.

+
+ + +

List of internal proxies' IP addresses as comma separated regular + expressions. If they appear in the remoteIpHeader + value, they will be trusted and will not appear in the + proxiesHeader value. If not specified the default value + of 10\.\d{1,3}\.\d{1,3}\.\d{1,3}, 192\.168\.\d{1,3}\.\d{1,3}, + 169\.254\.\d{1,3}\.\d{1,3}, 127\.\d{1,3}\.\d{1,3}\.\d{1,3} will + be used.

+
+ + +

Name of the HTTP header created by this valve to hold the list of + proxies that have been processed in the incoming + remoteIpHeader. If not specified, the default of + x-forwarded-by is used.

+
+ + +

List of trusted proxies' IP addresses as comma separated regular + expressions. If they appear in the remoteIpHeader + value, they will be trusted and will appear in the + proxiesHeader value. If not specified, no proxies will + be trusted.

+
+ + +

Name of the HTTP Header read by this valve that holds the protocol + used by the client to connect to the proxy. If not specified, the + default of null is used.

+
+ + +

Value of the protocolHeader to indicate that it is + an HTTPS request. If not specified, the default of https is + used.

+
+ + +

Value returned by ServletRequest.getServerPort() + when the protocolHeader indicates http + protocol. If not specified, the default of 80 is + used.

+
+ + +

Value returned by ServletRequest.getServerPort() + when the protocolHeader indicates https + protocol. If not specified, the default of 443 is + used.

+
+ +
+ +
+ +
+ + + + + +
diff --git a/webapps/docs/connectors.xml b/webapps/docs/connectors.xml new file mode 100644 index 000000000000..b5680eccd5c8 --- /dev/null +++ b/webapps/docs/connectors.xml @@ -0,0 +1,81 @@ + + + +]> + + + &project; + + + Remy Maucherat + Connectors How To + + + + +
+ +
+ +
+ +

Choosing a connector to use with Tomcat can be difficult. This page will +list the connectors which are supported with this Tomcat release, and will +hopefully help you make the right choice according to your needs.

+ +
+ +
+ +

The HTTP connector is setup by default with Tomcat, and is ready to use. This +connector features the lowest latency and best overall performance.

+ +

For clustering, a HTTP load balancer with support for web sessions stickiness +must be installed to direct the traffic to the Tomcat servers. Tomcat supports mod_proxy +(on Apache HTTP Server 2.x, and included by default in Apache HTTP Server 2.2) as the load balancer. +It should be noted that the performance of HTTP proxying is usually lower than the +performance of AJP, so AJP clustering is often preferable.

+ +
+ +
+ +

When using a single server, the performance when using a native webserver in +front of the Tomcat instance is most of the time significantly worse than a +standalone Tomcat with its default HTTP connector, even if a large part of the web +application is made of static files. If integration with the native webserver is +needed for any reason, an AJP connector will provide faster performance than +proxied HTTP. AJP clustering is the most efficient from the Tomcat perspective. +It is otherwise functionally equivalent to HTTP clustering.

+ +

The native connectors supported with this Tomcat release are: +

    +
  • JK 1.2.x with any of the supported servers
  • +
  • mod_proxy on Apache HTTP Server 2.x (included by default in Apache HTTP Server 2.2), +with AJP enabled
  • +
+

+ +

Other native connectors supporting AJP may work, but are no longer supported.

+ +
+ + + +
diff --git a/webapps/docs/default-servlet.xml b/webapps/docs/default-servlet.xml new file mode 100644 index 000000000000..1107f3f026ac --- /dev/null +++ b/webapps/docs/default-servlet.xml @@ -0,0 +1,320 @@ + + + +]> + + + &project; + + + Tim Funk + Default Servlet Reference + + + + +
+ +
+ +
+The default servlet is the servlet which serves static resources as well +as serves the directory listings (if directory listings are enabled). + +
+ +
+It is declared globally in $CATALINA_BASE/conf/web.xml. +By default here is it's declaration: + + <servlet> + <servlet-name>default</servlet-name> + <servlet-class> + org.apache.catalina.servlets.DefaultServlet + </servlet-class> + <init-param> + <param-name>debug</param-name> + <param-value>0</param-value> + </init-param> + <init-param> + <param-name>listings</param-name> + <param-value>true</param-value> + </init-param> + <load-on-startup>1</load-on-startup> + </servlet> + +... + + <servlet-mapping> + <servlet-name>default</servlet-name> + <url-pattern>/</url-pattern> + </servlet-mapping> + + + +So by default, the default servlet is loaded at webapp startup and +directory listings are enabled and debugging is turned off. +
+ +
+The DefaultServlet allows the following initParamters: + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
debug + Debugging level. It is not very useful unless you are a tomcat + developer. As + of this writing, useful values are 0, 1, 11, 1000. +
listings + If no welcome file is present, can a directory listing be + shown? + value may be true or false +
+ Welcome files are part of the servlet api. +
+ WARNING: Listings of directories containing many entries are + expensive. Multiple requests for large directory listings can consume + significant proportions of server resources. +
readmeFile + If a directory listing is presented, a readme file may also + be presented with the listing. This file is inserted as is + so it may contain HTML. default value is null +
globalXsltFile + If you wish to customize your directory listing, you + can use an XSL transformation. This value is an absolute + file name which be used for all directory listings. + This can be overridden per context and/or per directory. See + contextXsltFile and localXsltFile + below. The format of the xml is shown below. +
contextXsltFile + You may also customize your directory listing by context by + configuring contextXsltFile. This should be a context + relative path (e.g.: /path/to/context.xslt). This + overrides globalXsltFile. If this value is present but a + file does not exist, then globalXsltFile will be used. If + globalXsltFile does not exist, then the default + directory listing will be shown. +
localXsltFile + You may also customize your directory listing by directory by + configuring localXsltFile. This should be a relative + file name in the directory where the listing will take place. + This overrides globalXsltFile and + contextXsltFile. If this value is present but a file + does not exist, then contextXsltFile will be used. If + contextXsltFile does not exist, then + globalXsltFile will be used. If + globalXsltFile does not exist, then the default + directory listing will be shown. +
input + Input buffer size (in bytes) when reading + resources to be served. [2048] +
output + Output buffer size (in bytes) when writing + resources to be served. [2048] +
readonly + Is this context "read only", so HTTP commands like PUT and + DELETE are rejected? [true] +
fileEncoding + File encoding to be used when reading static resources. + [platform default] +
sendfileSize + If the connector used supports sendfile, this represents the minimal + file size in KB for which sendfile will be used. Use a negative value + to always disable sendfile. [48] +
useAcceptRanges + If true, the Accept-Ranges header will be set when appropriate for the + response. [true] +
+
+ +
+

You can override DefaultServlet with you own implementation and use that +in your web.xml declaration. If you +can understand what was just said, we will assume you can read the code +to DefaultServlet servlet and make the appropriate adjustments. (If not, +then that method isn't for you) +

+

+You can use either localXsltFile or +globalXsltFile and DefaultServlet will create +an xml document and run it through an xsl transformation based +on the values provided in localXsltFile and +globalXsltFile. localXsltFile is first +checked, followed by globalXsltFile, then default +behaviors takes place. +

+ +

+Format: + + <listing> + <entries> + <entry type='file|dir' urlPath='aPath' size='###' date='gmt date'> + fileName1 + </entry> + <entry type='file|dir' urlPath='aPath' size='###' date='gmt date'> + fileName2 + </entry> + ... + </entries> + <readme></readme> + </listing> + +

    +
  • size will be missing if type='dir'
  • +
  • Readme is a CDATA entry
  • +
+

+The following is a sample xsl file which mimics the default tomcat behavior: + +<?xml version="1.0"?> + +<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform" + version="1.0"> + + <xsl:output method="xhtml" encoding="iso-8859-1" indent="no"/> + + <xsl:template match="listing"> + <html> + <head> + <title> + Sample Directory Listing For + <xsl:value-of select="@directory"/> + </title> + <style> + h1{color : white;background-color : #0086b2;} + h3{color : white;background-color : #0086b2;} + body{font-family : sans-serif,Arial,Tahoma; + color : black;background-color : white;} + b{color : white;background-color : #0086b2;} + a{color : black;} HR{color : #0086b2;} + </style> + </head> + <body> + <h1>Sample Directory Listing For + <xsl:value-of select="@directory"/> + </h1> + <hr size="1" /> + <table cellspacing="0" + width="100%" + cellpadding="5" + align="center"> + <tr> + <th align="left">Filename</th> + <th align="center">Size</th> + <th align="right">Last Modified</th> + </tr> + <xsl:apply-templates select="entries"/> + </table> + <xsl:apply-templates select="readme"/> + <hr size="1" /> + <h3>Apache Tomcat/7.0</h3> + </body> + </html> + </xsl:template> + + + <xsl:template match="entries"> + <xsl:apply-templates select="entry"/> + </xsl:template> + + <xsl:template match="readme"> + <hr size="1" /> + <pre><xsl:apply-templates/></pre> + </xsl:template> + + <xsl:template match="entry"> + <tr> + <td align="left"> + <xsl:variable name="urlPath" select="@urlPath"/> + <a href="{$urlPath}"> + <tt><xsl:apply-templates/></tt> + </a> + </td> + <td align="right"> + <tt><xsl:value-of select="@size"/></tt> + </td> + <td align="right"> + <tt><xsl:value-of select="@date"/></tt> + </td> + </tr> + </xsl:template> + +</xsl:stylesheet> + + +
+ +
+Use web.xml in each individual webapp. See the security section of the +Servlet specification. + +
+ + + +
diff --git a/webapps/docs/deployer-howto.xml b/webapps/docs/deployer-howto.xml new file mode 100644 index 000000000000..633196b668cf --- /dev/null +++ b/webapps/docs/deployer-howto.xml @@ -0,0 +1,335 @@ + + + +]> + + + &project; + + + Allistair Crossley + Tomcat Web Application Deployment + + + + +
+ +
+ +
+

+ Deployment is the term used for the process of installing a web + application (either a 3rd party WAR or your own custom web application) + into the Tomcat server. +

+

+ Web application deployment may be accomplished in a number of ways + within the Tomcat server.

+
    +
  • Statically; the web application is setup before Tomcat is started
  • +
  • + Dynamically; in conjunction with the Tomcat Manager web application or + manipulating already deployed web applications +
  • +
+

+ The Tomcat Manager is a tool that allows URL-based web application + deployment features. There is also a tool called the Client Deployer, + which is a command shell based script that interacts with the Tomcat + Manager but provides additional functionality such as compiling and + validating web applications as well as packaging web application into + web application resource (WAR) files. +

+
+ +
+

+ There is no installation required for static deployment of web + applications as this is provided out of the box by Tomcat. Nor is any + installation required for deployment functions with the Tomcat Manager, + although some configuration is required as detailed in the + Tomcat Manager manual. An installation is however required if you wish + to use the Tomcat Client Deployer (TCD). +

+

+ The TCD is not packaged with the Tomcat core + distribution, and must therefore be downloaded separately from + the Downloads area. The download is usually labelled + apache-tomcat-7.0.x-deployer. +

+

+ TCD has prerequisites of Apache Ant 1.6.2+ and a Java installation. + Your environment should define an ANT_HOME environment value pointing to + the root of your Ant installation, and a JAVA_HOME value pointing to + your Java installation. Additionally, you should ensure Ant's ant + command, and the Java javac compiler command run from the command shell + that your operating system provides. +

+
    +
  1. Download the TCD distribution
  2. +
  3. + The TCD package need not be extracted into any existing Tomcat + installation, it can be extracted to any location. +
  4. +
  5. Read Using the + Tomcat Client Deployer
  6. +
+
+ +
+

+ In talking about deployment of web applications, the concept of a + Context is required to be understood. A Context is what Tomcat + calls a web application. +

+

+ In order to configure a Context within Tomcat a Context Descriptor + is required. A Context Descriptor is simply an XML file that contains + Tomcat related configuration for a Context, e.g naming resources or + session manager configuration. In earlier versions of + Tomcat the content of a Context Descriptor configuration was often stored within + Tomcat's primary configuration file server.xml but this is now + discouraged (although it currently still works). +

+

+ Context Descriptors not only help Tomcat to know how to configure + Contexts but other tools such as the Tomcat Manager and TCD often use + these Context Descriptors to perform their roles properly. +

+

+ The locations for Context Descriptors are: +

+
    +
  1. $CATALINA_BASE/conf/[enginename]/[hostname]/context.xml
  2. +
  3. $CATALINA_BASE/webapps/[webappname]/META-INF/context.xml
  4. +
+

+ Files in (1) are named [webappname].xml but files in (2) are named + context.xml. If a Context Descriptor is not provided for a Context, + Tomcat configures the Context using default values. +

+
+ +
+

+ If you are not interested in using the Tomcat Manager, or TCD, + then you'll need to deploy your web applications + statically to Tomcat, followed by a Tomcat startup. The location you + deploy web applications to for this type of deployment is called the + appBase which is specified per Host. You either copy a + so-called exploded web application, i.e non-compressed, to this + location, or a compressed web application resource .WAR file. +

+

+ The web applications present in the location specified by the Host's + (default Host is "localhost") appBase attribute (default + appBase is "$CATALINA_BASE/webapps") will be deployed on Tomcat startup + only if the Host's deployOnStartup attribute is "true". +

+

+ The following deployment sequence will occur on Tomcat startup in that + case: +

+
    +
  1. Any Context Descriptors will be deployed first.
  2. +
  3. + Exploded web applications not referenced by any Context + Descriptor will then be deployed. If they have an associated + .WAR file in the appBase and it is newer than the exploded web application, + the exploded directory will be removed and the webapp will be + redeployed from the .WAR +
  4. +
  5. .WAR files will be deployed
  6. +
+

+ Note again that for each deployed web application, a + Context Descriptor will be created unless one exists already. +

+
+ +
+

+ It is possible to deploy web applications to a running Tomcat server. +

+

+ If the Host autoDeploy attribute is "true", the Host will + attempt to deploy and update web applications dynamically, as needed, + for example if a new .WAR is dropped into the appBase. + For this to work, the Host needs to have background processing + enabled which is the default configuration. +

+ +

+ autoDeploy set to "true" and a running Tomcat allows for: +

+
    +
  • Deployment of .WAR files copied into the Host appBase.
  • +
  • + Deployment of exploded web applications which are + copied into the Host appBase. +
  • +
  • + Re-deployment of a web application which has already been deployed from + a .WAR when the new .WAR is provided. In this case the exploded + web application is removed, and the .WAR is expanded again. + Note that the explosion will not occur if the Host is configured + so that .WARs are not exploded with a unpackWARs + attribute set to "false", in which case the web application + will be simply redeployed as a compressed archive. +
  • +
  • + Re-deployment of a web application if the /WEB-INF/web.xml file (or any + other resource defined as a WatchedResource) is updated. +
  • +
  • + Re-deployment of a web application if the Context Descriptor file from which + the web application has been deployed is updated. +
  • +
  • + Re-deployment of a web application if a Context Descriptor file (with a + filename corresponding to the Context path of the previously deployed + web application) is added to the + $CATALINA_BASE/conf/[enginename]/[hostname]/ + directory. +
  • +
  • + Undeployment of a web application if its document base (docBase) + is deleted. Note that on Windows, this assumes that anti-locking + features (see Context configuration) are enabled, otherwise it is not + possible to delete the resources of a running web application. +
  • +
+

+ Note that web application reloading can also be configured in the loader, in which + case loaded classes will be tracked for changes. +

+
+ +
+

+ The Tomcat Manager is covered in its own manual page. +

+
+ +
+

+ Finally, deployment of web application may be achieved using the + Tomcat Client Deployer. This is a package which can be used to + validate, compile, compress to .WAR, and deploy web applications to + production or development Tomcat servers. It should be noted that this feature + uses the Tomcat Manager and as such the target Tomcat server should be + running. +

+ +

+ It is assumed the user will be familiar with Apache Ant for using the TCD. + Apache Ant is a scripted build tool. The TCD comes pre-packaged with a + build script to use. Only a modest understanding of Apache Ant is + required (installation as listed earlier in this page, and familiarity + with using the operating system command shell and configuring + environment variables). +

+ +

+ The TCD includes Ant tasks, the Jasper page compiler for JSP compilation + before deployment, as well as a task which + validates the web application Context Descriptor. The validator task (class + org.apache.catalina.ant.ValidatorTask) allows only one parameter: + the base path of an exploded web application. +

+ +

+ The TCD uses an exploded web application as input (see the list of the + properties used below). A web application that is programmatically + deployed with the deployer may include a Context Descriptor in + /META-INF/context.xml. +

+ +

+ The TCD includes a ready-to-use Ant script, with the following targets: +

+
    +
  • + compile (default): Compile and validate the web + application. This can be used standalone, and does not need a running + Tomcat server. The compiled application will only run on the associated + Tomcat 7.0.x server release, and is not guaranteed to work on another + Tomcat release, as the code generated by Jasper depends on its runtime + component. It should also be noted that this target will also compile + automatically any Java source file located in the + /WEB-INF/classes folder of the web application.
  • +
  • + deploy: Deploy a web application (compiled or not) to + a Tomcat server. +
  • +
  • undeploy: Undeploy a web application
  • +
  • start: Start web application
  • +
  • reload: Reload web application
  • +
  • stop: Stop web application
  • +
+ +

+ In order for the deployment to be configured, create a file + called deployer.properties in the TCD installation + directory root. In this file, add the following name=value pairs per + line: +

+ +

+ Additionally, you will need to ensure that a user has been + setup for the target Tomcat Manager (which TCD uses) otherwise the TCD + will not authenticate with the Tomcat Manager and the deployment will + fail. To do this, see the Tomcat Manager page. +

+ +
    +
  • + build: The build folder used will be, by default, + ${build}/webapp/${path}. After the end of the execution + of the compile target, the web application .WAR will be + located at ${build}/webapp/${path}.war. +
  • +
  • + webapp: The directory containing the exploded web application + which will be compiled and validated. By default, the folder is + myapp. +
  • +
  • + path: Deployed context path of the web application, + by default /myapp. +
  • +
  • + url: Absolute URL to the Tomcat Manager web application of a + running Tomcat server, which will be used to deploy and undeploy the + web application. By default, the deployer will attempt to access + a Tomcat instance running on localhost, at + http://localhost:8080/manager. +
  • +
  • + username: Tomcat Manager username (user should have a role of + manager) +
  • +
  • password: Tomcat Manager password.
  • +
+
+ + + +
diff --git a/webapps/docs/developers.xml b/webapps/docs/developers.xml new file mode 100644 index 000000000000..577b3d8c366f --- /dev/null +++ b/webapps/docs/developers.xml @@ -0,0 +1,79 @@ + + + +]> + + + &project; + + + Remy Maucherat + Yoav Shapira + Tomcat Developers + + + + +
+ +

+ The list indicates the developers' main areas of interest. Feel free to + add to the list :) The developers email addresses are + [login]@apache.org. Please do not contact + developers directly for any support issues (please post to the + tomcat-users mailing list instead, or one of the other support + resources; some organizations and individual consultants also offer + for pay Tomcat support, as listed on the + support and + training page on the Tomcat Wiki). +

+ +
    +
  • Bill Barker (billbarker): Connectors
  • +
  • Costin Manolache (costin): Catalina, Connectors
  • +
  • Filip Hanik (fhanik): Clustering, Release Manager
  • +
  • Jean-Frederic Clere (jfclere): Connectors
  • +
  • Jim Jagielski (jim): Connectors
  • +
  • Konstantin Kolinko (kkolinko): Catalina
  • +
  • Mark Thomas (markt): CGI, SSI, WebDAV, bug fixing
  • +
  • Mladen Turk (mturk): Connectors
  • +
  • Peter Rossbach (pero): Catalina, Clustering, JMX
  • +
  • Rainer Jung (rjung): Catalina, Clustering, Connectors
  • +
  • Remy Maucherat (remm): Catalina, Connectors, Docs
  • +
  • Tim Funk (funkman): Catalina, Docs
  • +
  • Tim Whittington (timw): Connectors
  • +
+ +
+ +
+ +
    +
  • Amy Roh (amyroh): Catalina
  • +
  • Glenn Nielsen (glenn): Catalina, Connectors
  • +
  • Henri Gomez (hgomez): Connectors
  • +
  • Jan Luehe (luehe): Jasper
  • +
  • Jean-Francois Arcand (jfarcand): Catalina
  • +
  • Kin-Man Chung (kinman): Jasper
  • +
  • Yoav Shapira (yoavs): Docs, JMX, Catalina, balancer
  • +
+
+ + +
diff --git a/webapps/docs/elapi/index.html b/webapps/docs/elapi/index.html new file mode 100644 index 000000000000..fee5f54e7f43 --- /dev/null +++ b/webapps/docs/elapi/index.html @@ -0,0 +1,34 @@ + + + + + + API docs + + + + +The EL Javadoc is not installed by default. Download and install +the "fulldocs" package to get it. + +You can also access the javadoc online in the Tomcat + +documentation bundle. + + + diff --git a/webapps/docs/extras.xml b/webapps/docs/extras.xml new file mode 100644 index 000000000000..3c76cf9b688f --- /dev/null +++ b/webapps/docs/extras.xml @@ -0,0 +1,110 @@ + + + +]> + + + &project; + + + Additional Components + Remy Maucherat + + + + +
+ +
+ +
+

+ A number of additional third party components may be used with Apache + Tomcat. These components may be built by users should they need them or they + can be downloaded from one of the mirrors. +

+ +
+ +
+

+ To download the extras components open the Tomcat download page and + select "browse" from the Quick Navigation Links. The extras components can be + found in bin/extras. +

+
+ +
+ +

+ The additional components are built using the extras.xml Ant + script which is present in the source bundle of Tomcat. +

+ +

The build process is the following:

+ +
    +
  • Follow the build instructions to build a + Tomcat binary from the source bundle (note: it will be used by the build + process of the additional components, but does not need to be actually + used later on)
  • +
  • Execute the command ant extras to run the build + script
  • +
  • The additional components JARs will be placed in the + output/extras folder
  • +
  • Refer to the documentation below about the usage of these JARs
  • +
+ +
+ +
+ + + +

+ Tomcat uses a package renamed commons-logging API implementation which is + hardcoded to use the java.util.logging API. The commons-logging additional + component builds a full fledged package renamed commons-logging + implementation which can be used to replace the implementation provided with + Tomcat. See the logging page for usage + instructions. +

+ +
+ + + +

+ Tomcat provides factories for JSR 109 which may be used to resolve web + services references. Place the generated catalina-ws.jar as well as + jaxrpc.jar and wsdl4j.jar (or another implementation of JSR 109) in the + Tomcat lib folder. +

+ +

+ Users should be aware that wsdl4j.jar is licensed under CPL 1.0 and not the + Apache License version 2.0. +

+ +
+ +
+ + +
diff --git a/webapps/docs/funcspecs/fs-admin-apps.xml b/webapps/docs/funcspecs/fs-admin-apps.xml new file mode 100644 index 000000000000..1370f2ad3ae3 --- /dev/null +++ b/webapps/docs/funcspecs/fs-admin-apps.xml @@ -0,0 +1,300 @@ + + + +]> + + + &project; + + + Craig McClanahan + Administrative Apps - Overall Requirements + $Id$ + + + + +
+ +
+ +
+ + + + +

The purpose of this specification is to define high level requirements + for administrative applications that can be used to manage the operation + of a running Tomcat container. A variety of Access Methods + to the supported administrative functionality shall be supported, to + meet varying requirements:

+
    +
  • As A Scriptable Web Application - The existing + Manager web application provides a simple HTTP-based + interface for managing Tomcat through commands that are expressed + entirely through a request URI. This is useful in environments + where you wish to script administrative commands with tools that + can generate HTTP transactions.
  • +
  • As An HTML-Based Web Application - Use an HTML presentation + to provide a GUI-like user interface for humans to interact with the + administrative capabilities.
  • +
  • As SOAP-Based Web Services - The operational commands to + administer Tomcat are made available as web services that utilize + SOAP message formats.
  • +
  • As Java Management Extensions (JMX) Commands - The operational + commands to administer Tomcat are made available through JMX APIs, + for integration into management consoles that utilize them.
  • +
  • Other Remote Access APIs - Other remote access APIs, such + as JINI, RMI, and CORBA can also be utilized to access administrative + capabilities.
  • +
+ +

Underlying all of the access methods described above, it is assumed + that the actual operations are performed either directly on the + corresponding Catalina components (such as calling the + Deployer.deploy() method to deploy a new web application), + or through a "business logic" layer that can be shared across all of the + access methods. This approach minimizes the cost of adding new + administrative capabilities later -- it is only necessary to add the + corresponding business logic function, and then write adapters to it for + all desired access methods.

+ +

The current status of this functional specification is + PROPOSED. It has not yet been discussed and + agreed to on the TOMCAT-DEV mailing list.

+ +
+ + + + +

The implementation of this functionality depends on the following + external specifications:

+ + +
+ + + + +

The implementation of this functionality shall conform to the + following requirements:

+
    +
  • To the maximum extent feasible, all administrative functions, + and the access methods that support them, shall run portably + on all platforms where Tomcat itself runs.
  • +
  • In a default Tomcat distribution, all administrative capabilities + shall be disabled. It shall be necessary for a system + administrator to specifically enable the desired access methods + (such as by adding a username/password with a specific role to + the Tomcat user's database.
  • +
  • Administrative functions shall be realized as direct calls to + corresponding Catalina APIs, or through a business logic layer + that is independent of the access method used to initiate it.
  • +
  • The common business logic components shall be implemented in + package org.apache.catalina.admin.
  • +
  • The common business logic components shall be built as part of the + standard Catalina build process, and made visible in the + Catalina class loader.
  • +
  • The Java components required for each access method shall be + implemented in subpackages of org.apache.catalina.admin. +
  • +
  • The build scripts should treat each access method as optional, + so that it will be built only if the corresponding required + APIs are present at build time.
  • +
  • It shall be possible to save the configured state of the running + Tomcat container such that this state can be reproduced when the + container is shut down and restarted.
  • +
  • Administrative commands to start up and shut down the overall + Tomcat container are out of scope for the + purposes of these applications. It is assumed that other + (usually platform-specific) mechanisms will be used for container + startup and shutdown.
  • +
+ +
+ + +
+ + +
+ + + + +

The following environmental dependencies must be met in order for + administrative applications to operate correctly:

+
    +
  • For access methods that require creation of server sockets, the + appropriate ports must be configured and available.
  • +
+ +
+ + + + +

Correct operation of administrative applications depends on the + following specific features of the surrounding container:

+
    +
  • To the maximum extent feasible, Catalina components that offer + direct administrative APIs and property setters shall support + "live" changes to their operation, without requiring a container + restart.
  • +
+ +
+ + + + +

The availability of the following technologies can be assumed + for the implementation and operation of the various access methods + and the corresponding administrative business logic:
+ FIXME - This list below is totally outdated, but nobody + cares about the administrative app anymore. It is removed and unsupported + since Tomcat 6.0.

+ + +
+ + +
+ + +
+ + + + +

Functional requirements for administrative applications are specified + in terms of Administered Objects, whose definitions and detailed + properties are listed here. In general, + Administered Objects correspond to components in the Catalina architecture, + but these objects are defined separately here for the following reasons:

+
    +
  • It is possible that the administrative applications do not expose + every possible configurable facet of the underlying components.
  • +
  • In some cases, an Administered Object (from the perspective of an + administrative operation) is realized by more than one Catalina + component, at a finer-grained level of detail.
  • +
  • It is necessary to represent the configuration information for a + component separately from the component itself (for instance, in + order to store that configuration information for later use).
  • +
  • It is necessary to represent configuration information (such as + a Default Context) when there is no corresponding component instance. +
  • +
  • Administered Objects, when realized as Java classes, will include + methods for administrative operations that have no correspondence + to operations performed by the corresponding actual components.
  • +
+ +

It is assumed that the reader is familiar with the overall component + architecture of Catalina. For further information, see the corresponding + Developer Documentation. To distinguish names that are used as both + Administered Objects and Components, different + font presentations are utilized. Default values for many properties + are listed in [square brackets].

+ +
+ + + + +

The administrative operations that are available are described in terms + of the corresponding Administered Objects (as defined above), in a manner + that is independent of the access method by which these operations are + requested. In general, such operations are relevant only in the context + of a particular Administered Object (and will most likely be realized as + method calls on the corresponding Administered Object classes), so they + are organized based on the currently "focused" administered object. + The available Supported Operations are documented + here.

+ +
+ + + + +
Scriptable Web Application
+ +

An appropriate subset of the administrative operations described above + shall be implemented as commands that can be performed by the "Manager" + web application. FIXME - Enumerate them.

+ +

In addition, this web application shall conform to the following + requirements:

+
    +
  • All request URIs shall be protected by a security constraint that + requires security role manager for processing.
  • +
  • The default user database shall not contain any + user that has been assigned the role manager.
  • +
+ +
HTML-Based Web Application
+ +

The entire suite of administrative operations described above shall be + made available through a web application designed for human interaction. + In addition, this web application shall conform to the following + requirements:

+
    +
  • Must be implemented using servlet, JSP, and MVC framework technologies + described under "External Technologies", above.
  • +
  • Prompts and error messages must be internationalizable to multiple + languages.
  • +
  • Rendered HTML must be compatible with Netscape Navigator (version 4.7 + or later) and Internet Explorer (version 5.0 or later).
  • +
+ +
+ + +
+ + +
+ +

FIXME - Complete this section.

+ +
+ + + + +
diff --git a/webapps/docs/funcspecs/fs-admin-objects.xml b/webapps/docs/funcspecs/fs-admin-objects.xml new file mode 100644 index 000000000000..8846033a3d3e --- /dev/null +++ b/webapps/docs/funcspecs/fs-admin-objects.xml @@ -0,0 +1,500 @@ + + + +]> + + + &project; + + + Craig McClanahan + Administrative Apps - Administered Objects + $Id$ + + + + +
+ +
+ +
+ +

This document defines the Administered Objects that represent +the internal architectural components of the Catalina servlet container. +Associated with each is a set of Supported +Operations that can be performed when the administrative application is +"focused" on a particular configurable object.

+ +

The following Administered Objects are defined:

+ + +
+ + +
+ +

An Access Logger is an optional Valve that can + create request access logs in the same formats as those provided by + web servers. Such access logs are useful input to hit count and user + access tracking analysis programs. An Access Logger can be attached to + an Engine, a Host, a Context, or a Default + Context.

+ +

The standard component implementing an Access Logger is + org.apache.catalina.valves.AccessLogValve. It supports the + following configurable properties:

+
    +
  • debug - Debugging detail level. [0]
  • +
  • directory - Absolute or relative (to $CATALINA_BASE) path + of the directory into which access log files are created. + [logs].
  • +
  • pattern - Pattern string defining the fields to be + included in the access log output, or "common" for the standard + access log pattern. See + org.apache.catalina.valves.AccessLogValve for more + information. [common]
  • +
  • prefix - Prefix added to the beginning of each log file + name created by this access logger.
  • +
  • resolveHosts - Should IP addresses be resolved to host + names in the log? [false]
  • +
  • suffix - Suffix added to the end of each log file name + created by this access logger.
  • +
+ +
+ + +
+ +

A Connector is the representation of a communications endpoint + by which requests are received from (and responses returned to) a Tomcat + client. The administrative applications shall support those connectors + that are commonly utilized in Tomcat installations, as described in detail + below.

+ +

For standalone use, the standard connector supporting the HTTP/1.1 + protocol is org.apache.catalina.connectors.http.HttpConnector. + It supports the following configurable properties:

+
    +
  • acceptCount - The maximum queue length of incoming + connections that have not yet been accepted. [10]
  • +
  • address - For servers with more than one IP address, the + address upon which this connector should listen. [All Addresses]
  • +
  • bufferSize - Default input buffer size (in bytes) for + requests created by this Connector. [2048]
  • +
  • debug - Debugging detail level. [0]
  • +
  • enableLookups - Should we perform DNS lookups on remote + IP addresses when request.getRemoteHost() is called? + [true]
  • +
  • maxProcessors - The maximum number of processor threads + supported by this connector. [20]
  • +
  • minProcessors - The minimum number of processor threads + to be created at container startup. [5]
  • +
  • port - TCP/IP port number on which this Connector should + listen for incoming requests. [8080]
  • +
  • proxyName - Host name to be returned when an application + calls request.getServerName(). [Value of Host: header]
  • +
  • proxyPort - Port number to be returned when an application + calls request.getServerPort(). [Same as port] +
  • +
+ +
+ + +
+ +

A Context is the representation of an individual web application, + which is associated with a corresponding Host. Note that the + administrable properties of a Context do not + include any settings from inside the web application deployment descriptor + for that application.

+ +

The standard component implementing a Context is + org.apache.catalina.core.StandardContext. It supports the + following configurable properties:

+
    +
  • cookies - Should be use cookies for session identifier + communication? [true]
  • +
  • crossContext - Should calls to + ServletContext.getServletContext() return the actual + context responsible for the specified path? [false]
  • +
  • debug - Debugging detail level. [0]
  • +
  • docBase - The absolute or relative (to the + appBase of our owning Host) pathname of a + directory containing an unpacked web application, or of a web + application archive (WAR) file.
  • +
  • override - Should settings in this Context + override corresponding settings in the Default Context? + [false]
  • +
  • path - Context path for this web application, or an empty + string for the root application of a Host. [Inferred from + directory or WAR file name]
  • +
  • reloadable - Should Tomcat monitor classes in the + /WEB-INF/classes directory for changes, and reload the + application if they occur? [false]
  • +
  • useNaming - Should Tomcat provide a JNDI naming context, + containing preconfigured entries and resources, corresponding to the + requirements of the Java2 Enterprise Edition specification? [true]
  • +
  • workDir - Absolute pathname of a scratch directory that is + provided to this web application. [Automatically assigned relative to + $CATALINA_BASE/work]
  • +
+ +

Each Context is owned by a parent Host, and is + associated with:

+
    +
  • An optional Access Logger that logs all requests processed + by this web application.
  • +
  • Zero or more Environment Entries representing environment + entries for the JNDI naming context associated with a web + application.
  • +
  • Zero or more JDBC Resources representing database connection + pools associated with a web application.
  • +
  • A Loader representing the web application class loader used + by this web application.
  • +
  • A Manager representing the session manager used by this + web application.
  • +
  • An optional Realm used to provide authentication and access + control information for this web application.
  • +
  • Zero or more Request Filters used to limit access to this + web application based on remote host name or IP address.
  • +
+ +
+ + +
+ +

A Default Context represents a subset of the configurable + properties of a Context, and is used to set defaults for those + properties when web applications are automatically deployed. A Default + Context object can be associated with an Engine or a + Host. The following configurable properties are supported:

+
    +
  • cookies - Should be use cookies for session identifier + communication? [true]
  • +
  • crossContext - Should calls to + ServletContext.getServletContext() return the actual + context responsible for the specified path? [false]
  • +
  • reloadable - Should Tomcat monitor classes in the + /WEB-INF/classes directory for changes, and reload the + application if they occur? [false]
  • +
  • useNaming - Should Tomcat provide a JNDI naming context, + containing preconfigured entries and resources, corresponding to the + requirements of the Java2 Enterprise Edition specification? [true]
  • +
+ +

Each Default Context is owned by a parent Engine or + Host, and is associated with:

+
    +
  • Zero or more Environment Entries representing environment + entries for the JNDI naming context associated with a web + application.
  • +
  • Zero or more JDBC Resources representing database connection + pools associated with a web application.
  • +
  • An optional Loader representing default configuration + properties for the Loader component of deployed web applications.
  • +
  • An optional Manager representing default configuration + properties for the Manager component of deployed web applications.
  • +
+ +
+ + +
+ +

Default web application characteristics are configured in a special + deployment descriptor named $CATALINA_BASE/conf/web.xml. This + section describes the configurable components that may be stored there.

+ +

FIXME - Complete the description of default servlets, + default mappings, default MIME types, and so on.

+ +
+ + +
+ +

An Engine is the representation of the entire Catalina + servlet container, and processes all requests for all of the associated + virtual hosts and web applications.

+ +

The standard component implementing an Engine is + org.apache.catalina.core.StandardEngine. It supports the + following configurable properties:

+
    +
  • debug - Debugging detail level. [0]
  • +
  • defaultHost - Name of the Host to which requests + will be directed if the requested host is unknown. [localhost]
  • +
  • name - Logical name of this engine. [Tomcat Stand-Alone] +
  • +
+ +

Each Engine is owned by a parent Service, and is + associated with:

+
    +
  • An optional Access Logger that logs all requests processed + by the entire container.
  • +
  • A Default Context, representing default properties of a + Context for automatically deployed applications for all + associated Hosts (unless overridden by a subordinate + component).
  • +
  • One or more Hosts representing individual virtual hosts + supported by this container.
  • +
  • A Realm used to provide authentication and access control + information for all virtual hosts and web applications (unless + overridden by a subordinate component).
  • +
  • Zero or more Request Filters used to limit access to the + entire container based on remote host name or IP address.
  • +
+ +
+ + +
+ +

An Environment Entry is the representation of a + <env-entry> element from a web application deployment + descriptor. It will cause the creation of a corresponding entry in the + JNDI naming context provided to the corresponding Context. The + following configurable properties are supported:

+
    +
  • description - Description of this environment entry.
  • +
  • name - Environment entry name (relative to the + java:comp/env context)
  • +
  • type - Environment entry type (must be one of the fully + qualified Java classes listed in the servlet spec).
  • +
  • value - Environment entry value (must be convertible from + String to the specified type.
  • +
+ +
+ + +
+ +

A Host is the representation of an individual virtual host, + which has a unique set of associated web applications.

+ +

The standard component implementing a Host is + org.apache.catalina.core.StandardHost. It supports the + following configurable properties:

+
    +
  • aliases - Zero or more DNS names that are also associated + with this host (for example, a particular host might be named + www.mycompany.com with an alias company.com). +
  • +
  • appBase - Absolute or relative (to $CATALINA_BASE) path + to a directory from which web applications will be automatically + deployed.
  • +
  • debug - Debugging detail level. [0]
  • +
  • name - DNS Name of the virtual host represented by this + object.
  • +
  • unpackWARs - Should web application archive files + deployed by this virtual host be unpacked first? [true]
  • +
+ +

Each Host is owned by a parent Engine, and is + associated with:

+
    +
  • An optional Access Logger that logs all requests processed + by this virtual host.
  • +
  • One or more Contexts representing the web applications + operating on this Host.
  • +
  • A Default Context representing default Context + properties for web applications that are automatically deployed + by this Host.
  • +
  • A optional Realm used to provide authentication and access + control information for all web applications associated with this + virtual host (unless overridden by a subordinate component).
  • +
+ +

FIXME - Should we support configuration of the + User Web Applications functionality?

+ +
+ + +
+ +

A JDBC Resources represents a database connection pool (i.e. + an implementation of javax.sql.DataSource that will be + configured and made available in the JNDI naming context associated with + a web application.

+ +

FIXME - properties of this administered object

+ +
+ + +
+ +

A Loader represents a web application class loader that will + be utilized to provide class loading services for a particular + Context.

+ +

The standard component implementing a Loader is + org.apache.catalina.loader.StandardLoader. It supports + the following configurable properties:

+
    +
  • checkInterval - Number of seconds between checks for + modified classes, if automatic reloading is enabled. [15]
  • +
  • debug - Debugging detail level. [0]
  • +
  • reloadable - Should this class loader check for modified + classes and initiate automatic reloads? [Set automatically from the + reloadable property of the corresponding Context] +
  • +
+ +

Each Loader is owned by a parent Context.

+ +
+ + +
+ +

A Manager represents a session manager that will be associated + with a particular web application. FIXME - Add support + for advanced session managers and their associated Stores.

+ +

The standard component implementing a Manager is + org.apache.catalina.session.StandardManager. It supports + the following configurable properties:

+
    +
  • checkInterval - Number of seconds between checks for + expired sessions. [60]
  • +
  • debug - Debugging detail level. [0]
  • +
  • entropy - String initialization parameter used to increase + the entropy (initial randomness) of the random number generator used to + create session identifiers. [Inferred from engine, host, and context] +
  • +
  • maxActiveSessions - The maximum number of active sessions + that are allowed, or -1 for no limit. [-1]
  • +
+ +

Each Manager is owned by a parent Context.

+ +
+ + +
+ +

A Realm represents a "database" of information about authorized + users, their passwords, and the security roles assigned to them. This will + be used by the container in the implementation of container-managed security + in accordance with the Servlet Specification. Several alternative + implementations are supported.

+ +

org.apache.catalina.realm.MemoryRealm initializes its user + information from a simple XML file at startup time. If changes are made + to the information in this file, the corresponding web applications using + it must be restarted for the changes to take effect. It supports the + following configurable properties:

+
    +
  • debug - Debugging detail level. [0]
  • +
  • pathname - Absolute or relative (to $CATALINA_BASE) path to + the XML file containing our user information. [conf/tomcat-users.xml] +
  • +
+ +

org.apache.catalina.realm.JDBCRealm uses a relational + database (accessed via JDBC APIs) to contain the user information. Changes + in the contents of this database take effect immediately; however, the roles + assigned to a particular user are calculated only when the user initially + logs on (and not per request). The following configurable properties + are supported:

+
    +
  • connectionName - Database username to use when establishing + a JDBC connection.
  • +
  • connectionPassword - Database password to use when + establishing a JDBC connection.
  • +
  • connectionURL - Connection URL to use when establishing + a JDBC connection.
  • +
  • debug - Debugging detail level. [0]
  • +
  • digest - Name of the MessageDigest algorithm + used to encode passwords in the database, or a zero-length string for + no encoding. [Zero-length String]
  • +
  • driverName - Fully qualified Java class name of the JDBC + driver to be utilized.
  • +
  • roleNameCol - Name of the column, in the User Roles table, + which contains the role name.
  • +
  • userCredCol - Name of the column, in the Users table, + which contains the password (encrypted or unencrypted).
  • +
  • userNameCol - Name of the column, in both the Users and + User Roles tables, that contains the username.
  • +
  • userRoleTable - Name of the User Roles table, which contains + one row per security role assigned to a particular user. This table must + contain the columns specified by the userNameCol and + roleNameCol properties.
  • +
  • userTable - Name of the Users table, which contains one row + per authorized user. This table must contain the columns specified by + the userNameCol and userCredCol properties. +
  • +
+ +

FIXME - Should we provide mechanisms to edit the contents + of a "tomcat-users.xml" file through the admin applications?

+ +

Each Realm is owned by a parent Engine, Host, + or Context.

+ +
+ + +
+ +

FIXME - complete this entry

+ +
+ + +
+ +

FIXME - complete this entry

+ +
+ + +
+ +

FIXME - complete this entry

+ +
+ + + +
diff --git a/webapps/docs/funcspecs/fs-admin-opers.xml b/webapps/docs/funcspecs/fs-admin-opers.xml new file mode 100644 index 000000000000..14270211c5b2 --- /dev/null +++ b/webapps/docs/funcspecs/fs-admin-opers.xml @@ -0,0 +1,343 @@ + + + +]> + + + &project; + + + Craig McClanahan + Administrative Apps - Supported Operations + $Id$ + + + + +
+ +
+ +
+ +

This document defines the Supported Operations that may +be performed against the Administered +Objects that are supported by Tomcat administrative applications. +Not all operations are required to be available through every administrative +application that is implemented. However, if a given operation is available, +it should operate consistently with the descriptions found here.

+ +

Supported Operations are described for the following Administered +Objects:

+ + +
+ + +
+ +

From the perspective of a particular Access Logger, it shall + be possible to perform the following administrative operations:

+
    +
  • Navigate to the owning Engine, Host, or + Context.
  • +
  • Edit the configurable properties of this object.
  • +
+ +
+ + +
+ +

From the perspective of a particular Connector, it shall be + possible to perform the following administrative operations:

+
    +
  • Navigate to the owning Service.
  • +
  • Edit the configurable properties of this object.
  • +
+ +
+ + +
+ +

From the perspective of a particular Context, it shall be + possible to perform the following administrative operations:

+
    +
  • Navigate to the owning Host.
  • +
  • Edit the configurable properties of this object.
  • +
  • Create and configure a new Access Logger associated + with this object.
  • +
  • Edit the configurable properties of the associated Access + Logger.
  • +
  • Remove the associated Access Logger.
  • +
  • Create and configure a new Environment Entry associated + with this object.
  • +
  • Select and edit the configurable properties of an associated + Environment Entry.
  • +
  • Remove an associated Environment Entry.
  • +
  • Create and configure a new JDBC Resource associated + with this object.
  • +
  • Select and edit the configurable properties of an associated + JDBC Resource.
  • +
  • Remove an associated JDBC Resource.
  • +
  • Create and configure a new Loader associated with + this object.
  • +
  • Edit the configurable properties of the associated Loader.
  • +
  • Remove the associated Loader.
  • +
  • Create and configure a new Manager associated with + this object.
  • +
  • Edit the configurable properties of the associated Manager.
  • +
  • Remove the associated Manager.
  • +
  • Create and configure a new Realm associated with + this object.
  • +
  • Edit the configurable properties of the associated Realm.
  • +
  • Remove the associated Realm.
  • +
  • Create and configure a new Request Filter associated with + this object.
  • +
  • Select and edit the configurable properties of an + associated Request Filter
  • +
  • Remove an associated Request Filter.
  • +
+ +
+ + +
+ +

From the perspective of a particular Default Context, it shall + be possible to perform the following administrative operations:

+
    +
  • Navigate to the owning Engine or Host.
  • +
  • Edit the configurable properties of this object.
  • +
  • Create and configure a new Environment Entry associated + with this object.
  • +
  • Select and edit the configurable properties of an associated + Environment Entry.
  • +
  • Remove an associated Environment Entry.
  • +
  • Create and configure a new JDBC Resource associated + with this object.
  • +
  • Select and edit the configurable properties of an associated + JDBC Resource.
  • +
  • Remove an associated JDBC Resource.
  • +
+ +
+ + +
+ +

From the perspective of a particular Engine, it shall be + possible to perform the following administrative operations:

+
    +
  • Navigate to the owning Service.
  • +
  • Edit the configurable properties of this object.
  • +
  • Create and configure a new Access Logger associated + with this object.
  • +
  • Edit the configurable properties of the associated Access + Logger.
  • +
  • Remove the associated Access Logger.
  • +
  • Create and configure a new Default Context associated + with this object.
  • +
  • Edit the configurable properties of the associated Default + Context.
  • +
  • Remove the associated Default Context.
  • +
  • Create and configure a new Host associated with + this object.
  • +
  • Select and edit the configurable properties of an + associated Host.
  • +
  • Remove an associated Host.
  • +
  • Create and configure a new Realm associated with + this object.
  • +
  • Edit the configurable properties of the associated Realm.
  • +
  • Remove the associated Realm.
  • +
  • Create and configure a new Request Filter associated with + this object.
  • +
  • Select and edit the configurable properties of an + associated Request Filter
  • +
  • Remove an associated Request Filter.
  • +
+ +
+ + +
+ +

From the perspective of a particular Environment Entry, it shall + be possible to perform the following administrative operations:

+
    +
  • Navigate to the owning Context or Default Context.
  • +
  • Edit the configurable properties of this object.
  • +
+ +
+ + +
+ +

From the perspective of a particular Host, it shall be + possible to perform the following administrative operations:

+
    +
  • Navigate to the owning Engine.
  • +
  • Edit the configurable properties of this object.
  • +
  • Create and configure a new Access Logger associated + with this object.
  • +
  • Edit the configurable properties of the associated Access + Logger.
  • +
  • Remove the associated Access Logger.
  • +
  • Create and configure a new Context associated with + this object.
  • +
  • Select and edit the configurable properties of an associated + Context.
  • +
  • Remove an associated Context.
  • +
  • Create and configure a new Default Context associated + with this object.
  • +
  • Edit the configurable properties of the associated Default + Context.
  • +
  • Remove the associated Default Context.
  • +
  • Create and configure a new Realm associated with + this object.
  • +
  • Edit the configurable properties of the associated Realm.
  • +
  • Remove the associated Realm.
  • +
  • Create and configure a new Request Filter associated with + this object.
  • +
  • Select and edit the configurable properties of an + associated Request Filter
  • +
  • Remove an associated Request Filter.
  • +
+ +
+ + +
+ +

From the perspective of a particular JDBC Resource, it shall + be possible to perform the following administrative operations:

+
    +
  • Navigate to the owning Context or Default Context.
  • +
  • Edit the configurable properties of this object.
  • +
+ +
+ + +
+ +

From the perspective of a particular Loader, it shall + be possible to perform the following administrative operations:

+
    +
  • Navigate to the owning Context.
  • +
  • Edit the configurable properties of this object.
  • +
+ +
+ + +
+ +

From the perspective of a particular Manager, it shall + be possible to perform the following administrative operations:

+
    +
  • Navigate to the owning Context.
  • +
  • Edit the configurable properties of this object.
  • +
+ +
+ + +
+ +

From the perspective of a particular Realm, it shall + be possible to perform the following administrative operations:

+
    +
  • Navigate to the owning Engine, Host, or + Context.
  • +
  • Edit the configurable properties of this object.
  • +
+ +
+ + +
+ +

From the perspective of a particular Request Filter, it shall + be possible to perform the following administrative operations:

+
    +
  • Navigate to the owning Engine, Host, or + Context.
  • +
  • Edit the configurable properties of this object.
  • +
+ +
+ + +
+ +

From the perspective of the overall Server, it shall be + possible to perform the following administrative operations:

+
    +
  • Edit the configurable properties of this object.
  • +
  • Create and configure a new Service associated with + this object.
  • +
  • Select and edit the configurable properties of an associated + Service.
  • +
+ +
+ + +
+ +

From the perspective of a particular Service, it shall be + possible to perform the following administrative operations:

+
    +
  • Navigate to the owning Server.
  • +
  • Edit the configurable properties of this object.
  • +
  • Create and configure a new Connector associated with + this object.
  • +
  • Select and edit the configurable properties of an associated + Connector.
  • +
  • Remove an associated Connector.
  • +
  • Create and configure a new Engine associated with + this object.
  • +
  • Edit the configurable properties of the associated Engine.
  • +
  • Remove the associated Engine.
  • +
+ +
+ + + + +
diff --git a/webapps/docs/funcspecs/fs-default.xml b/webapps/docs/funcspecs/fs-default.xml new file mode 100644 index 000000000000..aac40df5ceba --- /dev/null +++ b/webapps/docs/funcspecs/fs-default.xml @@ -0,0 +1,271 @@ + + + +]> + + + &project; + + + Craig McClanahan + Default Servlet + $Id$ + + + + +
+ +
+ +
+ + + + +

The purpose of the Default Servlet is to serve + static resources of a web application in response to client requests. + As the name implies, it is generally configured as the "default" + servlet for a web application, by being mapped to a URL pattern "/".

+ +
+ + + + +

The following external specifications have provisions which + partially define the correct behavior of the default servlet:

+ + +
+ + + + +

The implementation of this functionality shall conform to the + following requirements:

+
    +
  • Must be implemented as a servlet.
  • +
  • Must support configurable parameters for debugging detail level, + input buffer size, output buffer size, whether or not to produce + directory listings when no welcome file is present, and whether or not + modifications are supported via DELETE and PUT.
  • +
  • Log debugging and operational messages (suitably internationalized) + via the getServletContext().log() method.
  • +
+ +
+ + +
+ + +
+ + + + +

The following environmental dependencies must be met in order for + the default servlet to operate correctly:

+
    +
  • The default servlet must be registered in the application deployment + descriptor (or the default deployment descriptor in file + $CATALINA_BASE/conf/web.xml) using a "default servlet" + servlet mapping, signified by URL pattern "/".
  • +
+ +
+ + + + +

Correct operation of the default servlet depends on the following + specific features of the surrounding container:

+
    +
  • The container shall provide a servlet context attribute that + lists the welcome file names that have been defined for this + web application.
  • +
  • The container shall provide a servlet context attribute that + contains a javax.naming.directory.DirContext + implementation representing the static resources of this + web application.
  • +
+ +
+ + +
+ + +
+ + + + +

The following processing must be performed when the init() + method of the default servlet is called:

+
    +
  • Process and sanity check configuration parameters.
  • +
+ +
+ + + + + +

For all HTTP request methods, the resource path is determined from + the path information provided to this request, either as request attribute + javax.servlet.include.path_info (for a request dispatcher + access to a static resource) or by calling + request.getPathInfo() directly.

+ +

On each HTTP DELETE request processed by this servlet, the following + processing shall be performed:

+
    +
  • If modifications to the static resources are not allowed (set by a + configuration parameter), return HTTP status 403 (forbidden).
  • +
  • If an attempt is made to delete a resource from /META-INF + or /WEB-INF, return HTTP status 403 (forbidden).
  • +
  • If the requested resource does not exist, return HTTP status 404 + (not found)
  • +
  • Unbind the resource from the directory context containing the + static resources for this web application. If successful, return + HTTP status 204 (no content). Otherwise, return HTTP status 405 + (method not allowed).
  • +
+ + +

On each HTTP GET request processed by this servlet, the following + processing shall be performed:

+
    +
  • If the request is for a resource under /META-INF or + /WEB-INF, return HTTP status 404 (not found).
  • +
  • If the requested resource does not exist, return HTTP status 404 + (not found).
  • +
  • If the requested resource is not a directory, but the resource + path ends in "/" or "\", return HTTP status 404 (not found).
  • +
  • If the requested resource is a directory: +
      +
    • If the request path does not end with "/", redirect to a + corresponding path with "/" appended so that relative references + in welcome files are resolved correctly.
    • +
    • If one of the specified welcome files exists, redirect to the + path for that welcome file so that it will be served explicitly. +
    • +
  • +
  • If the request being processed contains an If-Range + header, perform the processing described in the HTTP/1.1 specification + to determine whether the client's information is up to date.
  • +
  • Determine the content type of the response, by looking up the + corresponding MIME type in our servlet context.
  • +
  • If the requested resource is a directory: +
      +
    • If directory listings are suppressed, return HTTP status 404 + (not found).
    • +
    • Set the content type to text/html.
    • +
  • +
  • Determine the range(s) to be returned, based on the existence of + any If-Range and Range headers.
  • +
  • If the requested resource is a directory, include an ETag + header in the response, with the value calculated based on the content + of the directory.
  • +
  • Include a Last-Modified header in the response documenting + the date/time that the resource was last modified.
  • +
  • Unless we are processing a HEAD request, include the appropriate + content (or content ranges) in the response.
  • +
+ +

On each HTTP HEAD request processed by this servlet, the following + processing shall be performed:

+
    +
  • Processed identically to an HTTP GET request, except that the data + content is not transmitted after the headers.
  • +
+ +

On each HTTP POST request processed by this servlet, the following + processing shall be performed:

+
    +
  • Processed identically to an HTTP GET request.
  • +
+ + +

On each HTTP PUT request processed by this servlet, the following + processing shall be performed:

+
    +
  • If modifications to the static resources are not allowed (set by a + configuration parameter), return HTTP status 403 (forbidden).
  • +
  • If an attempt is made to delete a resource from /META-INF + or /WEB-INF, return HTTP status 403 (forbidden).
  • +
  • Create a new resource from the body of this request.
  • +
  • Bind or rebind the specified path to the new resource (depending on + whether it currently exists or not). Return HTTP status as follows: +
      +
    • If binding was unsuccessful, return HTTP status 409 (conflict). +
    • +
    • If binding was successful and the resource did not previously + exist, return HTTP status 201 (created).
    • +
    • If binding was successful and the resource previously existed, + return HTTP status 204 (no content).
    • +
  • +
+ +
+ + + + +

No specific processing is required when the destroy() + method is called:

+ +
+ + +
+ + +
+ +

In addition the the assertions implied by the functionality requirements + listed above, the following additional assertions shall be tested to + validate the behavior of the default servlet:

+
    +
  • Requests for resources that do not exist in the web application must + return HTTP status 404 (not found).
  • +
  • The default servlet must operate identically for web applications that + are run out of a WAR file directly, or from an unpacked directory + structure.
  • +
  • If the web application is running out of an unpacked directory + structure, the default servlet must recognize cases where the resource + has been updated through external means.
  • +
+ +
+ + + + +
diff --git a/webapps/docs/funcspecs/fs-jdbc-realm.xml b/webapps/docs/funcspecs/fs-jdbc-realm.xml new file mode 100644 index 000000000000..86db3d1344c7 --- /dev/null +++ b/webapps/docs/funcspecs/fs-jdbc-realm.xml @@ -0,0 +1,267 @@ + + + +]> + + + &project; + + + Craig McClanahan + JDBCRealm + $Id$ + + + + +
+ +
+ +
+ + + + +

The purpose of the JDBCRealm implementation is to + provide a mechanism by which Tomcat can acquire information needed + to authenticate web application users, and define their security roles, + from a relational database accessed via JDBC APIs. For integration + with Catalina, the resulting class(es) must implement the + org.apache.catalina.Realm interface.

+ +

This specification reflects a combination of functionality that is + already present in the org.apache.catalina.realm.JDBCRealm + class, as well as requirements for enhancements that have been + discussed. Where appropriate, requirements statements are marked + [Current] and [Requested] to distinguish them.

+ +

The current status of this functional specification is + PROPOSED. It has not yet been discussed and + agreed to on the TOMCAT-DEV mailing list.

+ +
+ + + + +

The implementation of this functionality depends on the following + external specifications:

+ + +
+ + + + +

The implementation of this functionality shall conform to the + following requirements:

+
    +
  • Be realized in one or more implementation classes.
  • +
  • Implement the org.apache.catalina.Realm interface. + [Current]
  • +
  • Implement the org.apache.catalina.Lifecycle + interface. [Current]
  • +
  • Subclass the org.apache.catalina.realm.RealmBase + base class.
  • +
  • Live in the org.apache.catalina.realm package. + [Current]
  • +
  • Support a configurable debugging detail level. [Current]
  • +
  • Log debugging and operational messages (suitably internationalized) + via the getContainer().log() method. [Current]
  • +
+ +
+ + +
+ + +
+ + + + +

The following environmental dependencies must be met in order for + JDBCRealm to operate correctly:

+
    +
  • The desire to utilize JDBCRealm must be registered in + $CATALINA_BASE/conf/server.xml, in a + <Realm> element that is nested inside a + corresponding <Engine>, <Host>, + or <Context> element.
  • +
+ +
+ + + + +

Correct operation of JDBCRealm depends on the following + specific features of the surrounding container:

+
    +
  • Interactions with JDBCRealm will be initiated by + the appropriate Authenticator implementation, based + on the login method that is selected.
  • +
  • JDBCRealm must have the JDBC standard API classes + available to it. For a JDK 1.2 or later container, these APIs + are included in the standard platform.
  • +
  • When connection pooling is implemented, JDBCRealm + must have the JDBC Optional Package (version 2.0 or later) APIs + available to it. This library is available as a separate + download (and will be included in Tomcat binary distributions).
  • +
+ +
+ + +
+ + +
+ + + + +

The main purpose of JDBCRealm is to allow Catalina to + authenticate users, and look up the corresponding security roles, from + the information found in a relational database accessed via JDBC APIs. + For maximum flexibility, the details of how this is done (for example, + the names of the required tables and columns) should be configurable.

+ +

Each time that Catalina needs to authenticate a user, it will call + the authenticate() method of this Realm implementation, + passing the username and password that were specified by the user. If + we find the user in the database (and match on the password), we accumulate + all of the security roles that are defined for this user, and create a + new GenericPrincipal object to be returned. If the user + is not authenticated, we return null instead. The + GenericUser object caches the set of security roles that + were owned by this user at the time of authentication, so that calls to + isUserInRole() can be answered without going back to the + database every time.

+ +
+ + + + + +

Configurable Properties

+ +

The implementation shall support the following properties + that can be configured with JavaBeans property setters:

+
    +
  • Configuration parameters defining the JDBC driver to use, the + database connection URL to be accessed, and the username/password + to use for logging in. [Current]
  • +
  • Configuration parameters describing the connection pool to be + created to support simultaneous authentications. [Requested]
  • +
  • Name of the tables to be searched for users and roles. [Current]
  • +
  • Name of the columns to be used for usernames, passwords, and + role names. [Current]
  • +
+ +

Lifecycle Functionality

+ +

The following processing must be performed when the start() + method is called:

+
    +
  • Establish a connection to the configured database, using the + configured username and password. [Current]
  • +
  • Configure and establish a connection pool of connections to the + database. [Requested]
  • +
+ +

The following processing must be performed when the stop() + method is called:

+
    +
  • Close any opened connections to the database.
  • +
+ + +

Method authenticate() Functionality

+ +

When authenticate() is called, the following processing + is required:

+
    +
  • Acquire the one and only connection [Current] or acquire a connection + from the connection pool [Requested].
  • +
  • Select the one and only row from the user's table for this user, + and retrieve the corresponding password column. If zero rows (or + more than one row) are found, return null.
  • +
  • Authenticate the user by comparing the (possibly encrypted) password + value that was received against the password presented by the user. + If there is no match, return null.
  • +
  • Acquire a List of the security roles assigned to the + authenticated user by selecting from the roles table.
  • +
  • Construct a new instance of class + org.apache.catalina.realm.GenericPrincipal, passing as + constructor arguments: this realm instance, the authenticated + username, and a List of the security roles associated + with this user.
  • +
  • WARNING - Do not attempt to cache and reuse previous + GenericPrincipal objects for a particular user, because + the information in the directory server might have changed since the + last time this user was authenticated.
  • +
  • Return the newly constructed GenericPrincipal.
  • +
+ + +

Method hasRole() Functionality

+ +

When hasRole() is called, the following processing + is required:

+
    +
  • The principal that is passed as an argument SHOULD + be one that we returned (instanceof class + org.apache.catalina.realm.GenericPrincipal, with a + realm property that is equal to our instance.
  • +
  • If the passed principal meets these criteria, check + the specified role against the list returned by + getRoles(), and return true if the + specified role is included; otherwise, return false.
  • +
  • If the passed principal does not meet these criteria, + return false.
  • +
+ +
+ +
+ + +
+ +

In addition the the assertions implied by the functionality requirements + listed above, the following additional assertions shall be tested to + validate the behavior of JDBCRealm:

+
    +
+ +
+ + + + +
diff --git a/webapps/docs/funcspecs/fs-jndi-realm.xml b/webapps/docs/funcspecs/fs-jndi-realm.xml new file mode 100644 index 000000000000..0457a5a7f829 --- /dev/null +++ b/webapps/docs/funcspecs/fs-jndi-realm.xml @@ -0,0 +1,422 @@ + + + +]> + + + &project; + + + Craig McClanahan + JNDIRealm + $Id$ + + + + +
+ +
+ +
+ + + + +

The purpose of the JNDIRealm implementation is to + provide a mechanism by which Tomcat can acquire information needed + to authenticate web application users, and define their security roles, + from a directory server or other service accessed via JNDI APIs. For + integration with Catalina, this class must implement the + org.apache.catalina.Realm interface.

+ +

This specification reflects a combination of functionality that is + already present in the org.apache.catalina.realm.JNDIRealm + class, as well as requirements for enhancements that have been + discussed. Where appropriate, requirements statements are marked + [Current] and [Requested] to distinguish them.

+ +

The current status of this functional specification is + PROPOSED. It has not yet been discussed and + agreed to on the TOMCAT-DEV mailing list.

+ +

The code in the current version of JNDIRealm, and the + ideas expressed in this functional specification, are the results of + contributions from many individuals, including (alphabetically):

+
    +
  • Holman, John <j.g.holman@qmw.ac.uk>
  • +
  • Lockhart, Ellen <elockhart@home.com>
  • +
  • McClanahan, Craig <craigmcc@apache.org>
  • +
+ +
+ + + + +

The implementation of this functionality depends on the following + external specifications:

+ + +
+ + + + +

The implementation of this functionality shall conform to the + following requirements:

+
    +
  • Be realized in one or more implementation classes.
  • +
  • Implement the org.apache.catalina.Realm interface. + [Current]
  • +
  • Implement the org.apache.catalina.Lifecycle + interface. [Current]
  • +
  • Subclass the org.apache.catalina.realm.RealmBase + base class.
  • +
  • Live in the org.apache.catalina.realm package. + [Current]
  • +
  • Support a configurable debugging detail level. [Current]
  • +
  • Log debugging and operational messages (suitably internationalized) + via the getContainer().log() method. [Current]
  • +
+ +
+ + +
+ + +
+ + + + +

The following environmental dependencies must be met in order for + JNDIRealm to operate correctly:

+
    +
  • The desire to utilize JNDIRealm must be registered in + $CATALINA_BASE/conf/server.xml, in a + <Realm> element that is nested inside a + corresponding <Engine>, <Host>, + or <Context> element.
  • +
  • If the Administrator Login operational mode is selected, + the configured administrator username and password must be configured + in the corresponding directory server.
  • +
  • If the Username Login operational mode is selected, + the corresponding directory server must be configured to accept + logins with the username and password that will be passed to + JNDIRealm by the appropriate Authenticator. +
  • +
+ +
+ + + + +

Correct operation of JNDIRealm depends on the following + specific features of the surrounding container:

+
    +
  • Interactions with JNDIRealm will be initiated by + the appropriate Authenticator implementation, based + on the login method that is selected.
  • +
  • JNDIRealm must have the JNDI API classes available + to it. For a JDK 1.2 container, that means jndi.jar + and the appropriate implementation (such as ldap.jar) + must be placed in the server/lib directory.
  • +
+ +
+ + +
+ + +
+ + + + +

The completed JNDIRealm must support two major operational + modes in order to support all of the required use cases. For the purposes + of this document, the modes are called administrator login and + Username Login. They are described further in the following + paragraphs.

+ +

For Administrator Login mode, JNDIRealm will be + configured to establish one or more connections (using a connection pool) + to an appropriate directory server, using JNDI APIs, under a "system + administrator" username and password. This is similar to the approach + normally used to configure JDBCRealm to access authentication + and access control information in a database. It is assumed that the + system administrator username and password that are configured provide + sufficient privileges within the directory server to read (but not modify) + the username, password, and assigned roles for each valid user of the + web application associated with this Realm. The password + can be stored in cleartext, or in one of the digested modes supported by + the org.apache.catalina.realm.RealmBase base class.

+ +

For Username Login mode, JNDIRealm does not + normally remain connected to the directory server. Instead, whenever a + user is to be authenticated, a connection to the directory server + (using the username and password received from the authenticator) is + attempted. If this connection is successful, the user is assumed to be + successfully authenticated. This connection is then utilized to read + the corresponding security roles associated with this user, and the + connection is then broken.

+ +

NOTE - Username Login mode cannot be used + if you have selected login method DIGEST in your web + application deployment descriptor (web.xml) file. This + restriction exists because the cleartext password is never available + to the container, so it is not possible to bind to the directory server + using the user's username and password.

+ +

Because these operational modes work so differently, the functionality + for each mode will be described separately. Whether or not both modes + are actually supported by a single class (versus a class per mode) is + an implementation detail left to the designer.

+ +

NOTE - The current implementation only implements + part of the Administrator Lookup mode requirements. It does + not support the Username Lookup mode at all, at this point.

+ +
+ + + + + +

Configurable Properties

+ +

The implementation shall support the following properties + that can be configured with JavaBeans property setters:

+
    +
  • connectionURL - URL of the directory server we will + be contacting.
  • +
  • contextFactory - Fully qualified class name of the JNDI + context factory used to retrieve our InitialContext. + [com.sun.jndi.ldap.LdapCtxFactory]
  • +
  • Additional configuration properties required to establish the + appropriate connection. [Requested]
  • +
  • Connection pool configuration properties. [Requested]
  • +
  • Configuration properties defining how a particular user is + authenticated. The following capabilities should be supported: +
      +
    • Substitute the specified username into a string. [Requested]
    • +
    • Retrieve the distinguished name (DN) of an authorized user via an + LDAP search string with a replacement placeholder for the + username, and comparison of the password to a configurable + attribute retrieved from the search result. [Current]
    • +
  • +
  • Configuration properties defining how the roles associated with a + particular authenticated user can be retrieved. The following + approaches should be supported: +
      +
    • Retrieve a specified attribute (possibly multi-valued) + from an LDAP search expression, + with a replacement placeholder for the DN of the user. + [Current]
    • +
    • Retrieve a set of role names that are defined implicitly (by + selecting principals that match a search pattern) rather than + explicitly (by finding a particular attribute value). + [Requested]
    • +
  • +
+ +

Lifecycle Functionality

+ +

The following processing must be performed when the start() + method is called:

+
    +
  • Establish a connection to the configured directory server, using the + configured system administrator username and password. [Current]
  • +
  • Configure and establish a connection pool of connections to the + directory server. [Requested]
  • +
+ +

The following processing must be performed when the stop() + method is called:

+
    +
  • Close any opened connections to the directory server.
  • +
+ + +

Method authenticate() Functionality

+ +

When authenticate() is called, the following processing + is required:

+
    +
  • Acquire the one and only connection [Current] or acquire a connection + from the connection pool [Requested].
  • +
  • Authenticate the user by retrieving the user's Distinguished Name, + based on the specified username and password.
  • +
  • If the user was not authenticated, release the allocated connection + and return null.
  • +
  • Acquire a List of the security roles assigned to the + authenticated user.
  • +
  • Construct a new instance of class + org.apache.catalina.realm.GenericPrincipal, passing as + constructor arguments: this realm instance, the authenticated + username, and a List of the security roles associated + with this user.
  • +
  • WARNING - Do not attempt to cache and reuse previous + GenericPrincipal objects for a particular user, because + the information in the directory server might have changed since the + last time this user was authenticated.
  • +
  • Return the newly constructed GenericPrincipal.
  • +
+ + +

Method hasRole() Functionality

+ +

When hasRole() is called, the following processing + is required:

+
    +
  • The principal that is passed as an argument SHOULD + be one that we returned (instanceof class + org.apache.catalina.realm.GenericPrincipal, with a + realm property that is equal to our instance.
  • +
  • If the passed principal meets these criteria, check + the specified role against the list returned by + getRoles(), and return true if the + specified role is included; otherwise, return false.
  • +
  • If the passed principal does not meet these criteria, + return false.
  • +
+ +
+ + + + +

Configurable Properties

+ +

The implementation shall support the following properties + that can be configured with JavaBeans property setters:

+
    +
  • connectionURL - URL of the directory server we will + be contacting.
  • +
  • contextFactory - Fully qualified class name of the JNDI + context factory used to retrieve our InitialContext. + [com.sun.jndi.ldap.LdapCtxFactory]
  • +
  • Additional configuration properties required to establish the + appropriate connection. [Requested]
  • +
  • Connection pool configuration properties. [Requested]
  • +
  • Configuration properties defining if and how a user might be looked + up before binding to the directory server. The following approaches + should be supported: +
      +
    • No previous lookup is required - username specified by the user + is the same as that used to authenticate to the directory + server.
    • +
    • Substitute the specified username into a string.
    • +
    • Search the directory server based on configured criteria to + retrieve the distinguished name of the user, then attempt to + bind with that distinguished name.
    • +
  • +
  • Configuration properties defining how the roles associated with a + particular authenticated user can be retrieved. The following + approaches should be supported: +
      +
    • Retrieve a specified attribute (possibly multi-valued) + from an LDAP search expression, + with a replacement placeholder for the DN of the user. + [Current]
    • +
  • +
+ +

Lifecycle Functionality

+ +

The following processing must be performed when the start() + method is called:

+
    +
  • None required.
  • +
+ +

The following processing must be performed when the stop() + method is called:

+
    +
  • None required.
  • +
+ + +

Method authenticate() Functionality

+ +

When authenticate() is called, the following processing + is required:

+
    +
  • Attempt to bind to the directory server, using the username and + password provided by the user.
  • +
  • If the user was not authenticated, release the allocated connection + and return null.
  • +
  • Acquire a List of the security roles assigned to the + authenticated user.
  • +
  • Construct a new instance of class + org.apache.catalina.realm.GenericPrincipal, passing as + constructor arguments: this realm instance, the authenticated + username, and a List of the security roles associated + with this user.
  • +
  • WARNING - Do not attempt to cache and reuse previous + GenericPrincipal objects for a particular user, because + the information in the directory server might have changed since the + last time this user was authenticated.
  • +
  • Return the newly constructed GenericPrincipal.
  • +
+ + +

Method hasRole() Functionality

+ +

When hasRole() is called, the following processing + is required:

+
    +
  • The principal that is passed as an argument SHOULD + be one that we returned (instanceof class + org.apache.catalina.realm.GenericPrincipal, with a + realm property that is equal to our instance.
  • +
  • If the passed principal meets these criteria, check + the specified role against the list returned by + getRoles(), and return true if the + specified role is included; otherwise, return false.
  • +
  • If the passed principal does not meet these criteria, + return false.
  • +
+ +
+ +
+ + +
+ +

In addition the the assertions implied by the functionality requirements + listed above, the following additional assertions shall be tested to + validate the behavior of JNDIRealm:

+
    +
+ +
+ + + + +
diff --git a/webapps/docs/funcspecs/fs-memory-realm.xml b/webapps/docs/funcspecs/fs-memory-realm.xml new file mode 100644 index 000000000000..5780bf863143 --- /dev/null +++ b/webapps/docs/funcspecs/fs-memory-realm.xml @@ -0,0 +1,254 @@ + + + +]> + + + &project; + + + Craig McClanahan + MemoryRealm + $Id$ + + + + +
+ +
+ +
+ + + + +

The purpose of the MemoryRealm implementation is to + provide a mechanism by which Tomcat can acquire information needed + to authenticate web application users, and define their security roles, + from a simple text-based configuration file in XML format. This is + intended to simplify the initial installation and operation of Tomcat, + without the complexity of configuring a database or directory server + based Realm. It is not intended for production use.

+ +

This specification reflects a combination of functionality that is + already present in the org.apache.catalina.realm.MemoryRealm + class, as well as requirements for enhancements that have been + discussed. Where appropriate, requirements statements are marked + [Current] and [Requested] to distinguish them.

+ +

The current status of this functional specification is + PROPOSED. It has not yet been discussed and + agreed to on the TOMCAT-DEV mailing list.

+ +
+ + + + +

The implementation of this functionality depends on the following + external specifications:

+
    +
  • None
  • +
+ +
+ + + + +

The implementation of this functionality shall conform to the + following requirements:

+
    +
  • Be realized in one or more implementation classes.
  • +
  • Implement the org.apache.catalina.Realm interface. + [Current]
  • +
  • Implement the org.apache.catalina.Lifecycle + interface. [Current]
  • +
  • Subclass the org.apache.catalina.realm.RealmBase + base class.
  • +
  • Live in the org.apache.catalina.realm package. + [Current]
  • +
  • Support a configurable debugging detail level. [Current]
  • +
  • Log debugging and operational messages (suitably internationalized) + via the getContainer().log() method. [Current]
  • +
+ +
+ + +
+ + +
+ + + + +

The following environmental dependencies must be met in order for + MemoryRealm to operate correctly:

+
    +
  • The desire to utilize MemoryRealm must be registered in + $CATALINA_BASE/conf/server.xml, in a + <Realm> element that is nested inside a + corresponding <Engine>, <Host>, + or <Context> element. (This is already + included in the default server.xml file.)
  • +
+ +
+ + + + +

Correct operation of MemoryRealm depends on the following + specific features of the surrounding container:

+
    +
  • Interactions with MemoryRealm will be initiated by + the appropriate Authenticator implementation, based + on the login method that is selected.
  • +
  • MemoryRealm must have an XML parser compatible with + the JAXP/1.1 APIs available to it. This is normally accomplished + by placing the corresponding JAR files in directory + $CATALINA_HOME/lib.
  • +
+ +
+ + +
+ + +
+ + + + +

The main purpose of MemoryRealm is to allow Catalina to + authenticate users, and look up the corresponding security roles, from + the information found in an XML-format configuration file. The format + of this file is described below. When a MemoryRealm + instance is started, it will read the contents of this XML file and create + an "in memory database" of all the valid users and their associated + security roles.

+ +

Each time that Catalina needs to authenticate a user, it will call + the authenticate() method of this Realm implementation, + passing the username and password that were specified by the user. If + we find the user in the database (and match on the password), we accumulate + all of the security roles that are defined for this user, and create a + new GenericPrincipal object to be returned. If the user + is not authenticated, we return null instead. The + GenericUser object caches the set of security roles that + were owned by this user at the time of authentication, so that calls to + isUserInRole() can be answered without going back to the + database every time.

+ +
+ + + + + +

Configurable Properties

+ +

The implementation shall support the following properties + that can be configured with JavaBeans property setters:

+
    +
  • Configurable debugging detail level.
  • +
  • Configurable file pathname (absolute or relative to + $CATALINA_BASE of the XML file containing our + defined users. [conf/tomcat-users.xml].
  • +
+ +

Lifecycle Functionality

+ +

The following processing must be performed when the start() + method is called:

+
    +
  • Open and parse the specified XML file.
  • +
  • Create an in-memory database representation of the XML file + contents.
  • +
  • NOTE - There is no requirement to recognize + subsequent changes to the contents of the XML file.
  • +
+ +

The following processing must be performed when the stop() + method is called:

+
    +
  • Release object references to the in-memory database representation.
  • +
+ + +

Method authenticate() Functionality

+ +

When authenticate() is called, the following processing + is required:

+
    +
  • Select the one and only "user" instance from the in-memory database, + based on matching the specified username. If there is no such + instance, return null.
  • +
  • Authenticate the user by comparing the (possibly encrypted) password + value that was received against the password presented by the user. + If there is no match, return null.
  • +
  • Construct a new instance of class + org.apache.catalina.realm.GenericPrincipal (if not + already using this as the internal database representation) that + contains the authenticated username and a List of the + security roles associated with this user.
  • +
  • Return the newly constructed GenericPrincipal.
  • +
+ + +

Method hasRole() Functionality

+ +

When hasRole() is called, the following processing + is required:

+
    +
  • The principal that is passed as an argument SHOULD + be one that we returned (instanceof class + org.apache.catalina.realm.GenericPrincipal, with a + realm property that is equal to our instance.
  • +
  • If the passed principal meets these criteria, check + the specified role against the list returned by + getRoles(), and return true if the + specified role is included; otherwise, return false.
  • +
  • If the passed principal does not meet these criteria, + return false.
  • +
+ +
+ +
+ + +
+ +

In addition the the assertions implied by the functionality requirements + listed above, the following additional assertions shall be tested to + validate the behavior of MemoryRealm:

+
    +
+ +
+ + + + +
diff --git a/webapps/docs/funcspecs/index.xml b/webapps/docs/funcspecs/index.xml new file mode 100644 index 000000000000..dfb7f307ddf1 --- /dev/null +++ b/webapps/docs/funcspecs/index.xml @@ -0,0 +1,70 @@ + + + +]> + + + &project; + + + Craig R. McClanahan + Table of Contents + + + + + +
+ +

This documentation area includes functional specifications for +many features supported by the Catalina servlet container +portion of Tomcat. In most cases, these features are not documented in the +underlying Servlet or JSP specifications, so a definition of the expected +correct behavior is important both to implementors of those features, and to +test writers trying to decide what to test.

+ +

The functional specifications are divided into the following categories +in the menu (to the left):

+
    +
  • Administrative Apps - Overall requirements for supporting an + ability to configure and operate a Tomcat installation through tools, + as well as detailed requirements for the tools themselves.
  • +
  • Internal Servlets - Requirements for Catalina features that are + implemented as internal, container-managed, servlets.
  • +
  • Realm Implementations - Requirements for the implementations of + the org.apache.catalina.Realm interface (providing access to + collections of users, passwords and roles) that are included in the + standard Tomcat distribution.
  • +
+ +

NOTE - In some cases, the contents of these functional specs has +been "reverse engineered" from existing implementations. This exercise is +still useful, because it provides an introduction to what +Catalina does, without being as concerned with how this is +accomplished.

+ +

TODO - Obviously, this area has a long ways to go before +it is complete. Contributions are welcome!

+ +
+ + + + +
diff --git a/webapps/docs/funcspecs/mbean-names.xml b/webapps/docs/funcspecs/mbean-names.xml new file mode 100644 index 000000000000..088a7a7db73c --- /dev/null +++ b/webapps/docs/funcspecs/mbean-names.xml @@ -0,0 +1,753 @@ + + + +]> + + + &project; + + + Craig McClanahan + Amy Roh + Tomcat MBean Names + $Id$ + + + + +
+ +
+ +
+ +

We will be using JMX MBeans as the technology for + implementing manageability of Tomcat.

+ +

One of the key concepts of JMX (and JSR-77) is that each management + bean has a unique name in the MBeanServer's registry, and that + management applications can utilize these names to retrieve the MBean + of interest to them for a particular management operation. + This document proposes a naming convention for MBeans that allows easy + calculation of the name for a particular MBean. For background + information on JMX MBean names, see the Java Management Extensions + Instrumentation and Agent Specification, version 1.0, section 6. + In particular, we will be discussing the String Representation of + ObjectName instances.

+ +
+ +
+ +

Tomcat's servlet container implementation, called Catalina, can be +represented as a hierarchy of objects that contain references to each other. +The object hierarchy can be represented as a tree, or (isomorphically) based +on the nesting of configuration elements in the conf/server.xml +file that is traditionally used to configure Tomcat stand-alone.

+ +

The valid component nestings for Catalina are depicted in the following +table, with columns that contain the following values:

+
    +
  • Pattern - Nesting pattern of XML elements (in the + conf/server.xml file) used to configure this component.
  • +
  • Cardinality - Minimum and maximum number of occurrences of + this element at this nesting position, which also corresponds to the + minimum and maximum number of Catalina components.
  • +
  • Identifier - Name of the JavaBeans property of this component + that represents the unique identifier (within the nested hierarchy), + if any.
  • +
  • MBean ObjectName - The portion of the MBean object name that + appears after the domain name. For now, it should be + assumed that all of these MBeans appear in the default JMX domain.
  • +
+ +

In the MBean ObjectName descriptions, several types of symbolic +expressions are utilized to define variable text that is replaced by +corresponding values:

+
    +
  • ${GROUP} - One of the standard MBean names of the specified + "group" category. For example, the expression ${REALM} + represents the values like JDBCRealm and JAASRealm + that identify the various MBeans for possible Realm components.
  • +
  • ${name} - Replaced by the value of property name + from the current component.
  • +
  • ${parent.name} - Replaced by the value of property + name from a parent of the current component, with the + parent's type identified by parent.
  • +
  • ${###} - An arbitrary numeric identifier that preserves + order but has no other particular meaning. In general, the server will + assign numeric values to existing instances with large gaps into which + new items can be configured if desired.
  • +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
PatternCardinalityIdentifierMBean ObjectName
Server1..1(none)type=${SERVER}
Server / Listener0..n(none)type=${LISTENER}, sequence=${###}
Server / Service1..nnametype=${SERVICE}, name=${name}
Server / Service / Connector1..naddress, porttype=${CONNECTOR}, service=${service}, port=${port}, + address=${address}
Server / Service / Connector / Factory0..1(none)(Only defined explicitly for an SSL connector, but can be treated + as part of the connector component)
Server / Service / Connector / Listener0..n(none)type=${LISTENER}, sequence=${###}, service=${service}, + port=${connector.port}, address=${connector.address}
Server / Service / Engine1..1(none)type=${ENGINE}, service=${service.name}
Server / Service / Engine / Host1..nnametype=${HOST}, host=${name}, + service=${service.name}
Server / Service / Engine / Host / Context1..npathtype=${CONTEXT}, path=${path}, host=${host.name}, + service=${service.name}
Server / Service / Engine / Host / Context / InstanceListener0..n(none)type=${INSTANCE-LISTENER}, sequence=${###}, path=${context.path}, + host=${host.name}, service=${service.name}
Server / Service / Engine / Host / Context / Listener0..n(none)type=${LISTENER}, sequence=${###}, path=${context.path}, + host=${host.name}, service=${service.name}
Server / Service / Engine / Host / Context / Loader0..1(none)type=${LOADER}, path=${context.path}, host=${host.name}, + service=${service.name}
Server / Service / Engine / Host / Context / Manager0..1(none)type=${MANAGER}, path=${context.path}, host=${host.name}, + service=${service.name}
Server / Service / Engine / Host / Context / Realm0..1(none)type=${REALM}, path=${context.path}, host=${host.name}, + service=${service.name}
Server / Service / Engine / Host / Context / Resources0..1(none)type=${RESOURCES}, path=${context.path}, host=${host.name}, + service=${service.name}
Server / Service / Engine / Host / Context / Valve0..n(none)type=${VALVE}, sequence=${###}, path=${context.path}, + host=${host.name}, service=${service.name}
Server / Service / Engine / Host / Context / Wrapper0..n(none)j2eeType=Servlet,name=${name}, + WebModule=//${host.name}/${context.name}, + J2EEApplication=${context.J2EEApplication}, + J2EEServer=${context.J2EEServer}
Server / Service / Engine / Host / Context / WrapperLifecycle0..n(none)type=${WRAPPER-LIFECYCLE}, sequence=${###}, path=${context.path}, + host=${host.name}, service=${service.name}
Server / Service / Engine / Host / Context / WrapperListener0..n(none)type=${WRAPPER-LISTENER}, sequence=${###}, path=${context.path}, + host=${host.name}, service=${service.name}
Server / Service / Engine / Host / Listener0..n(none)type=${LISTENER}, sequence=${###}, host=${host.name}, + service=${service.name}
Server / Service / Engine / Host / Realm0..1(none)type=${REALM}, host=${host.name}, + service=${service.name}
Server / Service / Engine / Host / Valve0..n(none)type=${VALVE}, sequence=${###}, + host=${host.name}, service=${service.name}
Server / Service / Engine / Listener0..n(none)type=${LISTENER}, sequence=${###} + (FIXME - disambiguate from Server / Service / + Listener)
Server / Service / Engine / Realm0..1(none)type=${REALM}, service=${service.name}
Server / Service / Engine / Valve0..n(none)type=${VALVE}, sequence=${###}, + service=${service.name}
Server / Service / Listener0..n(none)type=${LISTENER}, sequence=${###} + (FIXME - disambiguate from Server / Service / + Engine / Listener)
+ +
+ +
+ +

The following MBean names shall be defined in the resource file +/org/apache/catalina/mbeans/mbeans-descriptors.xml (and +therefore available for use within the Administration/Configuration +web application for Tomcat):

+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
MBean NameGroup NameCatalina InterfaceImplementation Class
AccessLogValveVALVEorg.apache.catalina.Valveorg.apache.catalina.valves.AccessLogValve
BasicAuthenticatorVALVEorg.apache.catalina.Valveorg.apache.catalina.authenticator.BasicAuthenticator
CertificatesValveVALVEorg.apache.catalina.Valveorg.apache.catalina.valves.CertificatesValve
ContextConfigLISTENERorg.apache.catalina.LifecycleListenerorg.apache.catalina.startup.ContextConfig
ContextEnvironmentRESOURCESorg.apache.catalina.deploy.ContextEnvironmentorg.apache.catalina.deploy.ContextEnvironment
ContextResourceRESOURCESorg.apache.catalina.deploy.ContextResourceorg.apache.catalina.deploy.ContextResource
ContextResourceLinkRESOURCESorg.apache.catalina.deploy.ContextResourceLinkorg.apache.catalina.deploy.ContextResourceLink
CoyoteConnectorCONNECTORorg.apache.catalina.Connectororg.apache.coyote.tomcat4.CoyoteConnector
DigestAuthenticatorVALVEorg.apache.catalina.Valveorg.apache.catalina.authenticator.DigestAuthenticator
EngineConfigLISTENERorg.apache.catalina.LifecycleListenerorg.apache.catalina.startup.EngineConfig
ErrorReportValveVALVEorg.apache.catalina.Valveorg.apache.catalina.valves.ErrorReportValve
ErrorDispatcherValveVALVEorg.apache.catalina.Valveorg.apache.catalina.valves.ErrorDispatcherValve
FormAuthenticatorVALVEorg.apache.catalina.Valveorg.apache.catalina.authenticator.FormAuthenticator
GroupGROUPorg.apache.catalina.Grouporg.apache.catalina.Group
HostConfigLISTENERorg.apache.catalina.LifecycleListenerorg.apache.catalina.startup.HostConfig
HttpConnector10CONNECTORorg.apache.catalina.Connectororg.apache.catalina.connector.http10.HttpConnector
HttpConnector11CONNECTORorg.apache.catalina.Connectororg.apache.catalina.connector.http.HttpConnector
JAASRealmREALMorg.apache.catalina.Realmorg.apache.catalina.realm.JAASRealm
JDBCRealmREALMorg.apache.catalina.Realmorg.apache.catalina.realm.JDBCRealm
JDBCUserDatabaseUSERDATABASEorg.apache.catalina.users.JDBCUserDatabaseorg.apache.catalina.users.JDBCUserDatabase
JNDIRealmREALMorg.apache.catalina.Realmorg.apache.catalina.realm.JNDIRealm
MBeanFactoryorg.apache.catalina.mbeans.MBeanFactory
MemoryRealmREALMorg.apache.catalina.Realmorg.apache.catalina.realm.MemoryRealm
MemoryUserDatabaseUSERDATABASEorg.apache.catalina.users.MemoryUserDatabaseorg.apache.catalina.users.MemoryUserDatabase
NamingContextListenerLISTENERorg.apache.catalina.LifecycleListenerorg.apache.catalina.core.NamingContextListener
NamingResourcesRESOURCESorg.apache.catalina.deploy.NamingResourcesorg.apache.catalina.deploy.NamingResources
NonLoginAuthenticatorVALVEorg.apache.catalina.Valveorg.apache.catalina.authenticator.NonLoginAuthenticator
PersistentManagerMANAGERorg.apache.catalina.Managerorg.apache.catalina.session.PersistentManager
RemoteAddrValveVALVEorg.apache.catalina.Valveorg.apache.catalina.valves.RemoteAddrValve
RemoteHostValveVALVEorg.apache.catalina.Valveorg.apache.catalina.valves.RemoteHostValve
RequestDumperValveVALVEorg.apache.catalina.Valveorg.apache.catalina.valves.RequestDumperValve
RoleROLEorg.apache.catalina.Roleorg.apache.catalina.Role
SingleSignOnVALVEorg.apache.catalina.Valveorg.apache.catalina.valves.SingleSignOn
SSLAuthenticatorVALVEorg.apache.catalina.Valveorg.apache.catalina.authenticator.SSLAuthenticator
StandardContextCONTEXTorg.apache.catalina.Contextorg.apache.catalina.core.StandardContext
StandardContextValveVALVEorg.apache.catalina.Valveorg.apache.catalina.core.StandardContextValve
StandardEngineENGINEorg.apache.catalina.Engineorg.apache.catalina.core.StandardEngine
StandardEngineValveVALVEorg.apache.catalina.Valveorg.apache.catalina.core.StandardEngineValve
StandardHostHOSTorg.apache.catalina.Hostorg.apache.catalina.core.StandardHost
StandardHostValveVALVEorg.apache.catalina.Valveorg.apache.catalina.core.StandardHostValve
StandardManagerMANAGERorg.apache.catalina.Managerorg.apache.catalina.session.StandardManager
StandardServerSERVERorg.apache.catalina.Serverorg.apache.catalina.core.StandardServer
StandardServiceSERVICEorg.apache.catalina.Serviceorg.apache.catalina.core.StandardService
StandardWrapperWRAPPERorg.apache.catalina.Wrapperorg.apache.catalina.core.StandardWrapper
StandardWrapperValveVALVEorg.apache.catalina.Valveorg.apache.catalina.core.StandardWrapperValve
UserUSERorg.apache.catalina.Userorg.apache.catalina.User
UserDatabaseRealmREALMorg.apache.catalina.Realmorg.apache.catalina.realm.UserDatabaseRealm
WebappLoaderLOADERorg.apache.catalina.Loaderorg.apache.catalina.loader.WebappLoader
+ +
+ +
+ +

The managed objects in the JSR-77 object hierarchy correspond +to the specified MBean names or groups as follows:

+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
JSR-77 Managed ObjectMBean Name or GroupComments
J2EEServer${SERVICE}
Node${SERVICE}Tomcat supports a single node only.
Port${CONNECTOR}
Servlet${WRAPPER}
WebModule${CONTEXT}
+ +
+ +
+ +

The deployment objects in the JSR-88 API object hierarchy correspond +to the specified MBean names or groups as follows:

+ + + + + + + + + + + + + + + + + + + + + +
JSR-88 API ObjectMBean Name or GroupComments
DeployableObject${CONTEXT}Context deployment info plus the corresponding WAR file
Target${HOST}
+ +
+ + + +
diff --git a/webapps/docs/funcspecs/project.xml b/webapps/docs/funcspecs/project.xml new file mode 100644 index 000000000000..ed03e47d17ea --- /dev/null +++ b/webapps/docs/funcspecs/project.xml @@ -0,0 +1,54 @@ + + + + + Catalina Functional Specifications + + + Catalina Functional Specifications + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/webapps/docs/html-manager-howto.xml b/webapps/docs/html-manager-howto.xml new file mode 100644 index 000000000000..e8d5990cb2f5 --- /dev/null +++ b/webapps/docs/html-manager-howto.xml @@ -0,0 +1,585 @@ + + + +]> + + + &project; + + + Glenn L. Nielsen + Tomcat Web Application Manager How To + + + + +
+ +
+ +
+ +

In many production environments it is very useful to have the capability +to manage your web applications without having to shut down and restart +Tomcat. This document is for the HTML web interface to the web application +manager.

+ +

The interface is divided into six sections:

+
    +
  • Message - Displays success and failure messages.
  • +
  • Manager - General manager operations like list and + help.
  • +
  • Applications - List of web applications and + commands.
  • +
  • Deploy - Deploying web applications.
  • +
  • Diagnostics - Identifying potential problems.
  • +
  • Server Information - Information about the Tomcat + server.
  • +
+ +
+ +
+ +

+Displays information about the success or failure of the last web application +manager command you performed. If it succeeded OK is displayed +and may be followed by a success message. If it failed FAIL +is displayed followed by an error message. Common failure messages are +documented below for each command. The complete list of failure messages for +each command can be found in the manager web +application documentation. +

+ +
+ +
+ +

The Manager section has three links:

+
    +
  • List Applications - Redisplay a list of web + applications.
  • +
  • HTML Manager Help - A link to this document.
  • +
  • Manager Help - A link to the comprehensive Manager + App HOW TO.
  • +
+ +
+ +
+ +

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:

+
    +
  • Path - The web application context path.
  • +
  • Display Name - The display name for the web application + if it has one configured in its "web.xml" file.
  • +
  • Running - Whether the web application is running and + available (true), or not running and unavailable (false).
  • +
  • Sessions - 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.
  • +
  • Commands - 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: +
      +
    • Start - Start a web application which had been + stopped.
    • +
    • Stop - Stop a web application which is currently + running and make it unavailable.
    • +
    • Reload - Reload the web application so that new + ".jar" files in /WEB-INF/lib/ or new classes in + /WEB-INF/classes/ can be used.
    • +
    • Undeploy - Stop and then remove this web + application from the server.
    • +
    +
  • +
+ + + +

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.

+ +

If this command succeeds, you will see a Message like this:

+ +OK - Started application at context path /examples + + +

Otherwise, the Message will start with FAIL and include an +error message. Possible causes for problems include:

+
    +
  • Encountered exception +
    +

    An exception was encountered trying to start the web application. + Check the Tomcat logs for the details.

    +
  • +
  • Invalid context path was specified +
    +

    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.

    +
  • +
  • No context exists for path /foo +
    +

    There is no deployed application on the context path + that you specified.

    +
  • +
  • No context path was specified +
    + The path parameter is required. +
  • +
+ +
+ + + +

Signal an existing application to make itself unavailable, but leave it +deployed. 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.

+ +

If this command succeeds, you will see a Message like this:

+ +OK - Stopped application at context path /examples + + +

Otherwise, the Message will start with FAIL and include an +error message. Possible causes for problems include:

+
    +
  • Encountered exception +
    +

    An exception was encountered trying to stop the web application. + Check the Tomcat logs for the details.

    +
  • +
  • Invalid context path was specified +
    +

    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.

    +
  • +
  • No context exists for path /foo +
    +

    There is no deployed application on the context path + that you specified.

    +
  • +
  • No context path was specified +
    + The path parameter is required. +
  • +
+ +
+ + + +

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 /WEB-INF/classes +directory or when you have added or updated jar files in the +/WEB-INF/lib directory. +

+

NOTE: The /WEB-INF/web.xml +web application configuration file is not checked on a reload; +the previous web.xml configuration is used. +If you have made changes to your web.xml file you must stop +then start the web application. +

+ +

If this command succeeds, you will see a Message like this:

+ +OK - Reloaded application at context path /examples + + +

Otherwise, the Message will start with FAIL and include an +error message. Possible causes for problems include:

+
    +
  • Encountered exception +
    +

    An exception was encountered trying to restart the web application. + Check the Tomcat logs for the details.

    +
  • +
  • Invalid context path was specified +
    +

    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.

    +
  • +
  • No context exists for path /foo +
    +

    There is no deployed application on the context path + that you specified.

    +
  • +
  • No context path was specified +
    + The path parameter is required. +
  • +
  • Reload not supported on WAR deployed at path /foo +
    + Currently, application reloading (to pick up changes to the classes or + web.xml file) is not supported when a web application is + installed directly from a WAR file, which happens when the host is + configured to not unpack WAR files. As it only works when the web + application is installed from an unpacked directory, if you are using + a WAR file, you should undeploy and then deploy + the application again to pick up your changes. +
  • +
+ +
+ + + +

WARNING - This command will delete the +contents of the web application directory and/or ".war" file if it exists within +the appBase directory (typically "webapps") for this virtual host +. The web application temporary work directory is also deleted. If +you simply want to take an application out of service, you should use the +/stop command instead.

+ +

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 +/deploy Ant command, and the related deploy features available +in the HTML manager.

+ +

If this command succeeds, you will see a Message like this:

+ +OK - Undeployed application at context path /examples + + +

Otherwise, the Message will start with FAIL and include an +error message. Possible causes for problems include:

+
    +
  • Encountered exception +
    +

    An exception was encountered trying to undeploy the web application. + Check the Tomcat logs for the details.

    +
  • +
  • Invalid context path was specified +
    +

    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.

    +
  • +
  • No context exists for path /foo +
    +

    There is no deployed application on the context path + that you specified.

    +
  • +
  • No context path was specified +
    + The path parameter is required. +
  • +
+ +
+ +
+ +
+ +

Web applications can be deployed using files or directories located +on the Tomcat server or you can upload a web application archive (WAR) +file to the server.

+ +

To install an application, fill in the appropriate fields for the type +of install you want to do and then submit it using the Install +button.

+ + + +

Deploy and start a new web application, attached to the specified Context +Path: (which must not be in use by any other web application). +This command is the logical opposite of the Undeploy command.

+ +

There are a number of different ways the deploy command can be used.

+ +

Deploy a Directory or WAR by URL

+ +

Install a web application directory or ".war" file located on the Tomcat +server. If no Context Path is specified, the directory name or the +war file name without the ".war" extension is used as the path. The +WAR or Directory URL specifies a URL (including the file: +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 java.net.JarURLConnection class. Use only URLs that +refer to the entire WAR file.

+ +

In this example the web application located in the directory +C:\path\to\foo on the Tomcat server (running on Windows) +is deployed as the web application context named /footoo.

+ +Context Path: /footoo +WAR or Directory URL: file:C:/path/to/foo + + + +

In this example the ".war" file /path/to/bar.war on the +Tomcat server (running on Unix) is deployed as the web application +context named /bar. Notice that there is no path +parameter so the context path defaults to the name of the web application +archive file without the ".war" extension.

+ +WAR or Directory URL: jar:file:/path/to/bar.war!/ + + + +

Deploy a Directory or War from the Host appBase

+ +

Install a web application directory or ".war" file located in your Host +appBase directory. If no Context Path is specified the directory name +or the war file name without the ".war" extension is used as the path.

+ +

In this example the web application located in a subdirectory named +foo in the Host appBase directory of the Tomcat server is +deployed as the web application context named /foo. Notice +that there is no path parameter so the context path defaults +to the name of the web application directory.

+ +WAR or Directory URL: foo + + + +

In this example the ".war" file bar.war located in your +Host appBase directory on the Tomcat server is deployed as the web +application context named /bartoo.

+ +Context Path: /bartoo +WAR or Directory URL: bar.war + + + +

Deploy using a Context configuration ".xml" file

+ +

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 Path +is not used when installing a web application using a context ".xml" +configuration file.

+ +

A Context configuration ".xml" file can contain valid XML for a +web application Context just as if it were configured in your +Tomcat server.xml configuration file. Here is an +example for Tomcat running on Windows:

+ +<Context path="/foobar" docBase="C:\path\to\application\foobar" + debug="0"> + + <!-- Link to the user database we will get roles from --> + <ResourceLink name="users" global="UserDatabase" + type="org.apache.catalina.UserDatabase"/> + +</Context> + + + +

Use of the WAR or Directory URL is optional. When used +to select a web application ".war" file or directory it overrides any +docBase configured in the context configuration ".xml" file.

+ +

Here is an example of installing an application using a Context +configuration ".xml" file for Tomcat running on Windows.

+ +XML Configuration file URL: file:C:/path/to/context.xml + + + +

Here is an example of installing an application using a Context +configuration ".xml" file and a web application ".war" file located +on the server (Tomcat running on Unix).

+ +XML Configuration file URL: file:/path/to/context.xml +WAR or Directory URL: jar:file:/path/to/bar.war!/ + + + +
+ + + +

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.

+ +

Use the Browse button to select a WAR file to upload to the +server from your local desktop system.

+ +

The .WAR file may include Tomcat specific deployment configuration, by +including a Context configuration XML file in +/META-INF/context.xml.

+ +

Upload of a WAR file could fail for the following reasons:

+
    +
  • File uploaded must be a .war +
    +

    The upload install will only accept files which have the filename + extension of ".war".

    +
  • +
  • War file already exists on server +
    +

    If a war file of the same name already exists in your Host's + appBase the upload will fail. Either undeploy the existing war file + from your Host's appBase or upload the new war file using a different + name.

    +
  • +
  • File upload failed, no file +
    +

    The file upload failed, no file was received by the server.

    +
  • +
  • Install Upload Failed, Exception: +
    +

    The war file upload or install failed with a Java Exception. + The exception message will be listed.

    +
  • +
+ +
+ + + +

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.

+ +

If the application war or directory is deployed 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.

+ +

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.

+ +
+ + + +

If deployment and startup is successful, you will receive a Message +like this:

+ +OK - Deployed application at context path /foo + + +

Otherwise, the Message will start with FAIL and include an +error message. Possible causes for problems include:

+
    +
  • Application already exists at path /foo +
    +

    The context paths for all currently running web applications must be + unique. Therefore, you must either undeploy the existing web + application using this context path, or choose a different context path + for the new one.

    +
  • +
  • Document base does not exist or is not a readable directory +
    +

    The URL specified by the WAR or Directory URL: 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 WAR or Directory URL: field.

    +
  • +
  • Encountered exception +
    +

    An exception was encountered trying to start the new web application. + Check the Tomcat logs for the details, but likely explanations include + problems parsing your /WEB-INF/web.xml file, or missing + classes encountered when initializing application event listeners and + filters.

    +
  • +
  • Invalid application URL was specified +
    +

    The URL for the WAR or Directory URL: field that you specified + was not valid. Such URLs must start with file:, and URLs + for a WAR file must end in ".war".

    +
  • +
  • Invalid context path was specified +
    +

    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.

    +
  • +
  • Context path must match the directory or WAR file name: +
    + If the application war or directory is deployed 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. +
  • +
  • Only web applications in the Host web application directory can + be deployed +
    + 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. +
  • +
+ +
+
+ +
+ + + +

The find leaks diagnostic triggers a full garbage collection. It +should be used with extreme caution on production systems.

+ +

The find leaks diagnostic attempts to identify web applications that have +caused memory leaks when they were stopped, reloaded or undeployed. Results +should always be confirmed +with a profiler. The diagnostic uses additional functionality provided by the +StandardHost implementation. It will not work if a custom host is used that +does not extend StandardHost.

+ +

This diagnostic will list context paths for the web applications that were +stopped, reloaded or undeployed, but which classes from the previous runs +are still present in memory, thus being a memory leak. If an application +has been reloaded several times, it may be listed several times.

+ +

Explicitly triggering a full garbage collection from Java code is documented +to be unreliable. Furthermore, depending on the JVM used, there are options to +disable explicit GC triggering, like -XX:+DisableExplicitGC. +If you want to make sure, that the diagnostics were successfully running a full GC, +you will need to check using tools like GC logging, JConsole or similar.

+ +
+
+ +
+ +

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.

+ +
+ + + +
diff --git a/webapps/docs/images/add.gif b/webapps/docs/images/add.gif new file mode 100644 index 000000000000..0774d074e5e4 Binary files /dev/null and b/webapps/docs/images/add.gif differ diff --git a/webapps/docs/images/asf-logo.gif b/webapps/docs/images/asf-logo.gif new file mode 100644 index 000000000000..22eb9d7358ef Binary files /dev/null and b/webapps/docs/images/asf-logo.gif differ diff --git a/webapps/docs/images/code.gif b/webapps/docs/images/code.gif new file mode 100644 index 000000000000..d27307b5c094 Binary files /dev/null and b/webapps/docs/images/code.gif differ diff --git a/webapps/docs/images/design.gif b/webapps/docs/images/design.gif new file mode 100644 index 000000000000..f5db0a9fc783 Binary files /dev/null and b/webapps/docs/images/design.gif differ diff --git a/webapps/docs/images/docs.gif b/webapps/docs/images/docs.gif new file mode 100644 index 000000000000..d64a4a18c405 Binary files /dev/null and b/webapps/docs/images/docs.gif differ diff --git a/webapps/docs/images/fix.gif b/webapps/docs/images/fix.gif new file mode 100644 index 000000000000..d59ad642ba46 Binary files /dev/null and b/webapps/docs/images/fix.gif differ diff --git a/webapps/docs/images/printer.gif b/webapps/docs/images/printer.gif new file mode 100644 index 000000000000..5021187b064c Binary files /dev/null and b/webapps/docs/images/printer.gif differ diff --git a/webapps/docs/images/tomcat.gif b/webapps/docs/images/tomcat.gif new file mode 100644 index 000000000000..61756736b823 Binary files /dev/null and b/webapps/docs/images/tomcat.gif differ diff --git a/webapps/docs/images/tomcat.svg b/webapps/docs/images/tomcat.svg new file mode 100644 index 000000000000..cfa87dba9f27 --- /dev/null +++ b/webapps/docs/images/tomcat.svg @@ -0,0 +1,589 @@ + + + + + + + + + + + + + + +]> + + + + + + + + + + + + + + + + + + + + + + + 2006-05-09T08:17:21Z + 2006-05-09T08:37:38Z + Illustrator + + + + JPEG + 256 + 184 + /9j/4AAQSkZJRgABAgEASABIAAD/7QAsUGhvdG9zaG9wIDMuMAA4QklNA+0AAAAAABAASAAAAAEA AQBIAAAAAQAB/+4ADkFkb2JlAGTAAAAAAf/bAIQABgQEBAUEBgUFBgkGBQYJCwgGBggLDAoKCwoK DBAMDAwMDAwQDA4PEA8ODBMTFBQTExwbGxscHx8fHx8fHx8fHwEHBwcNDA0YEBAYGhURFRofHx8f Hx8fHx8fHx8fHx8fHx8fHx8fHx8fHx8fHx8fHx8fHx8fHx8fHx8fHx8fHx8f/8AAEQgAuAEAAwER AAIRAQMRAf/EAaIAAAAHAQEBAQEAAAAAAAAAAAQFAwIGAQAHCAkKCwEAAgIDAQEBAQEAAAAAAAAA AQACAwQFBgcICQoLEAACAQMDAgQCBgcDBAIGAnMBAgMRBAAFIRIxQVEGE2EicYEUMpGhBxWxQiPB UtHhMxZi8CRygvElQzRTkqKyY3PCNUQnk6OzNhdUZHTD0uIIJoMJChgZhJRFRqS0VtNVKBry4/PE 1OT0ZXWFlaW1xdXl9WZ2hpamtsbW5vY3R1dnd4eXp7fH1+f3OEhYaHiImKi4yNjo+Ck5SVlpeYmZ qbnJ2en5KjpKWmp6ipqqusra6voRAAICAQIDBQUEBQYECAMDbQEAAhEDBCESMUEFURNhIgZxgZEy obHwFMHR4SNCFVJicvEzJDRDghaSUyWiY7LCB3PSNeJEgxdUkwgJChgZJjZFGidkdFU38qOzwygp 0+PzhJSktMTU5PRldYWVpbXF1eX1RlZmdoaWprbG1ub2R1dnd4eXp7fH1+f3OEhYaHiImKi4yNjo +DlJWWl5iZmpucnZ6fkqOkpaanqKmqq6ytrq+v/aAAwDAQACEQMRAD8A9U4q7FXYq7FXYq7FXYq7 FXYq7FXYq7FXYq7FXYq7FXhH/OYHnWfQ/wAurfRLSUxXXmK49GQqaN9VtwJJqH3cxqfYnFXhP5Y/ 85O+f/JU0enaw769okbBJLS8ZvrUKg0IhnarDj/I9R2HHFX2F+Xn5neT/P8ApP6R8u3glKAfW7KS iXNuzdFljqaezCqnsTirK8VdirsVdirsVdirsVdirC/zM/Nvyd+XemC71255Xcqk2WmQUa5nI2+F CRxUd3ag+nbFXx1+Zf8Azkn+YvneaW1tLh9C0NgwXTrB2V3Sm/rzji8m3UDitP2cVfV//OOfmabz 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 + + + + + + + image/svg+xml + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + 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 +/Dn4G1vgFa2715u9zrn+L1T7Dxc= + + + diff --git a/webapps/docs/images/update.gif b/webapps/docs/images/update.gif new file mode 100644 index 000000000000..31e22abbc7a2 Binary files /dev/null and b/webapps/docs/images/update.gif differ diff --git a/webapps/docs/images/void.gif b/webapps/docs/images/void.gif new file mode 100644 index 000000000000..e565824aafaf Binary files /dev/null and b/webapps/docs/images/void.gif differ diff --git a/webapps/docs/index.xml b/webapps/docs/index.xml new file mode 100644 index 000000000000..b913b8df87d6 --- /dev/null +++ b/webapps/docs/index.xml @@ -0,0 +1,202 @@ + + + +]> + + + &project; + + + Craig R. McClanahan + Remy Maucherat + Yoav Shapira + Documentation Index + + + + +
+ +

This is the top-level entry point of the documentation bundle for the +Apache Tomcat Servlet/JSP container. Apache Tomcat version 7.0 +implements the +Servlet 3.0 and JavaServer Pages 2.2 specifications from the +Java Community Process, and includes many +additional features that make it a useful platform for developing and deploying +web applications and web services.

+ +

Select one of the links from the navigation menu (to the left) to drill +down to the more detailed documentation that is available. Each available +manual is described in more detail below.

+ +
+ + +
+ +

The following documents will assist you in downloading, installing +Apache Tomcat 7, and using many of the Apache Tomcat features.

+ +
    +
  1. Introduction - A + brief, high level, overview of Apache Tomcat.
  2. +
  3. Setup - How to install and run + Apache Tomcat on a variety of platforms.
  4. +
  5. First web application + - An introduction to the concepts of a web application as defined + in the Servlet + 2.4 Specification. Covers basic organization of your web application + source tree, the structure of a web application archive, and an + introduction to the web application deployment descriptor + (/WEB-INF/web.xml).
  6. +
  7. Deployer - + Operating the Apache Tomcat Deployer to deploy, precompile, and validate web + applications.
  8. +
  9. Manager - + Operating the Manager web app to deploy, undeploy, and + redeploy applications while Apache Tomcat is running.
  10. +
  11. Realms and Access Control + - Description of how to configure Realms (databases of users, + passwords, and their associated roles) for use in web applications that + utilize Container Managed Security.
  12. +
  13. Security Manager + - Configuring and using a Java Security Manager to + support fine-grained control over the behavior of your web applications. +
  14. +
  15. JNDI Resources + - Configuring standard and custom resources in the JNDI naming context + that is provided to each web application.
  16. +
  17. + JDBC DataSource + - Configuring a JNDI DataSoure with a DB connection pool. + Examples for many popular databases.
  18. +
  19. Classloading + - Information about class loading in Apache Tomcat, including where to place + your application classes so that they are visible.
  20. +
  21. JSPs + - Information about Jasper configuration, as well as the JSP compiler + usage.
  22. +
  23. SSL - + Installing and + configuring SSL support so that your Apache Tomcat will serve requests using + the https protocol.
  24. +
  25. SSI - + Using Server Side Includes in Apache Tomcat.
  26. +
  27. CGI - + Using CGIs with Apache Tomcat.
  28. +
  29. Proxy Support - + Configuring Apache Tomcat to run behind a proxy server (or a web server + functioning as a proxy server).
  30. +
  31. MBean Descriptor - + Configuring MBean descriptors files for custom components.
  32. +
  33. Default Servlet - + Configuring the default servlet and customizing directory listings.
  34. +
  35. Apache Tomcat Clustering - + Enable session replication in a Apache Tomcat environment.
  36. +
  37. Balancer - + Configuring, using, and extending the load balancer application.
  38. +
  39. Connectors - + Connectors available in Apache Tomcat, and native web server integration.
  40. +
  41. Monitoring and Management - + Enabling JMX Remote support, and using tools to monitor and manage Apache Tomcat.
  42. +
  43. Logging - + Configuring logging in Apache Tomcat.
  44. +
  45. Apache Portable Runtime - + Using APR to provide superior performance, scalability and better + integration with native server technologies.
  46. +
  47. Virtual Hosting - + Configuring virtual hosting in Apache Tomcat.
  48. +
  49. Advanced IO - + Extensions available over regular, blocking IO.
  50. +
  51. Additional Components - + Obtaining additional, optional components.
  52. + +
+ +
+ + +
+ +

The following documents are aimed at System Administrators who +are responsible for installing, configuring, and operating an Apache Tomcat server. +

+ + +
+ + +
+ +

The following documents are for Java developers who wish to contribute to +the development of the Apache Tomcat project.

+
    +
  • Building from Source - + Details the steps necessary to download Apache Tomcat source code (and the + other packages that it depends on), and build a binary distribution from + those sources. +
  • +
  • Changelog - Details the + changes made to Apache Tomcat. +
  • +
  • Status - + Apache Tomcat development status. +
  • +
  • Developers - List of active + Apache Tomcat contributors. +
  • +
  • Functional Specifications + - Requirements specifications for features of the Catalina servlet + container portion of Apache Tomcat.
  • +
  • Javadocs + - Javadoc API documentation for Apache Tomcat's internals.
  • +
  • Apache Tomcat Architecture + - Documentation of the Apache Tomcat Server Architecture.
  • +
+ +
+ + + +
diff --git a/webapps/docs/introduction.xml b/webapps/docs/introduction.xml new file mode 100644 index 000000000000..56beb0a423e7 --- /dev/null +++ b/webapps/docs/introduction.xml @@ -0,0 +1,151 @@ + + + +]> + + + &project; + + + Robert Slifka + Introduction + + + + +
+ +
+ +
+ +

For administrators and web developers alike, there are some important bits +of information you should familiarize yourself with before starting out. This +document serves as a brief introduction to some of the concepts and +terminology behind the Tomcat container. As well, where to go when you need +help.

+ +
+ + +
+ +

In the course of reading these documents, you'll run across a number of +terms; some specific to Tomcat, and others defined by the +Servlet or +JSP specifications.

+ +
    +
  • Context - In a nutshell, a Context is a + web application.
  • +
  • Term2 - This is it.
  • +
  • Term3 - This is it!
  • +
+ +
+ + +
+ +

Throughout the docs, you'll notice there are numerous references to +$CATALINA_HOME. This represents the root of your Tomcat +installation. When we say, "This information can be found in your +$CATALINA_HOME/README.txt file" we mean to look at the README.txt file at the +root of your Tomcat install. Optionally, Tomcat may be configured for multiple +instances by defining $CATALINA_BASE for each instance. If +multiple instances are not configured, $CATALINA_BASE is the +same as $CATALINA_HOME.

+ +

These are some of the key tomcat directories:

+ +
    +
  • /bin - Startup, shutdown, and other scripts. The + *.sh files (for Unix systems) are functional duplicates of + the *.bat files (for Windows systems). Since the Win32 + command-line lacks certain functionality, there are some additional + files in here.
  • +
  • /conf - Configuration files and related DTDs. The most + important file in here is server.xml. It is the main configuration file + for the container.
  • +
  • /logs - Log files are here by default.
  • +
  • /webapps - This is where your webapps go.
  • +
+ +
+ + +
+ +

This section will acquaint you with the basic information used during +the configuration of the container.

+ +

All of the information in the configuration files is read at startup, +meaning that any change to the files necessitates a restart of the container. +

+ +
+ + +
+ +

While we've done our best to ensure that these documents are clearly +written and easy to understand, we may have missed something. Provided +below are various web sites and mailing lists in case you get stuck.

+ +

As Tomcat 7 is a new release of Tomcat, keep in mind that some of the +issues and solutions vary between the major versions of Tomcat (6.x versus +7.x). As you search around the web, there will be some documentation that +is not relevant to Tomcat 7, but 6.x, 5.x or earlier versions. Doing 3.x +or 4.x things to 7 will probably not work in most cases as the server.xml +files are very different.

+ +
    +
  • Current document - most documents will list potential hangups. Be sure + to fully read the relevant documentation as it will save you much time + and effort. There's nothing like scouring the web only to find out that + the answer was right in front of you all along!
  • +
  • Tomcat FAQ
  • +
  • Tomcat WIKI
  • +
  • Tomcat FAQ at jGuru
  • +
  • Tomcat mailing list archives - numerous sites archive the Tomcat mailing + lists. Since the links change over time, clicking here will search + Google. +
  • +
  • The TOMCAT-USER mailing list, which you can subscribe to + here. If you don't + get a reply, then there's a good chance that your question was probably + answered in the list archives or one of the FAQs. Although questions + about web application development in general are sometimes asked and + answered, please focus your questions on Tomcat-specific issues.
  • +
  • The TOMCAT-DEV mailing list, which you can subscribe to + here. This list is + reserved for discussions about the development of Tomcat + itself. Questions about Tomcat configuration, and the problems you run + into while developing and running applications, will normally be more + appropriate on the TOMCAT-USER list instead.
  • +
+ +

And, if you think something should be in the docs, by all means let us know +on the TOMCAT-DEV list.

+ +
+ + + +
diff --git a/webapps/docs/jasper-howto.xml b/webapps/docs/jasper-howto.xml new file mode 100644 index 000000000000..c85669bc8a2f --- /dev/null +++ b/webapps/docs/jasper-howto.xml @@ -0,0 +1,377 @@ + + + +]> + + + &project; + + + Glenn L. Nielsen + Peter Rossbach + Jasper 2 JSP Engine How To + + + + +
+ +
+ +
+ +

Tomcat 7.0 uses the Jasper 2 JSP Engine to implement +the JavaServer Pages 2.1 +specification.

+ +

Jasper 2 has been redesigned to significantly improve performance over +the original Jasper. In addition to general code improvements the following +changes were made: +

    +
  • JSP Custom Tag Pooling - The java objects instantiated +for JSP Custom Tags can now be pooled and reused. This significantly boosts +the performance of JSP pages which use custom tags.
  • +
  • Background JSP compilation - If you make a change to +a JSP page which had already been compiled Jasper 2 can recompile that +page in the background. The previously compiled JSP page will still be +available to serve requests. Once the new page has been compiled +successfully it will replace the old page. This helps improve availability +of your JSP pages on a production server.
  • +
  • Recompile JSP when included page changes - Jasper 2 +can now detect when a page included at compile time from a JSP has changed +and then recompile the parent JSP.
  • +
  • JDT used to compile JSP pages - The +Eclipse JDT Java compiler is now used to perform JSP java source code +compilation. This compiler loads source dependencies from the container +classloader. Ant and javac can still be used.
  • +
+

+ +

Jasper is implemented using the servlet class +org.apache.jasper.servlet.JspServlet.

+ +
+ +
+ +

By default Jasper is configured for use when doing web application +development. See the section +Production Configuration for information on configuring Jasper +for use on a production Tomcat server.

+ +

The servlet which implements Jasper is configured using init parameters +in your global $CATALINA_BASE/conf/web.xml. + +

    +
  • checkInterval - If development is false and checkInterval +is greater than zero, background compiles are enabled. checkInterval is the time +in seconds between checks to see if a JSP page (and its dependent files) needs +to be recompiled. Default 0 seconds.
  • + +
  • classdebuginfo - Should the class file be compiled with +debugging information? true or false, default +true. +
  • + +
  • classpath - Defines the class path to be used to compile +the generated servlets. This parameter only has an effect if the ServletContext +attribute org.apache.jasper.Constants.SERVLET_CLASSPATH is not set. This +attribute is always set when Jasper is used within Tomcat. By default the +classpath is created dynamically based on the current web application.
  • + +
  • compiler - Which compiler Ant should use to compile JSP +pages. See the Ant documentation for more information. If the value is not set, +then the default Eclipse JDT Java compiler will be used instead of using Ant. +No default value.
  • + +
  • compilerSourceVM - What JDK version are the source files +compatible with? (Default value: 1.6)
  • + +
  • compilerTargetVM - What JDK version are the generated files +compatible with? (Default value: 1.6)
  • + +
  • development - Is Jasper used in development mode? If true, +the frequency at which JSPs are checked for modification may be specified via +the modificationTestInterval parameter.true or false, +default true.
  • + +
  • displaySourceFragment - Should a source fragment be +included in exception messages? true or false, +default true.
  • + +
  • dumpSmap - Should the SMAP info for JSR45 debugging be +dumped to a file? true or false, default +false. false if suppressSmap is true.
  • + +
  • enablePooling - Determines whether tag handler pooling is +enabled. This is a compilation option. It will not alter the behaviour of JSPs +that have already been compiled. true or false, +default true. +
  • + +
  • engineOptionsClass - Allows specifying the Options class +used to configure Jasper. If not present, the default EmbeddedServletOptions +will be used. +
  • + +
  • errorOnUseBeanInvalidClassAttribute - Should Jasper issue +an error when the value of the class attribute in an useBean action is not a +valid bean class? true or false, default +true.
  • + +
  • fork - Have Ant fork JSP page compiles so they are +performed in a separate JVM from Tomcat? true or +false, default true.
  • + +
  • genStringAsCharArray - Should text strings be generated as char +arrays, to improve performance in some cases? Default false.
  • + +
  • ieClassId - The class-id value to be sent to Internet +Explorer when using <jsp:plugin> tags. Default +clsid:8AD9C840-044E-11D1-B3E9-00805F499D93.
  • + +
  • javaEncoding - Java file encoding to use for generating +java source files. Default UTF8.
  • + +
  • keepgenerated - Should we keep the generated Java source +code for each page instead of deleting it? true or +false, default true.
  • + +
  • mappedfile - Should we generate static content with one +print statement per input line, to ease debugging? +true or false, default true.
  • + +
  • maxLoadedJsps - The maximum number of JSPs that will be +loaded for a web application. If more than this number of JSPs are loaded, the +least recently used JSPs will be unloaded so that the number of JSPs loaded at +any one time does not exceed this limit. A value of zero or less indicates no +limit. Default -1
  • + +
  • modificationTestInterval - Causes a JSP (and its dependent +files) to not be checked for modification during the specified time interval +(in seconds) from the last time the JSP was checked for modification. A value of +0 will cause the JSP to be checked on every access. Used in development mode +only. Default is 4 seconds.
  • + +
  • recompileOnFail - If a JSP compilation fails should the +modificationTestInterval be ignored and the next access trigger a re-compilation +attempt? Used in development mode only and is disabled by default as compilation +may be expensive and could lead to excessive resource usage.
  • + +
  • scratchdir - What scratch directory should we use when +compiling JSP pages? Default is the work directory for the current web +application.
  • + +
  • suppressSmap - Should the generation of SMAP info for JSR45 +debugging be suppressed? true or false, default +false.
  • + +
  • trimSpaces - Should white spaces in template text between +actions or directives be trimmed ?, default false.
  • + +
  • xpoweredBy - Determines whether X-Powered-By response +header is added by generated servlet. true or false, +default false.
  • +
+

+ +

The Java compiler from Eclipse JDT in included as the default compiler. It is +an advanced Java compiler which will load all dependencies from the Tomcat class +loader, which will help tremendously when compiling on large installations with +tens of JARs. On fast servers, this will allow sub-second recompilation cycles +for even large JSP pages.

+ +

Apache Ant, which was used in previous Tomcat releases, can be used instead +of the new compiler by simply removing the lib/ecj-*.jar file, +and placing the ant.jar and ant-launcher.jar files +from the latest Ant distribution in the lib folder.

+ +
+ +
+ +

As described in + +bug 39089, a known JVM issue, + +bug 6294277, may cause a +java.lang.InternalError: name is too long to represent exception +when compiling very large JSPs. If this is observed then it may be worked around +by using one of the following: +

    +
  • reduce the size of the JSP
  • +
  • disable SMAP generation and JSR-045 support by setting +suppressSmap to true.
  • +
+

+ +
+ +
+ +

The main JSP optimization which can be done is precompilation of JSPs. +However, this might not be possible (for example, when using the +jsp-property-group feature) or practical, in which case the configuration of the +Jasper servlet becomes critical.

+ +

When using Jasper 2 in a production Tomcat server you should consider making +the following changes from the default configuration. +

    +
  • development - To disable on access checks for JSP +pages compilation set this to false.
  • +
  • genStringAsCharArray - To generate slightly more efficient +char arrays, set this to true.
  • +
  • modificationTestInterval - If development has to be set to +true for any reason (such as dynamic generation of JSPs), setting +this to a high value will improve performance a lot.
  • +
  • trimSpaces - To remove useless bytes from the response, +set this to true.
  • +
+

+ +
+ +
+ +

Using Ant is the preferred way to compile web applications using JSPC. Note +that when pre-compiling JSPs, SMAP information only be included in the final +classes if suppressSmap is false and compile is true. +Use the script given below (a similar script is included in the "deployer" +download) to precompile a webapp: +

+ +

+ +<project name="Webapp Precompilation" default="all" basedir="."> + + <import file="${tomcat.home}/bin/catalina-tasks.xml"/> + + <target name="jspc"> + + <jasper + validateXml="false" + uriroot="${webapp.path}" + webXmlFragment="${webapp.path}/WEB-INF/generated_web.xml" + outputDir="${webapp.path}/WEB-INF/src" /> + + </target> + + <target name="compile"> + + <mkdir dir="${webapp.path}/WEB-INF/classes"/> + <mkdir dir="${webapp.path}/WEB-INF/lib"/> + + <javac destdir="${webapp.path}/WEB-INF/classes" + optimize="off" + debug="on" failonerror="false" + srcdir="${webapp.path}/WEB-INF/src" + excludes="**/*.smap"> + <classpath> + <pathelement location="${webapp.path}/WEB-INF/classes"/> + <fileset dir="${webapp.path}/WEB-INF/lib"> + <include name="*.jar"/> + </fileset> + <pathelement location="${tomcat.home}/lib"/> + <fileset dir="${tomcat.home}/lib"> + <include name="*.jar"/> + </fileset> + <fileset dir="${tomcat.home}/bin"> + <include name="*.jar"/> + </fileset> + </classpath> + <include name="**" /> + <exclude name="tags/**" /> + </javac> + + </target> + + <target name="all" depends="jspc,compile"> + </target> + + <target name="cleanup"> + <delete> + <fileset dir="${webapp.path}/WEB-INF/src"/> + <fileset dir="${webapp.path}/WEB-INF/classes/org/apache/jsp"/> + </delete> + </target> + +</project> + +

+ +

+The following command line can be used to run the script +(replacing the tokens with the Tomcat base path and the path to the webapp +which should be precompiled):
+ +$ANT_HOME/bin/ant -Dtomcat.home=<$TOMCAT_HOME> -Dwebapp.path=<$WEBAPP_PATH> + +

+ +

+Then, the declarations and mappings for the servlets which were generated +during the precompilation must be added to the web application deployment +descriptor. Insert the ${webapp.path}/WEB-INF/generated_web.xml +at the right place inside the ${webapp.path}/WEB-INF/web.xml file. +Restart the web application (using the manager) and test it to verify it is +running fine with precompiled servlets. An appropriate token placed in the +web application deployment descriptor may also be used to automatically +insert the generated servlet declarations and mappings using Ant filtering +capabilities. This is actually how all the webapps distributed with Tomcat +are automatically compiled as part of the build process. +

+ +

+At the jasper2 task you can use the option addWebXmlMappings for +automatic merge the ${webapp.path}/WEB-INF/generated_web.xml +with the current web application deployment descriptor at +${webapp.path}/WEB-INF/web.xml. When you want to use Java 6 +features inside your jsp's, add the following javac compiler task attributes: +source="1.6" target="1.6". For live +applications you can also compile with optimize="on" and +without debug info debug="off". +

+ +

+When you don't want to stop the jsp generation at first jsp syntax error, use +failOnError="false"and with +showSuccess="true" all successfull jsp to java +generation are printed out. Sometimes it is very helpfull, when you cleanup the +generate java source files at ${webapp.path}/WEB-INF/src +and the compile jsp servlet classes at +${webapp.path}/WEB-INF/classes/org/apache/jsp. +

+ +

Hints: +

    +
  • When you switch to another Tomcat release, then regenerate and recompile +your jsp's with the new Tomcat version.
  • +
  • Use java system property at server runtime to disable PageContext pooling +org.apache.jasper.runtime.JspFactoryImpl.USE_POOL=false. +and limit the buffering with +org.apache.jasper.runtime.BodyContentImpl.LIMIT_BUFFER=true. Note +that changing from the defaults may affect performance, but it will vary +depending on the application.
  • +
+

+
+ + + +
diff --git a/webapps/docs/jndi-datasource-examples-howto.xml b/webapps/docs/jndi-datasource-examples-howto.xml new file mode 100644 index 000000000000..3152221cadc4 --- /dev/null +++ b/webapps/docs/jndi-datasource-examples-howto.xml @@ -0,0 +1,650 @@ + + + +]> + + + &project; + + + Les Hughes + David Haraburda + Glenn Nielsen + Yoav Shapira + JNDI Datasource HOW-TO + + + + +
+ +
+ +
+ +

JNDI Datasource configuration is covered extensively in the +JNDI-Resources-HOWTO. However, feedback from tomcat-user has +shown that specifics for individual configurations can be rather tricky.

+ +

Here then are some example configurations that have been posted to +tomcat-user for popular databases and some general tips for db usage.

+ +

You should be aware that since these notes are derived from configuration +and/or feedback posted to tomcat-user YMMV :-). Please let us +know if you have any other tested configurations that you feel may be of use +to the wider audience, or if you feel we can improve this section in anyway.

+ +

+Please note that JNDI resource configuration changed somewhat between +Tomcat 5.0.x and Tomcat 5.5.x. You will most likely need to modify older +JNDI resource configurations to match the syntax in the example below in order +to make them work in Tomcat 7.x.x. +

+ +

+Also, please note that JNDI DataSource configuration in general, and this +tutorial in particular, assumes that you have read and understood the +Context and +Host configuration references, including +the section about Automatic Application Deployment in the latter reference. +

+
+ +
+ +

DBCP provides support for JDBC 2.0. On systems using a 1.4 JVM DBCP +will support JDBC 3.0. Please let us know if you have used DBCP and its +JDBC 3.0 features with a 1.4 JVM. +

+ +

See the +DBCP documentation for a complete list of configuration parameters. +

+ + +

DBCP uses the Commons Database Connection Pool. It relies on +number of Commons components: +

    +
  • Commons DBCP
  • +
  • Commons Pool
  • +
+These libraries are located in a single JAR at +$CATALINA_HOME/lib/tomcat-dbcp.jar. However, +only the classes needed for connection pooling have been included, and the +packages have been renamed to avoid interfering with applications. +

+ +
+ + + +

+A database connection pool creates and manages a pool of connections +to a database. Recycling and reusing already existing connections +to a dB is more efficient than opening a new connection. +

+ +

+There is one problem with connection pooling. A web application has +to explicitly close ResultSet's, Statement's, and Connection's. +Failure of a web application to close these resources can result in +them never being available again for reuse, a db connection pool "leak". +This can eventually result in your web application db connections failing +if there are no more available connections.

+ +

+There is a solution to this problem. The Jakarta-Commons DBCP can be +configured to track and recover these abandoned dB connections. Not +only can it recover them, but also generate a stack trace for the code +which opened these resources and never closed them.

+ +

+To configure a DBCP DataSource so that abandoned dB connections are +removed and recycled add the following attribute to the +Resource configuration for your DBCP DataSource: + + removeAbandoned="true" + +When available db connections run low DBCP will recover and recycle +any abandoned dB connections it finds. The default is false. +

+ +

+Use the removeAbandonedTimeout attribute to set the number +of seconds a dB connection has been idle before it is considered abandoned. + + removeAbandonedTimeout="60" + +The default timeout for removing abandoned connections is 300 seconds. +

+ +

+The logAbandoned attribute can be set to true +if you want DBCP to log a stack trace of the code which abandoned the +dB connection resources. + + logAbandoned="true" + +The default is false. +

+ +
+ + + +

0. Introduction

+

Versions of MySQL and JDBC drivers that have been reported to work: +

    +
  • MySQL 3.23.47, MySQL 3.23.47 using InnoDB,, MySQL 3.23.58, MySQL 4.0.1alpha
  • +
  • Connector/J 3.0.11-stable (the official JDBC Driver)
  • +
  • mm.mysql 2.0.14 (an old 3rd party JDBC Driver)
  • +
+

+ +

Before you proceed, don't forget to copy the JDBC Driver's jar into $CATALINA_HOME/lib.

+ +

1. MySQL configuration

+

+Ensure that you follow these instructions as variations can cause problems. +

+ +

Create a new test user, a new database and a single test table. +Your MySQL user must have a password assigned. The driver +will fail if you try to connect with an empty password. + +mysql> GRANT ALL PRIVILEGES ON *.* TO javauser@localhost + -> IDENTIFIED BY 'javadude' WITH GRANT OPTION; +mysql> create database javatest; +mysql> use javatest; +mysql> create table testdata ( + -> id int not null auto_increment primary key, + -> foo varchar(25), + -> bar int); + +

+Note: the above user should be removed once testing is +complete! +
+

+ +

Next insert some test data into the testdata table. + +mysql> insert into testdata values(null, 'hello', 12345); +Query OK, 1 row affected (0.00 sec) + +mysql> select * from testdata; ++----+-------+-------+ +| ID | FOO | BAR | ++----+-------+-------+ +| 1 | hello | 12345 | ++----+-------+-------+ +1 row in set (0.00 sec) + +mysql> + +

+ +

2. Context configuration

+

Configure the JNDI DataSource in Tomcat by adding a declaration for your +resource to your Context.

+

For example: + + +<Context path="/DBTest" docBase="DBTest" + debug="5" reloadable="true" crossContext="true"> + + <!-- maxActive: Maximum number of dB connections in pool. Make sure you + configure your mysqld max_connections large enough to handle + all of your db connections. Set to -1 for no limit. + --> + + <!-- maxIdle: Maximum number of idle dB connections to retain in pool. + Set to -1 for no limit. See also the DBCP documentation on this + and the minEvictableIdleTimeMillis configuration parameter. + --> + + <!-- maxWait: Maximum time to wait for a dB connection to become available + in ms, in this example 10 seconds. An Exception is thrown if + this timeout is exceeded. Set to -1 to wait indefinitely. + --> + + <!-- username and password: MySQL dB username and password for dB connections --> + + <!-- driverClassName: Class name for the old mm.mysql JDBC driver is + org.gjt.mm.mysql.Driver - we recommend using Connector/J though. + Class name for the official MySQL Connector/J driver is com.mysql.jdbc.Driver. + --> + + <!-- url: The JDBC connection url for connecting to your MySQL dB. + --> + + <Resource name="jdbc/TestDB" auth="Container" type="javax.sql.DataSource" + maxActive="100" maxIdle="30" maxWait="10000" + username="javauser" password="javadude" driverClassName="com.mysql.jdbc.Driver" + url="jdbc:mysql://localhost:3306/javatest"/> + +</Context> + +

+ +

3. web.xml configuration

+ +

Now create a WEB-INF/web.xml for this test application. + +<web-app xmlns="http://java.sun.com/xml/ns/j2ee" + xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" + xsi:schemaLocation="http://java.sun.com/xml/ns/j2ee +http://java.sun.com/xml/ns/j2ee/web-app_2_4.xsd" + version="2.4"> + <description>MySQL Test App</description> + <resource-ref> + <description>DB Connection</description> + <res-ref-name>jdbc/TestDB</res-ref-name> + <res-type>javax.sql.DataSource</res-type> + <res-auth>Container</res-auth> + </resource-ref> +</web-app> + +

+ +

4. Test code

+

Now create a simple test.jsp page for use later. + +<%@ taglib uri="http://java.sun.com/jsp/jstl/sql" prefix="sql" %> +<%@ taglib uri="http://java.sun.com/jsp/jstl/core" prefix="c" %> + +<sql:query var="rs" dataSource="jdbc/TestDB"> +select id, foo, bar from testdata +</sql:query> + +<html> + <head> + <title>DB Test</title> + </head> + <body> + + <h2>Results</h2> + +<c:forEach var="row" items="${rs.rows}"> + Foo ${row.foo}<br/> + Bar ${row.bar}<br/> +</c:forEach> + + </body> +</html> + +

+ +

That JSP page makes use of JSTL's SQL and Core taglibs. You can get it from Sun's Java Web Services Developer Pack or Jakarta Taglib Standard 1.1 project - just make sure you get a 1.1.x release. Once you have JSTL, copy jstl.jar and standard.jar to your web app's WEB-INF/lib directory. + +

+ +

Finally deploy your web app into $CATALINA_BASE/webapps either +as a warfile called DBTest.war or into a sub-directory called +DBTest

+

Once deployed, point a browser at +http://localhost:8080/DBTest/test.jsp to view the fruits of +your hard work.

+ +
+ + +

0. Introduction

+ +

Oracle requires minimal changes from the MySQL configuration except for the +usual gotchas :-)

+

Drivers for older Oracle versions may be distributed as *.zip files rather +than *.jar files. Tomcat will only use *.jar files installed in +$CATALINA_HOME/lib. Therefore classes111.zip +or classes12.zip will need to be renamed with a .jar +extension. Since jarfiles are zipfiles, there is no need to unzip and jar these +files - a simple rename will suffice.

+ +

For Oracle 9i onwards you should use oracle.jdbc.OracleDriver +rather than oracle.jdbc.driver.OracleDriver as Oracle have stated +that oracle.jdbc.driver.OracleDriver is deprecated and support +for this driver class will be discontinued in the next major release. +

+ +

1. Context configuration

+

In a similar manner to the mysql config above, you will need to define your +Datasource in your Context. Here we define a +Datasource called myoracle using the thin driver to connect as user scott, +password tiger to the sid called mysid. (Note: with the thin driver this sid is +not the same as the tnsname). The schema used will be the default schema for the +user scott.

+ +

Use of the OCI driver should simply involve a changing thin to oci in the URL string. + +<Resource name="jdbc/myoracle" auth="Container" + type="javax.sql.DataSource" driverClassName="oracle.jdbc.OracleDriver" + url="jdbc:oracle:thin:@127.0.0.1:1521:mysid" + username="scott" password="tiger" maxActive="20" maxIdle="10" + maxWait="-1"/> + +

+ +

2. web.xml configuration

+

You should ensure that you respect the element ordering defined by the DTD when you +create you applications web.xml file.

+ +<resource-ref> + <description>Oracle Datasource example</description> + <res-ref-name>jdbc/myoracle</res-ref-name> + <res-type>javax.sql.DataSource</res-type> + <res-auth>Container</res-auth> +</resource-ref> + +

3. Code example

+

You can use the same example application as above (asuming you create the required DB +instance, tables etc.) replacing the Datasource code with something like

+ +Context initContext = new InitialContext(); +Context envContext = (Context)initContext.lookup("java:/comp/env"); +DataSource ds = (DataSource)envContext.lookup("jdbc/myoracle"); +Connection conn = ds.getConnection(); +//etc. + +
+ + + +

0. Introduction

+

PostgreSQL is configured in a similar manner to Oracle.

+ +

1. Required files

+

+Copy the Postgres JDBC jar to $CATALINA_HOME/lib. As with Oracle, the +jars need to be in this directory in order for DBCP's Classloader to find +them. This has to be done regardless of which configuration step you take next. +

+ +

2. Resource configuration

+ +

+You have two choices here: define a datasource that is shared across all Tomcat +applications, or define a datasource specifically for one application. +

+ +

2a. Shared resource configuration

+

+Use this option if you wish to define a datasource that is shared across +multiple Tomcat applications, or if you just prefer defining your datasource +in this file. +

+

This author has not had success here, although others have reported so. +Clarification would be appreciated here.

+ + +<Resource name="jdbc/postgres" auth="Container" + type="javax.sql.DataSource" driverClassName="org.postgresql.Driver" + url="jdbc:postgresql://127.0.0.1:5432/mydb" + username="myuser" password="mypasswd" maxActive="20" maxIdle="10" maxWait="-1"/> + +

2b. Application-specific resource configuration

+ +

+Use this option if you wish to define a datasource specific to your application, +not visible to other Tomcat applications. This method is less invasive to your +Tomcat installation. +

+ +

+Create a resource definition for your Context. +The Context element should look something like the following. +

+ + +<Context path="/someApp" docBase="someApp" + crossContext="true" reloadable="true" debug="1"> + +<Resource name="jdbc/postgres" auth="Container" + type="javax.sql.DataSource" driverClassName="org.postgresql.Driver" + url="jdbc:postgresql://127.0.0.1:5432/mydb" + username="myuser" password="mypasswd" maxActive="20" maxIdle="10" +maxWait="-1"/> +</Context> + + +

3. web.xml configuration

+ +<resource-ref> + <description>postgreSQL Datasource example</description> + <res-ref-name>jdbc/postgres</res-ref-name> + <res-type>javax.sql.DataSource</res-type> + <res-auth>Container</res-auth> +</resource-ref> + + +

4. Accessing the datasource

+

+When accessing the datasource programmatically, remember to prepend +java:/comp/env to your JNDI lookup, as in the following snippet of +code. Note also that "jdbc/postgres" can be replaced with any value you prefer, provided +you change it in the above resource definition file as well. +

+ + +InitialContext cxt = new InitialContext(); +if ( cxt == null ) { + throw new Exception("Uh oh -- no context!"); +} + +DataSource ds = (DataSource) cxt.lookup( "java:/comp/env/jdbc/postgres" ); + +if ( ds == null ) { + throw new Exception("Data source not found!"); +} + + +
+
+ +
+

+These solutions either utilise a single connection to the database (not recommended for anything other +than testing!) or some other pooling technology. +

+
+ +
+ +

Whilst not strictly addressing the creation of a JNDI DataSource using the OCI client, these notes can be combined with the +Oracle and DBCP solution above.

+

+In order to use OCI driver, you should have an Oracle client installed. You should have installed +Oracle8i(8.1.7) client from cd, and download the suitable JDBC/OCI +driver(Oracle8i 8.1.7.1 JDBC/OCI Driver) from otn.oracle.com. +

+

+After renaming classes12.zip file to classes12.jar +for Tomcat, copy it into $CATALINA_HOME/lib. +You may also have to remove the javax.sql.* classes +from this file depending upon the version of Tomcat and JDK you are using. +

+
+ + +

+Ensure that you have the ocijdbc8.dll or .so in your $PATH or LD_LIBRARY_PATH + (possibly in $ORAHOME\bin) and also confirm that the native library can be loaded by a simple test program +using System.loadLibrary("ocijdbc8"); +

+

+You should next create a simple test servlet or jsp that has these +critical lines: +

+ +DriverManager.registerDriver(new +oracle.jdbc.driver.OracleDriver()); +conn = +DriverManager.getConnection("jdbc:oracle:oci8:@database","username","password"); + +

+where database is of the form host:port:SID Now if you try to access the URL of your +test servlet/jsp and what you get is a +ServletException with a root cause of java.lang.UnsatisfiedLinkError:get_env_handle. +

+

+First, the UnsatisfiedLinkError indicates that you have +

    +
  • a mismatch between your JDBC classes file and +your Oracle client version. The giveaway here is the message stating that a needed library file cannot be +found. For example, you may be using a classes12.zip file from Oracle Version 8.1.6 with a Version 8.1.5 +Oracle client. The classeXXXs.zip file and Oracle client software versions must match. +
  • +
  • A $PATH, LD_LIBRARY_PATH problem.
  • +
  • It has been reported that ignoring the driver you have downloded from otn and using +the classes12.zip file from the directory $ORAHOME\jdbc\lib will also work. +
  • +
+

+

+Next you may experience the error ORA-06401 NETCMN: invalid driver designator +

+

+The Oracle documentation says : "Cause: The login (connect) string contains an invalid +driver designator. Action: Correct the string and re-submit." + +Change the database connect string (of the form host:port:SID) with this one: +(description=(address=(host=myhost)(protocol=tcp)(port=1521))(connect_data=(sid=orcl))) +

+

+Ed. Hmm, I don't think this is really needed if you sort out your TNSNames - but I'm not an Oracle DBA :-) +

+
+
+ +
+

Here are some common problems encountered with a web application which +uses a database and tips for how to solve them.

+ + +

+Tomcat runs within a JVM. The JVM periodically performs garbage collection +(GC) to remove java objects which are no longer being used. When the JVM +performs GC execution of code within Tomcat freezes. If the maximum time +configured for establishment of a dB connection is less than the amount +of time garbage collection took you can get a db conneciton failure. +

+ +

To collect data on how long garbage collection is taking add the +-verbose:gc argument to your CATALINA_OPTS +environment variable when starting Tomcat. When verbose gc is enabled +your $CATALINA_BASE/logs/catalina.out log file will include +data for every garbage collection including how long it took.

+ +

When your JVM is tuned correctly 99% of the time a GC will take less +than one second. The remainder will only take a few seconds. Rarely, +if ever should a GC take more than 10 seconds.

+ +

Make sure that the db connection timeout is set to 10-15 seconds. +For the DBCP you set this using the parameter maxWait.

+ +
+ + +

+These can occur when one request gets a db connection from the connection +pool and closes it twice. When using a connection pool, closing the +connection just returns it to the pool for reuse by another request, +it doesn't close the connection. And Tomcat uses multiple threads to +handle concurrent requests. Here is an example of the sequence +of events which could cause this error in Tomcat: +

+  Request 1 running in Thread 1 gets a db connection.
+
+  Request 1 closes the db connection.
+
+  The JVM switches the running thread to Thread 2
+
+  Request 2 running in Thread 2 gets a db connection
+  (the same db connection just closed by Request 1).
+
+  The JVM switches the running thread back to Thread 1
+
+  Request 1 closes the db connection a second time in a finally block.
+
+  The JVM switches the running thread back to Thread 2
+
+  Request 2 Thread 2 tries to use the db connection but fails
+  because Request 1 closed it.
+
+Here is an example of properly written code to use a db connection +obtained from a connection pool: +
+  Connection conn = null;
+  Statement stmt = null;  // Or PreparedStatement if needed
+  ResultSet rs = null;
+  try {
+    conn = ... get connection from connection pool ...
+    stmt = conn.createStatement("select ...");
+    rs = stmt.executeQuery();
+    ... iterate through the result set ...
+    rs.close();
+    rs = null;
+    stmt.close();
+    stmt = null;
+    conn.close(); // Return to connection pool
+    conn = null;  // Make sure we don't close it twice
+  } catch (SQLException e) {
+    ... deal with errors ...
+  } finally {
+    // Always make sure result sets and statements are closed,
+    // and the connection is returned to the pool
+    if (rs != null) {
+      try { rs.close(); } catch (SQLException e) { ; }
+      rs = null;
+    }
+    if (stmt != null) {
+      try { stmt.close(); } catch (SQLException e) { ; }
+      stmt = null;
+    }
+    if (conn != null) {
+      try { conn.close(); } catch (SQLException e) { ; }
+      conn = null;
+    }
+  }
+
+

+ +
+ + +

+ Please note that although the above instructions place the JNDI declarations in a Context + element, it is possible and sometimes desirable to place these declarations in the + GlobalNamingResources section of the server + configuration file. A resource placed in the GlobalNamingResources section will be shared + among the Contexts of the server. +

+
+ + +

+ In order to get Realms to work, the realm must refer to the datasource as + defined in the <GlobalNamingResources> or <Context> section, not a datasource as renamed + using <ResourceLink>. +

+
+ +
+ + +
diff --git a/webapps/docs/jndi-resources-howto.xml b/webapps/docs/jndi-resources-howto.xml new file mode 100644 index 000000000000..29f6223953dc --- /dev/null +++ b/webapps/docs/jndi-resources-howto.xml @@ -0,0 +1,879 @@ + + + +]> + + + &project; + + + Craig R. McClanahan + Yoav Shapira + JNDI Resources HOW-TO + + + + +
+ +
+ +
+ +

Tomcat provides a JNDI InitialContext implementation +instance for each web application running under it, in a manner that is +compatible with those provided by a +Java Enterprise Edition application +server. The Java EE standard provides a standard set of elements in the +/WEB-INF/web.xml file to reference/define resources.

+ +

See the following Specifications for more information about programming APIs +for JNDI, and for the features supported by Java Enterprise Edition (Java EE) +servers, which Tomcat emulates for the services that it provides:

+ + +
+ +
+ +

The following elements may be used in the web application deployment +descriptor (/WEB-INF/web.xml) of your web application to define +resources:

+
    +
  • <env-entry> - Environment entry, a + single-value parameter that can be used to configure how the application + will operate.
  • +
  • <resource-ref> - Resource reference, + which is typically to an object factory for resources such as a JDBC + DataSource, a JavaMail Session, or custom + object factories configured into Tomcat.
  • +
  • <resource-env-ref> - Resource + environment reference, a new variation of resource-ref + added in Servlet 2.4 that is simpler to configure for resources + that do not require authentication information.
  • +
+ +

Providing that Tomcat is able to identify an appropriate resource factory to +use to create the resource and that no further configuration information is +required, Tomcat will use the information in /WEB-INF/web.xml to +create the resource.

+
+ +
+ +

If Tomcat is unable to identify the appropriate resource factory and/or +additional configuration information is required, additional Tomcat specific +configuration must be specified before Tomcat can create the resource. +Tomcat specific resource configuration is entered in +the <Context> elements that +can be specified in either $CATALINA_BASE/conf/server.xml or, +preferably, the per-web-application context XML file +(META-INF/context.xml).

+ +

Tomcat specific resource configuration is performed using the following +elements in the <Context> +element:

+ +
    +
  • <Environment> - + Configure names and values for scalar environment entries that will be + exposed to the web application through the JNDI + InitialContext (equivalent to the inclusion of an + <env-entry> element in the web application + deployment descriptor).
  • +
  • <Resource> - + Configure the name and data type of a resource made available to the + application (equivalent to the inclusion of a + <resource-ref> element in the web application + deployment descriptor).
  • +
  • <ResourceLink> - + Add a link to a resource defined in the global JNDI context. Use resource + links to give a web application access to a resource defined in + the<GlobalNamingResources> + child element of the <Server> + element.
  • +
  • <Transaction> - + Add a resource factory for instantiating the UserTransaction object + instance that is available at java:comp/UserTransaction.
  • + +
+ +

Any number of these elements may be nested inside a +<Context> element and will +be associated only with that particular web application.

+ +

If a resource has been defined in a +<Context> element it is not +necessary for that resource to be defined in /WEB-INF/web.xml. +However, it is recommended to keep the entry in /WEB-INF/web.xml +to document the resource requirements for the web application.

+ +

Where the same resource name has been defined for a +<env-entry> element included in the web application +deployment descriptor (/WEB-INF/web.xml) and in an +<Environment> element as part of the +<Context> element for the +web application, the values in the deployment descriptor will take precedence +only if allowed by the corresponding +<Environment> element (by setting the override +attribute to "true").

+ +
+ +
+ +

Tomcat maintains a separate namespace of global resources for the +entire server. These are configured in the + +<GlobalNameingResources> element of +$CATALINA_BASE/conf/server.xml. You may expose these resources to +web applications by using a +<ResourceLink> to +include it in the per-web-application context.

+ +

If a resource has been defined using a +<ResourceLink>, it is not +necessary for that resource to be defined in /WEB-INF/web.xml. +However, it is recommended to keep the entry in /WEB-INF/web.xml +to document the resource requirements for the web application.

+ +
+ +
+ +

The InitialContext is configured as a web application is +initially deployed, and is made available to web application components (for +read-only access). All configured entries and resources are placed in +the java:comp/env portion of the JNDI namespace, so a typical +access to a resource - in this case, to a JDBC DataSource - +would look something like this:

+ + +// Obtain our environment naming context +Context initCtx = new InitialContext(); +Context envCtx = (Context) initCtx.lookup("java:comp/env"); + +// Look up our data source +DataSource ds = (DataSource) + envCtx.lookup("jdbc/EmployeeDB"); + +// Allocate and use a connection from the pool +Connection conn = ds.getConnection(); +... use this connection to access the database ... +conn.close(); + + +
+ +
+ +

Tomcat includes a series of standard resource factories that can + provide services to your web applications, but give you configuration + flexibility (via the + <Context> element) + without modifying the web application or the deployment descriptor. Each + subsection below details the configuration and usage of the standard resource + factories.

+ +

See Adding Custom + Resource Factories for information about how to create, install, + configure, and use your own custom resource factory classes with + Tomcat.

+ +

NOTE - Of the standard resource factories, only the + "JDBC Data Source" and "User Transaction" factories are mandated to + be available on other platforms, and then they are required only if + the platform implements the Java Enterprise Edition (Java EE) specs. + All other standard resource factories, plus custom resource factories + that you write yourself, are specific to Tomcat and cannot be assumed + to be available on other containers.

+ + + +

0. Introduction

+ +

This resource factory can be used to create objects of any + Java class that conforms to standard JavaBeans naming conventions (i.e. + it has a zero-arguments constructor, and has property setters that + conform to the setFoo() naming pattern. The resource factory will + create a new instance of the appropriate bean class every time a + lookup() for this entry is made.

+ +

The steps required to use this facility are described below.

+ +

1. Create Your JavaBean Class

+ +

Create the JavaBean class which will be instantiated each time + that the resource factory is looked up. For this example, assume + you create a class com.mycompany.MyBean, which looks + like this:

+ + +package com.mycompany; + +public class MyBean { + + private String foo = "Default Foo"; + + public String getFoo() { + return (this.foo); + } + + public void setFoo(String foo) { + this.foo = foo; + } + + private int bar = 0; + + public int getBar() { + return (this.bar); + } + + public void setBar(int bar) { + this.bar = bar; + } + + +} + + +

2. Declare Your Resource Requirements

+ +

Next, modify your web application deployment descriptor + (/WEB-INF/web.xml) to declare the JNDI name under which + you will request new instances of this bean. The simplest approach is + to use a <resource-env-ref> element, like this:

+ + +<resource-env-ref> + <description> + Object factory for MyBean instances. + </description> + <resource-env-ref-name> + bean/MyBeanFactory + </resource-env-ref-name> + <resource-env-ref-type> + com.mycompany.MyBean + </resource-env-ref-type> +</resource-env-ref> + + +

WARNING - Be sure you respect the element ordering + that is required by the DTD for web application deployment descriptors! + See the + Servlet + Specification for details.

+ +

3. Code Your Application's Use Of This Resource

+ +

A typical use of this resource environment reference might look + like this:

+ + +Context initCtx = new InitialContext(); +Context envCtx = (Context) initCtx.lookup("java:comp/env"); +MyBean bean = (MyBean) envCtx.lookup("bean/MyBeanFactory"); + +writer.println("foo = " + bean.getFoo() + ", bar = " + + bean.getBar()); + + +

4. Configure Tomcat's Resource Factory

+ +

To configure Tomcat's resource factory, add an element like this to the + <Context> element for + this web application.

+ + +<Context ...> + ... + <Resource name="bean/MyBeanFactory" auth="Container" + type="com.mycompany.MyBean" + factory="org.apache.naming.factory.BeanFactory" + bar="23"/> + ... +</Context> + + +

Note that the resource name (here, bean/MyBeanFactory + must match the value specified in the web application deployment + descriptor. We are also initializing the value of the bar + property, which will cause setBar(23) to be called before + the new bean is returned. Because we are not initializing the + foo property (although we could have), the bean will + contain whatever default value is set up by its constructor.

+ +
+ + + + +

0. Introduction

+ +

UserDatabase resources are typically configured as global resources for + use by a UserDatabase realm. Tomcat includes a UserDatabaseFactoory that + creates UserDatabase resources backed by an XML file - usually + tomcat-users.xml

+ +

The steps required to set up a global UserDatabase resource are described + below.

+ +

1. Create/edit the XML file

+ +

The XMl file is typically located at + $CATALINA_BASE/conf/tomcat-users.xml however, you are free to + locate the file anywhere on the file system. It is recommended that the XML + files are placed in $CATALINA_BASE/conf. A typical XML would + look like:

+ + +<?xml version='1.0' encoding='utf-8'?> +<tomcat-users> + <role rolename="tomcat"/> + <role rolename="role1"/> + <user username="tomcat" password="tomcat" roles="tomcat"/> + <user username="both" password="tomcat" roles="tomcat,role1"/> + <user username="role1" password="tomcat" roles="role1"/> +</tomcat-users> + + +

2. Declare Your Resource

+ +

Next, modify $CATALINA_BASE/conf/server.xml to create the + UserDatabase resource based on your XMl file. It should look something like + this:

+ + +<Resource name="UserDatabase" + auth="Container" + type="org.apache.catalina.UserDatabase" + description="User database that can be updated and saved" + factory="org.apache.catalina.users.MemoryUserDatabaseFactory" + pathname="conf/tomcat-users.xml" + readonly="false" /> + + +

The pathname attribute can be absolute or relative. If + relative, it is relative to $CATALINA_BASE.

+ +

The readonly attribute is optional and defaults to + true if not supplied. If the XML is writeable then it will be + written to when Tomcat starts. WARNING: When the file is + written it will inherit the default file permissions for the user Tomcat + is running as. Ensure that these are appropriate to maintain the security + of your installation.

+ +

3. Configure the Realm

+ +

Configure a UserDatabase Realm to use this resource as described in the + Realm configuration documentation.

+ +
+ + + + +

0. Introduction

+ +

In many web applications, sending electronic mail messages is a + required part of the system's functionality. The + Java Mail API + makes this process relatively straightforward, but requires many + configuration details that the client application must be aware of + (including the name of the SMTP host to be used for message sending).

+ +

Tomcat includes a standard resource factory that will create + javax.mail.Session session instances for you, already + configured to connect to an SMTP server. + In this way, the application is totally insulated from changes in the + email server configuration environment - it simply asks for, and receives, + a preconfigured session whenever needed.

+ +

The steps required for this are outlined below.

+ +

1. Declare Your Resource Requirements

+ +

The first thing you should do is modify the web application deployment + descriptor (/WEB-INF/web.xml) to declare the JNDI name under + which you will look up preconfigured sessions. By convention, all such + names should resolve to the mail subcontext (relative to the + standard java:comp/env naming context that is the root of + all provided resource factories. A typical web.xml entry + might look like this:

+ +<resource-ref> + <description> + Resource reference to a factory for javax.mail.Session + instances that may be used for sending electronic mail + messages, preconfigured to connect to the appropriate + SMTP server. + </description> + <res-ref-name> + mail/Session + </res-ref-name> + <res-type> + javax.mail.Session + </res-type> + <res-auth> + Container + </res-auth> +</resource-ref> + + +

WARNING - Be sure you respect the element ordering + that is required by the DTD for web application deployment descriptors! + See the + Servlet + Specification for details.

+ +

2. Code Your Application's Use Of This Resource

+ +

A typical use of this resource reference might look like this:

+ +Context initCtx = new InitialContext(); +Context envCtx = (Context) initCtx.lookup("java:comp/env"); +Session session = (Session) envCtx.lookup("mail/Session"); + +Message message = new MimeMessage(session); +message.setFrom(new InternetAddress(request.getParameter("from")); +InternetAddress to[] = new InternetAddress[1]; +to[0] = new InternetAddress(request.getParameter("to")); +message.setRecipients(Message.RecipientType.TO, to); +message.setSubject(request.getParameter("subject")); +message.setContent(request.getParameter("content"), "text/plain"); +Transport.send(message); + + +

Note that the application uses the same resource reference name + that was declared in the web application deployment descriptor. This + is matched up against the resource factory that is configured in the + <Context> element + for the web application as described below.

+ +

3. Configure Tomcat's Resource Factory

+ +

To configure Tomcat's resource factory, add an elements like this to the + <Context> element for + this web application.

+ + +<Context ...> + ... + <Resource name="mail/Session" auth="Container" + type="javax.mail.Session" + mail.smtp.host="localhost"/> + ... +</Context> + + +

Note that the resource name (here, mail/Session) must + match the value specified in the web application deployment descriptor. + Customize the value of the mail.smtp.host parameter to + point at the server that provides SMTP service for your network.

+ +

4. Install the JavaMail libraries

+ +

+ Download the JavaMail API. The JavaMail API requires the Java Activation + Framework (JAF) API as well. The Java Activation Framework can be downloaded + from Sun's site. +

+ +

This download includes 2 vital libraries for the configuration; + activation.jar and mail.jar. Unpackage both distributions and place + them into $CATALINA_HOME/lib so that they are available to + Tomcat during the initialization of the mail Session Resource. + Note: placing these jars in both $CATALINA_HOME/lib and a + web application's lib folder will cause an error, so ensure you have + them in the $CATALINA_HOME/lib location only. +

+ +

Example Application

+ +

The /examples application included with Tomcat contains + an example of utilizing this resource factory. It is accessed via the + "JSP Examples" link. The source code for the servlet that actually + sends the mail message is in + /WEB-INF/classes/SendMailServlet.java.

+ +

WARNING - The default configuration assumes that there + is an SMTP server listing on port 25 on localhost. If this is + not the case, edit the + <Context> element for + this web application and modify the parameter value for the + mail.smtp.host parameter to be the host name of an SMTP server + on your network.

+ +
+ + + +

0. Introduction

+ +

Many web applications need to access a database via a JDBC driver, + to support the functionality required by that application. The Java EE + Platform Specification requires Java EE Application Servers to make + available a DataSource implementation (that is, a connection + pool for JDBC connections) for this purpose. Tomcat offers exactly + the same support, so that database-based applications you develop on + Tomcat using this service will run unchanged on any Java EE server.

+ +

For information about JDBC, you should consult the following:

+ + +

NOTE - The default data source support in Tomcat + is based on the DBCP connection pool from the + Commons + project. However, it is possible to use any other connection pool + that implements javax.sql.DataSource, by writing your + own custom resource factory, as described + below.

+ +

1. Install Your JDBC Driver

+ +

Use of the JDBC Data Sources JNDI Resource Factory requires + that you make an appropriate JDBC driver available to both Tomcat internal + classes and to your web application. This is most easily accomplished by + installing the driver's JAR file(s) into the + $CATALINA_HOME/lib directory, which makes the driver + available both to the resource factory and to your application.

+ +

2. Declare Your Resource Requirements

+ +

Next, modify the web application deployment descriptor + (/WEB-INF/web.xml) to declare the JNDI name under + which you will look up preconfigured data source. By convention, all such + names should resolve to the jdbc subcontext (relative to the + standard java:comp/env naming context that is the root of + all provided resource factories. A typical web.xml entry + might look like this:

+ +<resource-ref> + <description> + Resource reference to a factory for java.sql.Connection + instances that may be used for talking to a particular + database that is configured in the <Context> + configurartion for the web application. + </description> + <res-ref-name> + jdbc/EmployeeDB + </res-ref-name> + <res-type> + javax.sql.DataSource + </res-type> + <res-auth> + Container + </res-auth> +</resource-ref> + + +

WARNING - Be sure you respect the element ordering + that is required by the DTD for web application deployment descriptors! + See the + Servlet + Specification for details.

+ +

3. Code Your Application's Use Of This Resource

+ +

A typical use of this resource reference might look like this:

+ +Context initCtx = new InitialContext(); +Context envCtx = (Context) initCtx.lookup("java:comp/env"); +DataSource ds = (DataSource) + envCtx.lookup("jdbc/EmployeeDB"); + +Connection conn = ds.getConnection(); +... use this connection to access the database ... +conn.close(); + + +

Note that the application uses the same resource reference name that was + declared in the web application deployment descriptor. This is matched up + against the resource factory that is configured in the + <Context> element for + the web application as described below.

+ +

4. Configure Tomcat's Resource Factory

+ +

To configure Tomcat's resource factory, add an element like this to the + <Context> element for + the web application.

+ + +<Context ...> + ... + <Resource name="jdbc/EmployeeDB" + auth="Container" + type="javax.sql.DataSource" + username="dbusername" + password="dbpassword" + driverClassName="org.hsql.jdbcDriver" + url="jdbc:HypersonicSQL:database" + maxActive="8" + maxIdle="4"/> + ... +</Context> + + +

Note that the resource name (here, jdbc/EmployeeDB) must + match the value specified in the web application deployment descriptor.

+ +

This example assumes that you are using the HypersonicSQL database + JDBC driver. Customize the driverClassName and + driverName parameters to match your actual database's + JDBC driver and connection URL.

+ +

The configuration properties for Tomcat's standard data source + resource factory + (org.apache.tomcat.dbcp.dbcp.BasicDataSourceFactory) are + as follows:

+
    +
  • driverClassName - Fully qualified Java class name + of the JDBC driver to be used.
  • +
  • maxActive - The maximum number of active instances + that can be allocated from this pool at the same time.
  • +
  • maxIdle - The maximum number of connections that + can sit idle in this pool at the same time.
  • +
  • maxWait - The maximum number of milliseconds that the + pool will wait (when there are no available connections) for a + connection to be returned before throwing an exception.
  • +
  • password - Database password to be passed to our + JDBC driver.
  • +
  • url - Connection URL to be passed to our JDBC driver. + (For backwards compatibility, the property driverName + is also recognized.)
  • +
  • username - Database username to be passed to our + JDBC driver.
  • +
  • validationQuery - SQL query that can be used by the + pool to validate connections before they are returned to the + application. If specified, this query MUST be an SQL SELECT + statement that returns at least one row.
  • +
+

For more details, please refer to the commons-dbcp documentation.

+ +
+ +
+ + +
+ +

If none of the standard resource factories meet your needs, you can write + your own factory and integrate it into Tomcat, and then configure the use + of this factory in the + <Context> element for + the web application. In the example below, we will create a factory that only + knows how to create com.mycompany.MyBean beans from the + Generic JavaBean Resources example + above.

+ +

1. Write A Resource Factory Class

+ +

You must write a class that implements the JNDI service provider + javax.naming.spi.ObjectFactory inteface. Every time your + web application calls lookup() on a context entry that is + bound to this factory, the getObjectInstance() method is + called, with the following arguments:

+
    +
  • Object obj - The (possibly null) object containing + location or reference information that can be used in creating an object. + For Tomcat, this will always be an object of type + javax.naming.Reference, which contains the class name of + this factory class, as well as the configuration properties (from the + <Context> for the + web application) to use in creating objects to be returned.
  • +
  • Name name - The name to which this factory is bound + relative to nameCtx, or null if no name + is specified.
  • +
  • Context nameCtx - The context relative to which the + name parameter is specified, or null if + name is relative to the default initial context.
  • +
  • Hashtable environment - The (possibly null) + environment that is used in creating this object. This is generally + ignored in Tomcat object factories.
  • +
+ +

To create a resource factory that knows how to produce MyBean + instances, you might create a class like this:

+ + +package com.mycompany; + +import java.util.Enumeration; +import java.util.Hashtable; +import javax.naming.Context; +import javax.naming.Name; +import javax.naming.NamingException; +import javax.naming.RefAddr; +import javax.naming.Reference; +import javax.naming.spi.ObjectFactory; + +public class MyBeanFactory implements ObjectFactory { + + public Object getObjectInstance(Object obj, + Name name, Context nameCtx, Hashtable environment) + throws NamingException { + + // Acquire an instance of our specified bean class + MyBean bean = new MyBean(); + + // Customize the bean properties from our attributes + Reference ref = (Reference) obj; + Enumeration addrs = ref.getAll(); + while (addrs.hasMoreElements()) { + RefAddr addr = (RefAddr) addrs.nextElement(); + String name = addr.getType(); + String value = (String) addr.getContent(); + if (name.equals("foo")) { + bean.setFoo(value); + } else if (name.equals("bar")) { + try { + bean.setBar(Integer.parseInt(value)); + } catch (NumberFormatException e) { + throw new NamingException("Invalid 'bar' value " + value); + } + } + } + + // Return the customized instance + return (bean); + + } + +} + + +

In this example, we are unconditionally creating a new instance of + the com.mycompany.MyBean class, and populating its properties + based on the parameters included in the <ResourceParams> + element that configures this factory (see below). You should note that any + parameter named factory should be skipped - that parameter is + used to specify the name of the factory class itself (in this case, + com.mycompany.MyBeanFactory) rather than a property of the + bean being configured.

+ +

For more information about ObjectFactory, see the + JNDI 1.2 Service + Provider Interface (SPI) Specification.

+ +

You will need to compile this class against a class path that includes + all of the JAR files in the $CATALINA_HOME/lib directory. When you are through, + place the factory class (and the corresponding bean class) unpacked under + $CATALINA_HOME/lib, or in a JAR file inside + $CATALINA_HOME/lib. In this way, the required class + files are visible to both Catalina internal resources and your web + application.

+ +

2. Declare Your Resource Requirements

+ +

Next, modify your web application deployment descriptor + (/WEB-INF/web.xml) to declare the JNDI name under which + you will request new instances of this bean. The simplest approach is + to use a <resource-env-ref> element, like this:

+ + +<resource-env-ref> + <description> + Object factory for MyBean instances. + </description> + <resource-env-ref-name> + bean/MyBeanFactory + </resource-env-ref-name> + <resource-env-ref-type> + com.mycompany.MyBean + </resource-env-ref-type> +<resource-env-ref> + + +

WARNING - Be sure you respect the element ordering + that is required by the DTD for web application deployment descriptors! + See the + Servlet + Specification for details.

+ +

3. Code Your Application's Use Of This Resource

+ +

A typical use of this resource environment reference might look + like this:

+ + +Context initCtx = new InitialContext(); +Context envCtx = (Context) initCtx.lookup("java:comp/env"); +MyBean bean = (MyBean) envCtx.lookup("bean/MyBeanFactory"); + +writer.println("foo = " + bean.getFoo() + ", bar = " + + bean.getBar()); + + +

4. Configure Tomcat's Resource Factory

+ +

To configure Tomcat's resource factory, add an elements like this to the + <Context> element for + this web application.

+ + +<Context ...> + ... + <Resource name="bean/MyBeanFactory" auth="Container" + type="com.mycompany.MyBean" + factory="com.mycompany.MyBeanFactory" + bar="23"/> + ... +</Context> + + +

Note that the resource name (here, bean/MyBeanFactory + must match the value specified in the web application deployment + descriptor. We are also initializing the value of the bar + property, which will cause setBar(23) to be called before + the new bean is returned. Because we are not initializing the + foo property (although we could have), the bean will + contain whatever default value is set up by its constructor.

+ +

You will also note that, from the application developer's perspective, + the declaration of the resource environment reference, and the programming + used to request new instances, is identical to the approach used for the + Generic JavaBean Resources example. This illustrates one of the + advantages of using JNDI resources to encapsulate functionality - you can + change the underlying implementation without necessarily having to + modify applications using the resources, as long as you maintain + compatible APIs.

+ +
+ + + +
diff --git a/webapps/docs/jspapi/index.html b/webapps/docs/jspapi/index.html new file mode 100644 index 000000000000..6e8e8414aadb --- /dev/null +++ b/webapps/docs/jspapi/index.html @@ -0,0 +1,34 @@ + + + + + + API docs + + + + +The JSP Javadoc is not installed by default. Download and install +the "fulldocs" package to get it. + +You can also access the javadoc online in the Tomcat + +documentation bundle. + + + diff --git a/webapps/docs/logging.xml b/webapps/docs/logging.xml new file mode 100644 index 000000000000..cf6d3772520b --- /dev/null +++ b/webapps/docs/logging.xml @@ -0,0 +1,324 @@ + + + +]> + + + &project; + + + Logging in Tomcat + Allistair Crossley + Yoav Shapira + + + + +
+ +
+ +
+

+ Tomcat uses + Apache Commons Logging + throughout its internal code. + Commons Logging provides Tomcat with the ability to log + hierarchically across various log levels without needing to rely on a + particular logging implementation. +

+ +

+ By default, only java.util.logging is available for the logs generated by + the Tomcat internal loggers, as Tomcat uses a package renamed commons + logging implementation which is hardcoded to use java.util.logging. Use of + alternative logging frameworks requires building or downloading an + extras component which include a full + commons-logging implementation. Instructions for configuring the extras + components to enable log4j to be used for Tomcat's internal logging may be + found below. +

+ +

+ Tomcat no longer uses localhost_log as the runtime + exception/stack trace log. These types of error are usually thrown by + uncaught exceptions, but are still valuable to the developer. They can now + be found in the stdout log file (catalina.out). +

+ +
+ +
+ +

+ The default implementation of java.util.logging provided in the JDK is too + limited to be useful. A limitation of JDK Logging appears to be the + inability to have per-web application logging, as the configuration is + per-VM. As a result, Tomcat will, in the default configuration, replace the + default LogManager implementation with a container friendly implementation + called JULI, which addresses these shortcomings. It supports the same + configuration mechanisms as the standard JDK java.util.logging, using either + a programmatic approach, or properties files. The main difference is that + per-classloader properties files can be set (which enables easy redeployment + friendly webapp configuration), and the properties files support slightly + extended constructs which allows more freedom for defining handlers and + assigning them to loggers. +

+

+ JULI is enabled by default, and supports per classloader configuration, in + addition to the regular global java.util.logging configuration. This means + that logging can be configured at the following layers: +

    +
  • In the JDK's logging.properties file. Check your JAVA_HOME environment + setting to see which JDK Tomcat is using. The file will be in + $JAVA_HOME/jre/lib. + Alternately, it can also use a global configuration file located elsewhere + by using the system property java.util.logging.config.file, + or programmatic configuration using + java.util.logging.config.class.
  • +
  • In each classloader using a logging.properties file. This means that + it is possible to have a configuration for the Tomcat core, as well as + separate configurations for each webapps which will have the same + lifecycle as the webapps.
  • +
+

+

+ The default logging.properties specifies a ConsoleHandler for routing + logging to stdout and also a FileHandler. A handler's log level threshold + can be set using SEVERE, WARNING, INFO, CONFIG, FINE, FINER, FINEST or ALL. + The logging.properties shipped with JDK is set to INFO. You can also target + specific packages to collect logging from and specify a level. Here is how + you would set debugging from Tomcat. You would need to ensure the + ConsoleHandler's level is also set to collect this threshold, so FINEST or + ALL should be set. Please refer to Sun's java.util.logging documentation for + the complete details. +

+

+ org.apache.catalina.level=FINEST +

+

+ The configuration used by JULI is extremely similar, but uses a few + extensions to allow better flexibility in assigning loggers. The main + differences are: +

    +
  • A prefix may be added to handler names, so that multiple handlers of a + single class may be instantiated. A prefix is a String which starts with a + digit, and ends with '.'. For example, 22foobar. is a valid + prefix.
  • +
  • As in Java 6.0, loggers can define a list of handlers using the + loggerName.handlers property.
  • +
  • By default, loggers will not delegate to their parent if they have + associated handlers. This may be changed per logger using the + loggerName.useParentHandlers property, which accepts a + boolean value.
  • +
  • The root logger can define its set of handlers using a + .handlers property.
  • +
  • Logging is not buffered by default. To configure buffering, use the + bufferSize property of a handler. A value of 0 + uses system default buffering (typically an 8K buffer will be used). A + value of <0 forces a writer flush upon each log write. A + value >0 uses a BufferedOutputStream with the defined + value but note that the system default buffering will also be + applied.
  • +
  • System property replacement is performed for property values which + contain ${systemPropertyName}.
  • +
+

+

+ Example logging.properties file to be placed in $CATALINA_BASE/conf: + +handlers = 1catalina.org.apache.juli.FileHandler, \ + 2localhost.org.apache.juli.FileHandler, \ + 3manager.org.apache.juli.FileHandler, \ + 4admin.org.apache.juli.FileHandler, \ + java.util.logging.ConsoleHandler + +.handlers = 1catalina.org.apache.juli.FileHandler, java.util.logging.ConsoleHandler + +############################################################ +# Handler specific properties. +# Describes specific configuration info for Handlers. +############################################################ + +1catalina.org.apache.juli.FileHandler.level = FINE +1catalina.org.apache.juli.FileHandler.directory = ${catalina.base}/logs +1catalina.org.apache.juli.FileHandler.prefix = catalina. + +2localhost.org.apache.juli.FileHandler.level = FINE +2localhost.org.apache.juli.FileHandler.directory = ${catalina.base}/logs +2localhost.org.apache.juli.FileHandler.prefix = localhost. + +3manager.org.apache.juli.FileHandler.level = FINE +3manager.org.apache.juli.FileHandler.directory = ${catalina.base}/logs +3manager.org.apache.juli.FileHandler.prefix = manager. + +4admin.org.apache.juli.FileHandler.level = FINE +4admin.org.apache.juli.FileHandler.directory = ${catalina.base}/logs +4admin.org.apache.juli.FileHandler.prefix = admin. +4admin.org.apache.juli.FileHandler.bufferSize = 16384 + +java.util.logging.ConsoleHandler.level = FINE +java.util.logging.ConsoleHandler.formatter = java.util.logging.SimpleFormatter + + +############################################################ +# Facility specific properties. +# Provides extra control for each logger. +############################################################ + +org.apache.catalina.core.ContainerBase.[Catalina].[localhost].level = INFO +org.apache.catalina.core.ContainerBase.[Catalina].[localhost].handlers = \ + 2localhost.org.apache.juli.FileHandler + +org.apache.catalina.core.ContainerBase.[Catalina].[localhost].[/manager].level = INFO +org.apache.catalina.core.ContainerBase.[Catalina].[localhost].[/manager].handlers = \ + 3manager.org.apache.juli.FileHandler + +org.apache.catalina.core.ContainerBase.[Catalina].[localhost].[/admin].level = INFO +org.apache.catalina.core.ContainerBase.[Catalina].[localhost].[/admin].handlers = \ + 4admin.org.apache.juli.FileHandler + +# For example, set the org.apache.catalina.util.LifecycleBase logger to log +# each component that extends LifecycleBase changing state: +#org.apache.catalina.util.LifecycleBase.level = FINE + +

+ +

+ Example logging.properties for the servlet-examples web application to be + placed in WEB-INF/classes inside the web application: + +handlers = org.apache.juli.FileHandler, java.util.logging.ConsoleHandler + +############################################################ +# Handler specific properties. +# Describes specific configuration info for Handlers. +############################################################ + +org.apache.juli.FileHandler.level = FINE +org.apache.juli.FileHandler.directory = ${catalina.base}/logs +org.apache.juli.FileHandler.prefix = servlet-examples. + +java.util.logging.ConsoleHandler.level = FINE +java.util.logging.ConsoleHandler.formatter = java.util.logging.SimpleFormatter + +

+ +
+ +
+

+ This section explains how to configure Tomcat to use log4j rather than + java.util.logging for all Tomcat's internal logging. The following steps + describe configuring log4j to output Tomcat's internal logging to a file + named tomcat.log. +

+ +

+

    +
  1. Create a file called log4j.properties with the following content + and save it into $CATALINA_HOME/lib. + +log4j.rootLogger=INFO, R
    +log4j.appender.R=org.apache.log4j.RollingFileAppender
    +log4j.appender.R.File=${catalina.base}/logs/tomcat.log
    +log4j.appender.R.MaxFileSize=10MB
    +log4j.appender.R.MaxBackupIndex=10
    +log4j.appender.R.layout=org.apache.log4j.PatternLayout
    +log4j.appender.R.layout.ConversionPattern=%p %t %c - %m%n + +
  2. + +
  3. Download Log4J + (v1.2 or later) and place the log4j jar in $CATALINA_HOME/lib.
  4. + +
  5. Build or download the additional logging components. See the + extras components documentation for + details.
  6. + +
  7. Replace $CATALINA_HOME/bin/tomcat-juli.jar with + output/extras/tomcat-juli.jar.
  8. + +
  9. Place output/extras/tomcat-juli-adapters.jar in + $CATALINA_HOME/lib.
  10. + +
  11. Delete $CATALINA_BASE/conf/logging.properties to + prevent java.util.logging generating zero length log files.
  12. +
  13. Start Tomcat
  14. +
+

+ +

+ This log4j configuration sets up a file called tomcat.log in your + Tomcat logs folder with a maximum file size of 10MB and + up to 10 backups. INFO level is specified which will result in a similar + level of detail to the standard java.util.logging confgiuration. Use DEBUG + level logging for the most verbose output from Tomcat. +

+ +

+ You can (and should) be more picky about which packages to include + in the logging. Tomcat defines loggers by Engine and Host names. + For example, for a more detailed Catalina localhost log, add this to the + end of the log4j.properties above. Note that there are known issues with + using this naming convention (with square brackets) in log4j XML based + configuration files, so we recommend you use a properties file as + described until a future version of log4j allows this convention. + + +log4j.logger.org.apache.catalina.core.ContainerBase.[Catalina].[localhost]=DEBUG
+log4j.logger.org.apache.catalina.core=DEBUG
+log4j.logger.org.apache.catalina.session=DEBUG
+ + + Be warned a level of DEBUG will produce megabytes of logging and slow + startup of Tomcat. This level should be used sparingly when debugging of + internal Tomcat operations is required. +

+ +

+ Your web applications should certainly use their own log4j configuration. + This is valid with the above configuration. You would place a + similar log4j.properties file in your web application's WEB-INF/classes + directory, and log4jx.y.z.jar into WEB-INF/lib. Then specify your package + level logging. This is a basic setup of log4j which does *not* require + Commons-Logging, and you should consult the + log4j + documentation for more options. This page is intended only as a + bootstrapping guide. +

+ +

+ If you have multiple instances of Tomcat, each with a separate + $CATALINA_BASE but a shared $CATALINA_HOME then + you can configure log4j on a per instance basis by replacing references to + $CATALINA_HOME in the above instructions with + $CATALINA_BASE. Note that if you do this then you may need to + make some, or all, of the following additional changes: +

    +
  • create a $CATALINA_BASE/bin directory
  • +
  • create a $CATALINA_BASE/lib directory
  • +
  • if running with a security manager, adjust the codebase for JULI in + $CATALINA_BASE/conf/catalina.policy
  • +
+

+
+ + +
diff --git a/webapps/docs/manager-howto.xml b/webapps/docs/manager-howto.xml new file mode 100644 index 000000000000..cd080648445c --- /dev/null +++ b/webapps/docs/manager-howto.xml @@ -0,0 +1,1324 @@ + + + +]> + + + &project; + + + Craig R. McClanahan + Manager App HOW-TO + + + + +
+ +
+ +
+ +

In many production environments, it is very useful to have the capability +to deploy a new web application, or undeploy an existing one, without having +to shut down and restart the entire container. In addition, you can request +an existing application to reload itself, even if you have not declared it +to be reloadable in the Tomcat server +configuration file.

+ +

To support these capabilities, Tomcat includes a web application +(installed by default on context path /manager) that supports +the following functions:

+
    +
  • Deploy a new web application from the uploaded contents of a WAR file.
  • +
  • Deploy a new web application, on a specified context path, from the + server file system.
  • +
  • List the currently deployed web applications, as well as the + sessions that are currently active for those web apps.
  • +
  • Reload an existing web application, to reflect changes in the + contents of /WEB-INF/classes or /WEB-INF/lib. +
  • +
  • List the OS and JVM property values.
  • +
  • List the available global JNDI resources, for use in deployment + tools that are preparing <ResourceLink> elements + nested in a <Context> deployment description.
  • +
  • List the available security roles defined in the user database.
  • +
  • Start a stopped application (thus making it available again).
  • +
  • Stop an existing application (so that it becomes unavailable), but + do not undeploy it.
  • +
  • Undeploy a deployed web application and delete its document base + directory (unless it was deployed from file system).
  • +
+ +

A default Tomcat installation includes the Manager. To add an instance of the +Manager web application Context to a new host install the +manager.xml context configuration file in the +$CATALINA_BASE/conf/[enginename]/[hostname] folder. Here is an +example:

+
+<Context path="/manager" debug="0" privileged="true"
+         docBase="/usr/local/kinetic/tomcat6/server/webapps/manager">
+</Context>
+
+ +

If you have Tomcat configured to support multiple virtual hosts +(websites) you would need to configure a Manager for each.

+ +

There are three ways to use the Manager web application.

+
    +
  • As an application with a user interface you use in your browser. +Here is an example URL where you can replace localhost with +your website host name: http://localhost/manager/html/ .
  • +
  • A minimal version using HTTP requests only which is suitable for use +by scripts setup by system administrators. Commands are given as part of the +request URI, and responses are in the form of simple text that can be easily +parsed and processed. See +Supported Manager Commands for more information.
  • +
  • A convenient set of task definitions for the Ant +(version 1.4 or later) build tool. See +Executing Manager Commands +With Ant for more information.
  • +
+ +
+ +
+ +
+

The description below uses the variable name $CATALINA_BASE to refer the + base directory against which most relative paths are resolved. If you have + not configured Tomcat for multiple instances by setting a CATALINA_BASE + directory, then $CATALINA_BASE will be set to the value of $CATALINA_HOME, + the directory into which you have installed Tomcat.

+
+ +

It would be quite unsafe to ship Tomcat with default settings that allowed +anyone on the Internet to execute the Manager application on your server. +Therefore, the Manager application is shipped with the requirement that anyone +who attempts to use it must authenticate themselves, using a username and +password that have the role manager-script associated with +them. Further, there is no username in the default users file +($CATALINA_BASE/conf/tomcat-users.xml) that is assigned this +role. Therefore, access to the Manager application is completely disabled +by default.

+ +

To enable access to the Manager web application, you must either create +a new username/password combination and associate the role name +manager-script with it, or add the +manager-script role +to some existing username/password combination. Exactly where this is done +depends on which Realm implementation you are using:

+
    +
  • MemoryRealm - If you have not customized your + $CATALINA_BASE/conf/server.xml to select a different one, + Tomcat defaults to an XML-format file stored at + $CATALINA_BASE/conf/tomcat-users.xml, which can be + edited with any text editor. This file contains an XML + <user> for each individual user, which might + look something like this: + +<user name="craigmcc" password="secret" roles="standard,manager-script" /> + + which defines the username and password used by this individual to + log on, and the role names he or she is associated with. You can + add the manager-script role to the comma-delimited + roles attribute for one or more existing users, and/or + create new users with that assigned role.
  • +
  • JDBCRealm - Your user and role information is stored in + a database accessed via JDBC. Add the manager-script role + to one or more existing users, and/or create one or more new users + with this role assigned, following the standard procedures for your + environment.
  • +
  • JNDIRealm - Your user and role information is stored in + a directory server accessed via LDAP. Add the + manager-script role to one or more existing users, + and/or create one or more new users with this role assigned, following + the standard procedures for your environment.
  • +
+ +

The first time you attempt to issue one of the Manager commands +described in the next section, you will be challenged to log on using +BASIC authentication. The username and password you enter do not matter, +as long as they identify a valid user in the users database who possesses +the role manager-script.

+ +

In addition to the password restrictions the Manager web application +could be restricted by the remote IP address or host by adding a +RemoteAddrValve or RemoteHostValve. Here is +an example of restricting access to the localhost by IP address:

+
+<Context path="/manager" privileged="true"
+         docBase="/usr/local/kinetic/tomcat6/server/webapps/manager">
+         <Valve className="org.apache.catalina.valves.RemoteAddrValve"
+                allow="127\.0\.0\.1"/>
+</Context>
+
+
+ + +
+ +

All commands that the Manager application knows how to process are +specified in a single request URI like this:

+ +http://{host}:{port}/manager/text/{command}?{parameters} + +

where {host} and {port} represent the hostname +and port number on which Tomcat is running, {command} +represents the Manager command you wish to execute, and +{parameters} represents the query parameters +that are specific to that command. In the illustrations below, customize +the host and port appropriately for your installation.

+ +

Most commands accept one or more of the following query parameters:

+
    +
  • path - The context path (including the leading slash) + of the web application you are dealing with. To select the ROOT web + application, specify "/". NOTE - + It is not possible to perform administrative commands on the + Manager application itself.
  • +
  • war - URL of a web application archive (WAR) file, + 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: +
      +
    • file:/absolute/path/to/a/directory - The absolute + path of a directory that contains the unpacked version of a web + application. This directory will be attached to the context path + you specify without any changes.
    • +
    • file:/absolute/path/to/a/webapp.war - The absolute + path of a web application archive (WAR) file. This is valid + only for the /deploy command, and is + the only acceptable format to that command.
    • +
    • jar:file:/absolute/path/to/a/warfile.war!/ - The + URL to a local web application archive (WAR) file. You can use any + syntax that is valid for the JarURLConnection class + for reference to an entire JAR file.
    • +
    • file:/absolute/path/to/a/context.xml - The + absolute path of a web application Context configuration ".xml" + file which contains the Context configuration element.
    • +
    • directory - The directory name for the web + application context in the Host's application base directory.
    • +
    • webapp.war - The name of a web application war file + located in the Host's application base directory.
    • +
  • +
+ +

Each command will return a response in text/plain format +(i.e. plain ASCII with no HTML markup), making it easy for both humans and +programs to read). The first line of the response will begin with either +OK or FAIL, indicating whether the requested +command was successful or not. In the case of failure, the rest of the first +line will contain a description of the problem that was encountered. Some +commands include additional lines of information as described below.

+ +

Internationalization Note - The Manager application looks up +its message strings in resource bundles, so it is possible that the strings +have been translated for your platform. The examples below show the English +version of the messages.

+ + + + +http://localhost:8080/manager/text/deploy?path=/foo + + +

Upload the web application archive (WAR) file that is specified as the +request data in this HTTP PUT request, install it into the appBase +directory of our corresponding virtual host, and start , using the directory +name or the war file name without the .war extension as the path. The +application can later be undeployed (and the corresponding application directory +removed) by use of the /undeploy command.

+ +

The .WAR file may include Tomcat specific deployment configuration, by +including a Context configuration XML file in +/META-INF/context.xml.

+ +

URL parameters include:

+
    +
  • update: When set to true, any existing update will be + undeployed first. The default value is set to false.
  • +
  • tag: Specifying a tag name, this allows associating the + deployed webapp with a version number. The application version can + be later redeployed when needed using only the tag.
  • +
+ +

NOTE - This command is the logical +opposite of the /undeploy command.

+ +

If installation and startup is successful, you will receive a response +like this:

+ +OK - Deployed application at context path /foo + + +

Otherwise, the response will start with FAIL and include an +error message. Possible causes for problems include:

+
    +
  • Application already exists at path /foo +
    +

    The context paths for all currently running web applications must be + unique. Therefore, you must undeploy the existing web + application using this context path, or choose a different context path + for the new one. The update parameter may be specified as + a parameter on the URL, with a value of true to avoid this + error. In that case, an undeploy will be performed on an existing + application before performing the deployment.

    +
  • +
  • Encountered exception +
    +

    An exception was encountered trying to start the new web application. + Check the Tomcat logs for the details, but likely explanations include + problems parsing your /WEB-INF/web.xml file, or missing + classes encountered when initializing application event listeners and + filters.

    +
  • +
+ +
+ + + +

Deploy and start a new web application, attached to the specified context +path (which must not be in use by any other web application). +This command is the logical opposite of the /undeploy command.

+ +

There are a number of different ways the deploy command can be used.

+ +

Deploy a version of a previously deployed webapp

+ +

This can be used to deploy a previous version of a web application, which +has been deployed using the tag attribute. Note that the work +directory for the Manager webapp will contain the previously deployed WARs; +removing it would make the deployment fail.

+ +http://localhost:8080/manager/text/deploy?path=/footoo&tag=footag + + + +

Deploy a Directory or WAR by URL

+ +

Deploy a web application directory or ".war" file located on the Tomcat +server. If no path is specified, the directory name or the war file +name without the ".war" extension is used as the path. The war +parameter specifies a URL (including the file: 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 +java.net.JarURLConnection class. Use only URLs that refer to +the entire WAR file.

+ +

In this example the web application located in the directory +/path/to/foo on the Tomcat server is deployed as the +web application context named /footoo.

+ +http://localhost:8080/manager/text/deploy?path=/footoo&war=file:/path/to/foo + + + +

In this example the ".war" file /path/to/bar.war on the +Tomcat server is deployed as the web application context named +/bar. Notice that there is no path parameter +so the context path defaults to the name of the web application archive +file without the ".war" extension.

+ +http://localhost:8080/manager/text/deploy?war=jar:file:/path/to/bar.war!/ + + + +

Deploy a Directory or War from the Host appBase

+ +

Deploy a web application directory or ".war" file located in your Host +appBase directory. The directory name or the war file name without the ".war" +extension is used as the path.

+ +

In this example the web application located in a sub directory named +foo in the Host appBase directory of the Tomcat server is +deployed as the web application context named /foo. Notice +that the context path used is the name of the web application directory.

+ +http://localhost:8080/manager/text/deploy?war=foo + + + +

In this example the ".war" file bar.war located in your +Host appBase directory on the Tomcat server is deployed as the web +application context named /bar.

+ +http://localhost:8080/manager/text/deploy?war=bar.war + + + +

Deploy using a Context configuration ".xml" file

+ +

If the Host deployXML flag is set to true you can deploy a web +application using a Context configuration ".xml" file and an optional +".war" file or web application directory. The context path +is not used when deploying a web application using a context ".xml" +configuration file.

+ +

A Context configuration ".xml" file can contain valid XML for a +web application Context just as if it were configured in your +Tomcat server.xml configuration file. Here is an +example:

+ +<Context path="/foobar" docBase="/path/to/application/foobar" + debug="0"> + + <!-- Link to the user database we will get roles from --> + <ResourceLink name="users" global="UserDatabase" + type="org.apache.catalina.UserDatabase"/> + +</Context> + + + +

When the optional war 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.

+ +

Here is an example of deploying an application using a Context +configuration ".xml" file.

+ +http://localhost:8080/manager/text/deploy?config=file:/path/context.xml + + + +

Here is an example of deploying an application using a Context +configuration ".xml" file and a web application ".war" file located +on the server.

+ +http://localhost:8080/manager/text/deploy?config=file:/path/context.xml&war=jar:file:/path/bar.war!/ + + + +

Deployment Notes

+ +

If the Host is configured with unpackWARs=true and you deploy a war +file, the war will be unpacked into a directory in your Host appBase +directory.

+ +

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.

+ +

For security when untrusted users can manage web applications, the +Host deployXML flag can be set to false. This prevents untrusted users +from deploying web applications using a configuration XML file and +also prevents them from deploying application directories or ".war" +files located outside of their Host appBase.

+ + +

Deploy Response

+ +

If installation and startup is successful, you will receive a response +like this:

+ +OK - Deployed application at context path /foo + + +

Otherwise, the response will start with FAIL and include an +error message. Possible causes for problems include:

+
    +
  • Application already exists at path /foo +
    +

    The context paths for all currently running web applications must be + unique. Therefore, you must undeploy the existing web + application using this context path, or choose a different context path + for the new one. The update parameter may be specified as + a parameter on the URL, with a value of true to avoid this + error. In that case, an undeploy will be performed on an existing + application before performing the deployment.

    +
  • +
  • Document base does not exist or is not a readable directory +
    +

    The URL specified by the war parameter 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 specified by + the war parameter.

    +
  • +
  • Encountered exception +
    +

    An exception was encountered trying to start the new web application. + Check the Tomcat logs for the details, but likely explanations include + problems parsing your /WEB-INF/web.xml file, or missing + classes encountered when initializing application event listeners and + filters.

    +
  • +
  • Invalid application URL was specified +
    +

    The URL for the directory or web application that you specified + was not valid. Such URLs must start with file:, and URLs + for a WAR file must end in ".war".

    +
  • +
  • Invalid context path was specified +
    +

    The context path must start with a slash character. To reference the + ROOT web application use "/".

    +
  • +
  • Context path must match the directory or WAR file name: +
    + 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. +
  • +
  • Only web applications in the Host web application directory can + be installed +
    + If the Host deployXML flag is set to false this error will happen + if an attempt is made to deploy a web application directory or + ".war" file outside of the Host appBase directory. +
  • +
+ +
+ + + + +http://localhost:8080/manager/text/list + + +

List the context paths, current status (running or +stopped), and number of active sessions for all currently +deployed web applications. A typical response immediately +after starting Tomcat might look like this:

+ +OK - Listed applications for virtual host localhost +/webdav:running:0 +/examples:running:0 +/manager:running:0 +/:running:0 + + +
+ + + + +http://localhost:8080/manager/text/reload?path=/examples + + +

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 /WEB-INF/classes +directory or when you have added or updated jar files in the +/WEB-INF/lib directory. +

+

NOTE: The /WEB-INF/web.xml +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. +

+ +

If this command succeeds, you will see a response like this:

+ +OK - Reloaded application at context path /examples + + +

Otherwise, the response will start with FAIL and include an +error message. Possible causes for problems include:

+
    +
  • Encountered exception +
    +

    An exception was encountered trying to restart the web application. + Check the Tomcat logs for the details.

    +
  • +
  • Invalid context path was specified +
    +

    The context path must start with a slash character. To reference the + ROOT web application use "/".

    +
  • +
  • No context exists for path /foo +
    +

    There is no deployed application on the context path + that you specified.

    +
  • +
  • No context path was specified +
    + The path parameter is required. +
  • +
  • Reload not supported on WAR deployed at path /foo +
    + Currently, application reloading (to pick up changes to the classes or + web.xml file) is not supported when a web application is + deployed directly from a WAR file. It only works when the web application + is deployed from an unpacked directory. If you are using a WAR file, + you should undeploy and then deploy or + deploy with the update parameter the + application again to pick up your changes. +
  • +
+ +
+ + + + +http://localhost:8080/manager/text/serverinfo + + +

Lists information about the Tomcat version, OS, and JVM properties.

+ +

If an error occurs, the response will start with FAIL and +include an error message. Possible causes for problems include:

+
    +
  • Encountered exception +
    +

    An exception was encountered trying to enumerate the system properties. + Check the Tomcat logs for the details.

    +
  • +
+ +
+ + + + +http://localhost:8080/manager/text/resources[?type=xxxxx] + + +

List the global JNDI resources that are available for use in resource +links for context configuration files. If you specify the type +request parameter, the value must be the fully qualified Java class name of +the resource type you are interested in (for example, you would specify +javax.sql.DataSource to acquire the names of all available +JDBC data sources). If you do not specify the type request +parameter, resources of all types will be returned.

+ +

Depending on whether the type request parameter is specified +or not, the first line of a normal response will be:

+
+  OK - Listed global resources of all types
+
+

or

+
+  OK - Listed global resources of type xxxxx
+
+

followed by one line for each resource. Each line is composed of fields +delimited by colon characters (":"), as follows:

+
    +
  • Global Resource Name - The name of this global JNDI resource, + which would be used in the global attribute of a + <ResourceLink> element.
  • +
  • Global Resource Type - The fully qualified Java class name of + this global JNDI resource.
  • +
+ +

If an error occurs, the response will start with FAIL and +include an error message. Possible causes for problems include:

+
    +
  • Encountered exception +
    +

    An exception was encountered trying to enumerate the global JNDI + resources. Check the Tomcat logs for the details.

    +
  • +
  • No global JNDI resources are available +
    +

    The Tomcat server you are running has been configured without + global JNDI resources.

    +
  • +
+ + +
+ + + + + +http://localhost:8080/manager/text/roles + + +

List the security role names (and corresponding descriptions) that are +available in the org.apache.catalina.UserDatabase resource that +is linked to the users resource reference in the web.xml file +for the Manager web application. This would typically be used, for example, +by a deployment tool that wanted to create +<security-role-ref> elements to map security role names +used in a web application to the role names actually defined within the +container.

+ +

By default, the users resource reference is pointed at the +global UserDatabase resource. If you choose to utilize a +different user database per virtual host, you should modify the +<ResourceLink> element in the default +manager.xml context configuration file to point at the global +user database resource for this virtual host.

+ +

When this command is executed, the first line of the response will be:

+
+  OK - Listed security roles
+
+

followed by one line for each security role. Each line is composed of +fields delimited by colon characters (":") as follows:

+
    +
  • Security Role Name - A security role name that is known to Tomcat + in the user database.
  • +
  • Description - Description of this security role (useful in + creating user interfaces for selecting roles.
  • +
+ +

If an error occurs, the response will start with FAIL and +include an error message. Possible causes for problems include:

+
    +
  • Cannot resolve user database reference - A JNDI error prevented + the successful lookup of the org.apache.catalina.UserDatabase + resource. Check the Tomcat log files for a stack trace associated with + this error.
  • +
  • No user database is available - You have not configured a resource + reference for the users resource that points at an + appropriate user database instance. Check your manager.xml + file and ensure that you have created an appropriate + <ResourceLink> or + <ResourceParams> element for this resource.
  • +
+ +
+ + + + + +http://localhost:8080/manager/text/sessions?path=/examples + + +

Display the default session timeout for a web application, and the +number of currently active sessions that fall within ten-minute ranges of +their actual timeout times. For example, after restarting Tomcat and then +executing one of the JSP samples in the /examples web app, +you might get something like this:

+ +OK - Session information for application at context path /examples +Default maximum session inactive interval 30 minutes +30 - <40 minutes:1 sessions + + +
+ + + + + +http://localhost:8080/manager/text/start?path=/examples + + +

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.

+ +

If this command succeeds, you will see a response like this:

+ +OK - Started application at context path /examples + + +

Otherwise, the response will start with FAIL and include an +error message. Possible causes for problems include:

+
    +
  • Encountered exception +
    +

    An exception was encountered trying to start the web application. + Check the Tomcat logs for the details.

    +
  • +
  • Invalid context path was specified +
    +

    The context path must start with a slash character. To reference the + ROOT web application use "/".

    +
  • +
  • No context exists for path /foo +
    +

    There is no deployed application on the context path + that you specified.

    +
  • +
  • No context path was specified +
    + The path parameter is required. +
  • +
+ +
+ + + + +http://localhost:8080/manager/text/stop?path=/examples + + +

Signal an existing application to make itself unavailable, but leave it +deployed. 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.

+ +

If this command succeeds, you will see a response like this:

+ +OK - Stopped application at context path /examples + + +

Otherwise, the response will start with FAIL and include an +error message. Possible causes for problems include:

+
    +
  • Encountered exception +
    +

    An exception was encountered trying to stop the web application. + Check the Tomcat logs for the details.

    +
  • +
  • Invalid context path was specified +
    +

    The context path must start with a slash character. To reference the + ROOT web application use "/".

    +
  • +
  • No context exists for path /foo +
    +

    There is no deployed application on the context path + that you specified.

    +
  • +
  • No context path was specified +
    + The path parameter is required. +
  • +
+ +
+ + + + + +http://localhost:8080/manager/text/undeploy?path=/examples + + +

WARNING - This command will delete any web +application artifacts that exist within appBase directory +(typically "webapps") for this virtual host. +This will delete the the application .WAR, if present, +the application directory resulting either from a deploy in unpacked form +or from .WAR expansion as well as the XML Context definition from +$CATALINA_BASE/conf/[enginename]/[hostname]/ directory. +If you simply want to take an application +out of service, you should use the /stop command instead.

+ +

Signal an existing application to gracefully shut itself down, and +remove it from Tomcat (which also makes this context path available for +reuse later). In addition, the document root directory is removed, if it +exists in the appBase directory (typically "webapps") for +this virtual host. This command is the logical opposite of the +/deploy command.

+ +

If this command succeeds, you will see a response like this:

+ +OK - Undeployed application at context path /examples + + +

Otherwise, the response will start with FAIL and include an +error message. Possible causes for problems include:

+
    +
  • Encountered exception +
    +

    An exception was encountered trying to undeploy the web application. + Check the Tomcat logs for the details.

    +
  • +
  • Invalid context path was specified +
    +

    The context path must start with a slash character. To reference the + ROOT web application use "/".

    +
  • +
  • No context exists for path /foo +
    +

    There is no deployed application on the context path + that you specified.

    +
  • +
  • No context path was specified +
    + The path parameter is required. +
  • +
+ +
+ + + + +http://localhost:8080/manager/text/findleaks + + +

The find leaks diagnostic triggers a full garbage collection. It +should be used with extreme caution on production systems.

+ +

The find leaks diagnostic attempts to identify web applications that have +caused memory leaks when they were stopped, reloaded or undeployed. Results +should always be confirmed +with a profiler. The diagnostic uses additional functionality provided by the +StandardHost implementation. It will not work if a custom host is used that +does not extend StandardHost.

+ +

Explicitly triggering a full garbage collection from Java code is documented +to be unreliable. Furthermore, depending on the JVM used, there are options to +disable explicit GC triggering, like -XX:+DisableExplicitGC. +If you want to make sure, that the diagnostics were successfully running a full GC, +you will need to check using tools like GC logging, JConsole or similar.

+ +

If this command succeeds, you will see a response like this:

+ +/leaking-webapp + + +

Each context path for a web application that was stopped, reloaded or +undeployed, but which classes from the previous runs are still loaded in memory, +thus causing a memory leak, will be listed on a new line. If an application +has been reloaded several times, it may be listed several times.

+ +

If the command does not succeed, the response will start with +FAIL and include an error message.

+ +
+ + + +

From this link , you can view information about the server.

+ +

First, you have the server and JVM version number, JVM provider, OS name +and number followed by the architecture type.

+ +

Second, there is several information about the memory usage of the JVM +(available, total and max memory).

+ +

Then, there is information about the Tomcat AJP and HTTP connectors. +The same information is available for both of them : +

+
    +
  • Threads information : Max threads, min and max spare threads, + current thread count and current thread busy.

  • +
  • Request information : Max processing time and processing time, + request and error count, bytes received and sent.

  • +
  • A table showing Stage, Time, Bytes Sent, Bytes Receive, Client, + VHost and Request. All existing threads are listed in the table. + Here is the list of the possible thread stages :

    +
      +
    • "Parse and Prepare Request" : The request headers are + being parsed or the necessary preparation to read the request body (if + a transfer encoding has been specified) is taking place.

    • +
    • "Service" : The thread is processing a request and + generating the response. This stage follows the "Parse and Prepare + Request" stage and precedes the "Finishing" stage. There is always at + least one thread in this stage (the server-status page).

    • +
    • "Finishing" : The end of the request processing. Any + remainder of the response still in the output buffers is sent to the + client. This stage is followed by "Keep-Alive" if it is appropriate to + keep the connection alive or "Ready" if "Keep-Alive" is not + appropriate.

    • +
    • "Keep-Alive" : The thread keeps the connection open to + the client in case the client sends another request. If another request + is recieved, the next stage will br "Parse and Prepare Requst". If no + request is received before the keep alive times out, the connection will + be closed and the next stage will be "Ready".

    • +
    • "Ready" : The thread is at rest and ready to be + used.

    • +
    +
  • +
+
+ +
+ +
+ +

In addition to the ability to execute Manager commands via HTTP requests, +as documented above, Tomcat includes a convenient set of Task definitions +for the Ant (version 1.4 or later) build tool. In order to use these +commands, you must perform the following setup operations:

+
    +
  • Download the binary distribution of Ant from + http://ant.apache.org. + You must use version 1.4 or later.
  • +
  • Install the Ant distribution in a convenient directory (called + ANT_HOME in the remainder of these instructions).
  • +
  • Copy the file server/lib/catalina-ant.jar from your Tomcat + installation into Ant's library directory ($ANT_HOME/lib). +
  • +
  • Add the $ANT_HOME/bin directory to your PATH + environment variable.
  • +
  • Configure at least one username/password combination in your Tomcat + user database that includes the manager-script role.
  • +
+ +

To use custom tasks within Ant, you must declare them first with a +<taskdef> element. Therefore, your build.xml +file might look something like this:

+ + + +
+<project name="My Application" default="compile" basedir=".">
+
+  <!-- Configure the directory into which the web application is built -->
+  <property name="build"    value="${basedir}/build"/>
+
+  <!-- Configure the context path for this application -->
+  <property name="path"     value="/myapp"/>
+
+  <!-- Configure properties to access the Manager application -->
+  <property name="url"      value="http://localhost:8080/manager/text"/>
+  <property name="username" value="myusername"/>
+  <property name="password" value="mypassword"/>
+
+  <!-- Configure the custom Ant tasks for the Manager application -->
+  <taskdef name="deploy"    classname="org.apache.catalina.ant.DeployTask"/>
+  <taskdef name="list"      classname="org.apache.catalina.ant.ListTask"/>
+  <taskdef name="reload"    classname="org.apache.catalina.ant.ReloadTask"/>
+  <taskdef name="resources" classname="org.apache.catalina.ant.ResourcesTask"/>
+  <taskdef name="roles"     classname="org.apache.catalina.ant.RolesTask"/>
+  <taskdef name="start"     classname="org.apache.catalina.ant.StartTask"/>
+  <taskdef name="stop"      classname="org.apache.catalina.ant.StopTask"/>
+  <taskdef name="undeploy"  classname="org.apache.catalina.ant.UndeployTask"/>
+
+  <!-- Executable Targets -->
+  <target name="compile" description="Compile web application">
+    <!-- ... construct web application in ${build} subdirectory, and
+            generated a ${path}.war ... -->
+  </target>
+
+  <target name="deploy" description="Install web application"
+          depends="compile">
+    <deploy url="${url}" username="${username}" password="${password}"
+            path="${path}" war="file:${build}${path}.war"/>
+  </target>
+
+  <target name="reload" description="Reload web application"
+          depends="compile">
+    <reload  url="${url}" username="${username}" password="${password}"
+            path="${path}"/>
+  </target>
+
+  <target name="undeploy" description="Remove web application">
+    <undeploy url="${url}" username="${username}" password="${password}"
+            path="${path}"/>
+  </target>
+
+</project>
+
+ +

Note: The definition of the resources task above will override the resources +datatype added in Ant 1.7. If you wish to use the resources datatype you will +need to use Ant's namespace support to assign the Tomcat tasks to their own +namespace.

+ +

Now, you can execute commands like ant deploy to deploy the +application to a running instance of Tomcat, or ant reload to +tell Tomcat to reload it. Note also that most of the interesting values in +this build.xml file are defined as replaceable properties, so +you can override their values from the command line. For example, you might +consider it a security risk to include the real manager password in your +build.xml file's source code. To avoid this, omit the password +property, and specify it from the command line:

+
+  ant -Dpassword=secret deploy
+
+ + + +

Using Ant version 1.6.2 or later, +the Catalina tasks offer the option to capture their output in +properties or external files. They support directly the following subset of the +<redirector> type attributes: +

+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
AttributeDescriptionRequired
outputName of a file to which to write the output. If +the error stream is not also redirected to a file or property, it will +appear in this output.No
errorThe file to which the standard error of the +command should be redirected.No
logErrorThis attribute is used when you wish to see +error output in Ant's log and you are redirecting output to a +file/property. The error output will not be included in the output +file/property. If you redirect error with the error or errorProperty +attributes, this will have no effect.No
appendWhether output and error files should be +appended to or overwritten. Defaults to false.No
createemptyfilesWhether output and error files should be created +even when empty. Defaults to true.No
outputpropertyThe name of a property in which the output of +the command should be stored. Unless the error stream is redirected to +a separate file or stream, this property will include the error output.No
errorpropertyThe name of a property in which the standard +error of the command should be stored.No
+ +

A couple of additional attributes can also be specified: +

+ + + + + + + + + + + + + + + + + + +
AttributeDescriptionRequired
alwaysLogThis attribute is used when you wish to see the +output you are capturing, appearing also in the Ant's log. It must not be +used unless you are capturing task output. +Defaults to false. +This attribute will be supported directly by <redirector> +in Ant 1.6.3No
failonerrorThis attribute is used when you wish to avoid that +any manager command processing error terminates the ant execution. Defaults to true. +It must be set to false, if you want to capture error output, +otherwise execution will terminate before anything can be captured. +

+This attribute acts only on manager command execution, +any wrong or missing command attribute will still cause Ant execution termination. +
No
+ +

They also support the embedded <redirector> element +in which you can specify +its full set of attributes, but input, inputstring and +inputencoding that, even if accepted, are not used because they have +no meaning in this context. +Refer to ant manual for details on +<redirector> element attributes. +

+ +

+Here is a sample build file extract that shows how this output redirection support +can be used: +

+ + + +
+    <target name="manager.deploy"
+        depends="context.status"
+        if="context.notInstalled">
+        <deploy url="${mgr.url}"
+            username="${mgr.username}"
+            password="${mgr.password}"
+            path="${mgr.context.path}"
+            config="${mgr.context.descriptor}"/>
+    </target>
+
+    <target name="manager.deploy.war"
+        depends="context.status"
+        if="context.deployable">
+        <deploy url="${mgr.url}"
+            username="${mgr.username}"
+            password="${mgr.password}"
+            update="${mgr.update}"
+            path="${mgr.context.path}"
+            war="${mgr.war.file}"/>
+    </target>
+    
+    <target name="context.status">
+        <property name="running" value="${mgr.context.path}:running"/>
+        <property name="stopped" value="${mgr.context.path}:stopped"/>
+    
+        <list url="${mgr.url}"
+            outputproperty="ctx.status"
+            username="${mgr.username}"
+            password="${mgr.password}">
+        </list>
+        
+        <condition property="context.running">
+            <contains string="${ctx.status}" substring="${running}"/>
+        </condition>
+        <condition property="context.stopped">
+            <contains string="${ctx.status}" substring="${stopped}"/>
+        </condition>
+        <condition property="context.notInstalled">
+            <and>
+                <isfalse value="${context.running}"/>
+                <isfalse value="${context.stopped}"/>
+            </and>
+        </condition>
+        <condition property="context.deployable">
+            <or>
+                <istrue value="${context.notInstalled}"/>
+                <and>
+                    <istrue value="${context.running}"/>
+                    <istrue value="${mgr.update}"/>
+                </and>
+                <and>
+                    <istrue value="${context.stopped}"/>
+                    <istrue value="${mgr.update}"/>
+                </and>
+            </or>
+        </condition>
+        <condition property="context.undeployable">
+            <or>
+                <istrue value="${context.running}"/>
+                <istrue value="${context.stopped}"/>
+            </or>
+        </condition>
+    </target>
+
+ +

WARNING: even if it doesn't make many sense, and is always a bad idea, +calling a Catalina task more than once, +badly set Ant tasks depends chains may cause that a task be called +more than once in the same Ant run, even if not intended to. A bit of caution should be exercised when you are +capturing output from that task, because this could lead to something unexpected:

+
    +
  • when capturing in a property you will find in it only the output from the first call, because +Ant properties are immutable and once set they cannot be changed, +
  • +
  • when capturing in a file, each run will overwrite it and you will find in it only the last call +output, unless you are using the append="true" attribute, in which case you will +see the output of each task call appended to the file. +
  • +
+ +
+ +
+ +
+ + + The JMX Proxy Servlet is a lightweight proxy to get and set the + tomcat internals. (Or any class that has been exposed via an MBean) + Its usage is not very user friendly but the UI is + extremely help for integrating command line scripts for monitoring + and changing the internals of tomcat. You can do two things with the proxy: + get information and set information. For you to really understand the + JMX Proxy Servlet, you should have a general understanding of JMX. + If you don't know what JMX is, then prepare to be confused. + + + + This takes the form: + +http://webserver/manager/jmxproxy/?qry=STUFF + + Where STUFF is the JMX query you wish to perform. For example, + here are some queries you might wish to run: +
    +
  • + qry=*%3Atype%3DRequestProcessor%2C* --> + type=RequestProcessor which will locate all + workers which can process requests and report + their state. +
  • +
  • + qry=*%3Aj2eeType=Servlet%2c* --> + j2eeType=Servlet which return all loaded servlets. +
  • +
  • + qry=Catalina%3Atype%3DEnvironment%2Cresourcetype%3DGlobal%2Cname%3DsimpleValue --> + Catalina:type=Environment,resourcetype=Global,name=simpleValue + which look for a specific MBean by the given name. +
  • +
+ You'll need to experiment with this to really understand its capabilites. + If you provide no qry parameter, then all of the MBeans will + be displayed. We really recommend looking at the tomcat source code and + understand the JMX spec to get a better understanding of all the queries + you may run. +
+ + + Now that you can query an MBean, its time to muck with Tomcat's internals! + The general form of the set command is : + +http://webserver/manager/jmxproxy/?set=BEANNAME&att=MYATTRIBUTE&val=NEWVALUE + + So you need to provide 3 request parameters: +
    +
  1. set: The full bean name
  2. +
  3. att: The attribute you wish to alter
  4. +
  5. val: The new value
  6. +
+ If all goes ok, then it will say OK, otherwise an error message will be + shown. For example, lets say we wish to turn up debugging on the fly for the + ErrorReportValve. The following will set debugging to 10. + +http://localhost:8080/manager/jmxproxy/ +?set=Catalina%3Atype%3DValve%2Cname%3DErrorReportValve%2Chost%3Dlocalhost&att=debug&val=10 + + and my result is (YMMV): + +Result: ok + + + Here is what I see if I pass in a bad value. Here is the URL I used, + I try set debugging equal to 'cowbell': + +http://localhost:8080/manager/jmxproxy/ +?set=Catalina%3Atype%3DValve%2Cname%3DErrorReportValve%2Chost%3Dlocalhost&att=debug&val=cowbell + + When I try that, my result is + +Error: java.lang.NumberFormatException: For input string: "cowbell" + +
+ + +
+ + + + + +
diff --git a/webapps/docs/maven-jars.xml b/webapps/docs/maven-jars.xml new file mode 100644 index 000000000000..b1cdf66c6370 --- /dev/null +++ b/webapps/docs/maven-jars.xml @@ -0,0 +1,57 @@ + + + +]> + + + &project; + + + Filip Hanik + Apache Tomcat - Using Tomcat libraries with Maven + + + + +
+ +
+ +
+ + Tomcat snapshots are located in the + Apache Snapshot Repository. + The official URL is http://people.apache.org/repo/m2-snapshot-repository/org/apache/tomcat/
+ Snapshots are done periodically, not on a regular basis, but when changes happen and the Tomcat team deems a new snapshot might + useful. +
+ + At every release, be it alpha, beta or stable, we will publish the JARs to + Tomcat's Staging Repository. + The URL for this is http://tomcat.apache.org/dev/dist/m2-repository/org/apache/tomcat/.
+ At some point, this URL will change over to ASF's main repository that synchronizes with IBiblio.
+ When that happens, all releases will be moved over, and this repository will stick around for a while, but no + new releases will be published to the staging repository. +
+ +
+ + + +
diff --git a/webapps/docs/mbeans-descriptor-howto.xml b/webapps/docs/mbeans-descriptor-howto.xml new file mode 100644 index 000000000000..597ddb9d60ec --- /dev/null +++ b/webapps/docs/mbeans-descriptor-howto.xml @@ -0,0 +1,83 @@ + + + +]> + + + &project; + + + Amy Roh + MBean Descriptor How To + + + + +
+ +
+ +
+ +

Tomcat uses JMX MBeans as the technology for implementing +manageability of Tomcat.

+ +

The descriptions of JMX MBeans for Catalina are in the mbeans-descriptor.xml +file in each package.

+ +

You will need to add MBean descriptions for your custom components +in order to avoid a "ManagedBean is not found" exception.

+ +
+ +
+ +

You may also add MBean descriptions for custom components in +a mbeans-descriptor.xml file, located in the same package as the class files +it describes.

+ + + <mbean name="LDAPRealm" + className="org.apache.catalina.mbeans.ClassNameMBean" + description="Custom LDAPRealm" + domain="Catalina" + group="Realm" + type="com.myfirm.mypackage.LDAPRealm"> + + <attribute name="className" + description="Fully qualified class name of the managed object" + type="java.lang.String" + writeable="false"/> + + <attribute name="debug" + description="The debugging detail level for this component" + type="int"/> + . + . + . + + </mbean> + + + +
+ + + +
diff --git a/webapps/docs/monitoring.xml b/webapps/docs/monitoring.xml new file mode 100644 index 000000000000..017f658a3cbe --- /dev/null +++ b/webapps/docs/monitoring.xml @@ -0,0 +1,1130 @@ + + + +]> + + + &project; + + + Peter Rossbach + Remy Maucherat + Monitoring and Managing Tomcat + + + + +
+ +
+ +
+ +

Monitoring is a key aspect of system administration. Looking inside a + running server, obtaining some statistics or reconfiguring some aspects of + an application are all daily administration tasks.

+ +
+ +
+ +

The Sun website includes the list of options and how to configure JMX Remote on Java 5: + + http://download.oracle.com/javase/6/docs/technotes/guides/management/agent.html. +

+

The following is a quick configuration guide for Java 6:

+

Add the following parameters to your Tomcat startup script: + + set CATALINA_OPTS=-Dcom.sun.management.jmxremote \ + -Dcom.sun.management.jmxremote.port=%my.jmx.port% \ + -Dcom.sun.management.jmxremote.ssl=false \ + -Dcom.sun.management.jmxremote.authenticate=false + +

+

+

    +
  1. If you require authorization, add and change this : + + -Dcom.sun.management.jmxremote.authenticate=true \ + -Dcom.sun.management.jmxremote.password.file=../conf/jmxremote.password \ + -Dcom.sun.management.jmxremote.access.file=../conf/jmxremote.access \ + +
  2. +
  3. edit the access authorization file $CATALINA_BASE/conf/jmxremote.access : + +monitorRole readonly +controlRole readwrite + +
  4. +
  5. edit the password file $CATALINA_BASE/conf/jmxremote.password : + +monitorRole tomcat +controlRole tomcat + + Tip: The password file should be read-only and only accessible by the + operating system user Tomcat is running as. +
  6. +
+ Note:The JSR 160 JMX-Adaptor opens a second data channel on a random + port. That is a problem when you have a local firewall installed.
+

+ +
+ +
+

To simplify JMX usage with Ant 1.6.x, a set of tasks is provided that may + be used with antlib.

+

antlibCopy your catalina-ant.jar from $CATALINA_HOME/lib to $ANT_HOME/lib.

+

The following example shows the JMX Accessor usage:

+ + +

+<project name="Catalina Ant JMX" 
+        xmlns:jmx="antlib:org.apache.catalina.ant.jmx" 
+        default="state"
+        basedir=".">
+    <property name="jmx.server.name" value="localhost" />
+    <property name="jmx.server.port" value="9012" />
+    <property name="cluster.server.address" value="192.168.1.75" />
+    <property name="cluster.server.port" value="9025" />
+ 
+    <target name="state" description="Show JMX Cluster state">
+        <jmx:open
+            host="${jmx.server.name}"
+            port="${jmx.server.port}"
+            username="controlRole"
+            password="tomcat"/>
+        <jmx:get
+            name="Catalina:type=IDataSender,host=localhost,senderAddress=${cluster.server.address},senderPort=${cluster.server.port}" 
+            attribute="connected"
+            resultproperty="IDataSender.backup.connected"
+            echo="false"
+        />
+       <jmx:get
+            name="Catalina:type=ClusterSender,host=localhost" 
+            attribute="senderObjectNames"
+            resultproperty="senderObjectNames"
+            echo="false"
+        />
+        <!-- get current maxActiveSession from ClusterTest application
+             echo it to Ant output and store at 
+             property <em>clustertest.maxActiveSessions.orginal</em>
+        -->
+       <jmx:get
+            name="Catalina:type=Manager,path=/ClusterTest,host=localhost" 
+            attribute="maxActiveSessions"
+            resultproperty="clustertest.maxActiveSessions.orginal"
+            echo="true"
+        />
+        <!-- set maxActiveSession to 100
+        -->
+        <jmx:set
+            name="Catalina:type=Manager,path=/ClusterTest,host=localhost" 
+            attribute="maxActiveSessions"
+            value="100"
+            type="int"
+        />
+        <!-- get all sessions and split result as delimiter <em>SPACE</em> for easy
+             access all session ids directly with Ant property sessions.[0..n].
+        -->
+        <jmx:invoke
+            name="Catalina:type=Manager,path=/ClusterTest,host=localhost" 
+            operation="listSessionIds"
+            resultproperty="sessions"
+            echo="false"
+            delimiter=" "
+        />
+        <!-- Access session attribute <em>Hello</em> from first session.
+        -->
+        <jmx:invoke
+            name="Catalina:type=Manager,path=/ClusterTest,host=localhost" 
+            operation="getSessionAttribute"
+            resultproperty="Hello"
+            echo="false"
+        >
+          <arg value="${sessions.0}"/>
+          <arg value="Hello"/>
+        </jmx:invoke> 
+        <!-- Query for all application manager.of the server from all hosts
+             and bind all attributes from all found manager MBeans.
+        -->
+        <jmx:query
+            name="Catalina:type=Manager,*" 
+            resultproperty="manager"
+            echo="true"
+            attributebinding="true"
+        />
+        <!-- echo the create properties -->
+        <echo>
+           senderObjectNames: ${senderObjectNames.0}
+           IDataSender.backup.connected: ${IDataSender.backup.connected}
+           session: ${sessions.0}
+           manager.length: ${manager.length}
+           manager.0.name: ${manager.0.name}
+           manager.1.name: ${manager.1.name}
+           hello: ${Hello}
+           manager.ClusterTest.0.name: ${manager.ClusterTest.0.name}
+           manager.ClusterTest.0.activeSessions: ${manager.ClusterTest.0.activeSessions}
+           manager.ClusterTest.0.counterSend_EVT_SESSION_EXPIRED: ${manager.ClusterTest.0.counterSend_EVT_SESSION_EXPIRED}
+           manager.ClusterTest.0.counterSend_EVT_GET_ALL_SESSIONS: ${manager.ClusterTest.0.counterSend_EVT_GET_ALL_SESSIONS}
+        </echo>   
+
+    </target>
+ 
+</project>
+   

+
+

import: Import the JMX Accessor Project with + <import file="${CATALINA.HOME}/bin/catalina-tasks.xml" /> and + reference the tasks with jmxOpen, jmxSet, jmxGet, + jmxQuery, jmxInvoke,jmxEquals and jmxCondition.

+ +
+ + + +
+

+List of Attributes
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
AttributeDescriptionDefault value
urlSet JMX connection URL - service:jmx:rmi:///jndi/rmi://localhost:8050/jmxrmi +
hostSet the host, shortcut the very long URL syntax. + localhost
portSet the remote connection port + 8050
usernameremote JMX connection user name. +
passwordremote JMX connection password. +
refName of the internal connection reference. With this attribute you can + configure more the one connection inside the same Ant project. + jmx.server
echoEcho the command usage (for access analysis or debugging) + false
ifOnly execute if a property of the given name exists in the current project. +
unlessOnly execute if a property of the given name not exists in the current project. +
+

+

+Example to open a new JMX connection
+ + <jmx:open + host="${jmx.server.name}" + port="${jmx.server.port}" + /> + +

+

+Example to open a JMX connection from URL, with authorization and +store at other reference
+ + <jmx:open + url="service:jmx:rmi:///jndi/rmi://localhost:9024/jmxrmi" + ref="jmx.server.9024" + username="controlRole" + password="tomcat" + /> + +

+ +

+Example to open a JMX connection from URL, with authorization and +store at other reference, but only when property jmx.if exists and +jmx.unless not exists
+ + <jmx:open + url="service:jmx:rmi:///jndi/rmi://localhost:9024/jmxrmi" + ref="jmx.server.9024" + username="controlRole" + password="tomcat" + if="jmx.if" + unless="jmx.unless" + /> + +

+

Note: All properties from jmxOpen task also exists at all +other tasks and conditions. +

+ +
+ + + +
+

+List of Attributes
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
AttributeDescriptionDefault value
nameFull qualified JMX ObjectName -- Catalina:type=Server +
attributeExisting MBean attribute (see Tomcat MBean description above) +
refJMX Connection reference + jmx.server
echoEcho command usage (access and result) + false
resultpropertySave result at this project property +
delimiterSplit result with delimiter (java.util.StringTokenizier) + and use resultproperty as prefix to store tokens. +
separatearrayresultsWhen return value is an array, save result as property list + ($resultproperty.[0..N] and $resultproperty.length) + true
+

+

+Example to get remote MBean attribute from default JMX connection
+ + <jmx:get + name="Catalina:type=Manager,path=/servlets-examples,host=localhost" + attribute="maxActiveSessions" + resultproperty="servlets-examples.maxActiveSessions" + /> + +

+

+Example to get and result array and split it at separate properties
+ + <jmx:get + name="Catalina:type=ClusterSender,host=localhost" + attribute="senderObjectNames" + resultproperty="senderObjectNames" + /> + +Access the senderObjectNames properties with: + + ${senderObjectNames.length} give the number of returned sender list. + ${senderObjectNames.[0..N]} found all sender object names + +

+ +

+Example to get IDataSender attribute connected only when cluster is configured. + +<jmx:query + failonerror="false" + name="Catalina:type=Cluster,host=${tomcat.application.host}" + resultproperty="cluster" +/> +<jmx:get + name="Catalina:type=IDataSender,host=${tomcat.application.host},senderAddress=${cluster.backup.address},senderPort=${cluster.backup.port}" + attribute="connected" + resultproperty="datasender.connected" + if="cluster.0.name" /> + +

+ +
+ + + +
+

+List of Attributes
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
AttributeDescriptionDefault value
nameFull qualified JMX ObjectName -- Catalina:type=Server +
attributeExisting MBean attribute (see Tomcat MBean description above) +
valuevalue that set to attribute +
typetype of the attribute. + java.lang.String
refJMX Connection reference + jmx.server
echoEcho command usage (access and result) + false
+

+

+Example to set remote MBean attribute value
+ + <jmx:set + name="Catalina:type=Manager,path=/servlets-examples,host=localhost" + attribute="maxActiveSessions" + value="500" + type="int" + /> + +

+ +
+ + + +
+

+List of Attributes
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
AttributeDescriptionDefault value
nameFull qualified JMX ObjectName -- Catalina:type=Server +
operationExisting MBean operation (see Tomcat + funcspecs/fs-admin-opers.html). +
refJMX Connection reference + jmx.server
echoEcho command usage (access and result) + false
resultpropertySave result at this project property +
delimiterSplit result with delimiter (java.util.StringTokenizier) + and use resultproperty as prefix to store tokens. +
separatearrayresultsWhen return value is an array, save result as property list + ($resultproperty.[0..N] and $resultproperty.length) + true
+

+

+stop an application
+ + <jmx:invoke + name="Catalina:type=Manager,path=/servlets-examples,host=localhost" + operation="stop"/> + +Now you can find the sessionid at ${sessions.[0..N} properties and access the count +with ${sessions.length} property. +

+

+Example to get all sessionids
+ + <jmx:invoke + name="Catalina:type=Manager,path=/servlets-examples,host=localhost" + operation="listSessionIds" + resultproperty="sessions" + delimiter=" " + /> + +Now you can find the sessionid at ${sessions.[0..N} properties and access the count +with ${sessions.length} property. +

+

+Example to get remote MBean session attribute from session ${sessionid.0}
+ + <jmx:invoke + name="Catalina:type=Manager,path=/ClusterTest,host=localhost" + operation="getSessionAttribute" + resultproperty="hello"> + <arg value="${sessionid.0}"/> + <arg value="Hello" /> + </jmx:invoke> + +

+

+Example to create a new access logger valve at vhost localhost + + <jmx:invoke + name="Catalina:type=MBeanFactory" + operation="createAcccesLoggerValve" + resultproperty="acccesLoggerObjectName" + > + <arg value="Catalina:type=Host,host=localhost"/> + </jmx:invoke> + +Now you can find new MBean with name stored at ${acccesLoggerObjectName} +property. +

+ +
+ + + +
+

+List of Attributes
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
AttributeDescriptionDefault value
nameJMX ObjectName query string -- Catalina:type=Manager,* +
refJMX Connection reference + jmx.server
echoEcho command usage (access and result) + false
resultpropertyPrefix project property name to all founded MBeans (mbeans.[0..N].objectname) +
attributebinduingbind ALL MBean attributes in addition to name + false
delimiterSplit result with delimiter (java.util.StringTokenizier) + and use resultproperty as prefix to store tokens. +
separatearrayresultsWhen return value is an array, save result as property list + ($resultproperty.[0..N] and $resultproperty.length) + true
+

+

+Get all Manager ObjectNames from all services and Hosts
+ + <jmx:query + name="Catalina:type=Manager,* + resultproperty="manager" /> + +Now you can find the Session Manager at ${manager.[0..N].name} +properties and access the result object counter with ${manager.length} property. +

+

+Example to get the Manager from servlet-examples application an bind all MBean properties
+ + <jmx:query + name="Catalina:type=Manager,path=/servlet-examples,host=localhost*" + attributebinding="true" + resultproperty="manager.servletExamples" /> + +Now you can find the manager at ${manager.servletExamples.0.name} property +and can access all properties from this manager with ${manager.servletExamples.0.[manager attribute names]}. +The result object counter from MBeans is stored ad ${manager.length} property. +

+ +

+Example to get all MBeans from a server and store inside an external XML property file
+ +<project name="jmx.query" + xmlns:jmx="antlib:org.apache.catalina.ant.jmx" + default="query-all" basedir="."> +<property name="jmx.host" value="localhost"/> +<property name="jmx.port" value="8050"/> +<property name="jmx.username" value="controlRole"/> +<property name="jmx.password" value="tomcat"/> + +<target name="query-all" description="Query all MBeans of a server"> +<!-- Configure connection --> +<jmx:open + host="${jmx.host}" + port="${jmx.port}" + ref="jmx.server" + username="${jmx.username}" + password="${jmx.password}"/> +<!-- Query MBean list --> +<jmx:query + name="*:*" + resultproperty="mbeans" + attributebinding="false"/> + +<echoproperties + destfile="mbeans.properties" + prefix="mbeans." + format="xml"/> + +<!-- Print results --> +<echo + message="Number of MBeans in server ${jmx.host}:${jmx.port} is ${mbeans.length}"/> +</target> +</project> + +Now you can find all MBeans inside the file mbeans.properties. +

+ +
+ + + +
+

+List of Attributes
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
AttributeDescriptionDefault value
nameFull qualified JMX ObjectName -- Catalina:type=MBeanFactory +
classNameExisting MBean full qualified class name (see Tomcat MBean description above) +
classLoaderObjectName of server or web application classloader
+ ( Catalina:type=ServerClassLoader,name=[server,common,shared] or
+ Catalina:type=WebappClassLoader,path=/myapps,host=localhost) +
refJMX Connection reference + jmx.server
echoEcho command usage (access and result) + false
+

+

+Example to create remote MBean
+ + <jmx:create + ref="${jmx.reference}" + name="Catalina:type=MBeanFactory" + className="org.apache.commons.modeler.BaseModelMBean" + classLoader="Catalina:type=ServerClassLoader,name=server"> + <Arg value="org.apache.catalina.mbeans.MBeanFactory" /> + </jmx:create> + +

+

+ Warning: Many Tomcat MBeans can't be linked to their parent once
+ created. The Valve, Cluster and Realm MBeans are not automatically
+ connected with their parent. Use the MBeanFacrory create
+ operation instead. +

+ +
+ + + +
+

+List of Attributes
+ + + + + + + + + + + + + + + + + + + + + + + + + + +
AttributeDescriptionDefault value
nameFull qualified JMX ObjectName -- Catalina:type=MBeanFactory +
refJMX Connection reference + jmx.server
echoEcho command usage (access and result) + false
+

+

+Example to unregister remote MBean
+ + <jmx:unregister + name="Catalina:type=MBeanFactory" + /> + +

+

+ Warning: A lot of Tomcat MBeans can't be unregister.
+ The MBeans are not unlinked from their parent. Use MBeanFacrory
+ remove operation instead. +

+ +
+ + + +
+

+List of Attributes
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
AttributeDescriptionDefault value
urlSet JMX connection URL - service:jmx:rmi:///jndi/rmi://localhost:8050/jmxrmi +
hostSet the host, shortcut the very long URL syntax. + localhost
portSet the remote connection port + 8050
usernameremote JMX connection user name. +
passwordremote JMX connection password. +
refName of the internal connection reference. With this attribute you can + configure more the one connection inside the same Ant project. + jmx.server
nameFull qualified JMX ObjectName -- Catalina:type=Server +
echoEcho condition usage (access and result) + false
ifOnly execute if a property of the given name exists in the current project. +
unlessOnly execute if a property of the given name not exists in the current project. +
value (requiered)Second arg for operation +
typeValue type to express operation (support long and double) + long
operation express one +
    +
  • == equals
  • +
  • != not equals
  • +
  • > greater than (&gt;)
  • +
  • >= greater than or equals (&gt;=)
  • +
  • < lesser than (&lt;)
  • +
  • <= lesser than or equals (&lt;=)
  • +
+
==
+

+

+Wait for server connection and that cluster backup node is accessable
+ + <target name="wait"> + <waitfor maxwait="${maxwait}" maxwaitunit="second" timeoutproperty="server.timeout" > + <and> + <socket server="${server.name}" port="${server.port}"/> + <http url="${url}"/> + <jmx:condition + operation="==" + host="localhost" + port="9014" + username="controlRole" + password="tomcat" + name="Catalina:type=IDataSender,host=localhost,senderAddress=192.168.111.1,senderPort=9025" + attribute="connected" + value="true" + /> + </and> + </waitfor> + <fail if="server.timeout" message="Server ${url} don't answer inside ${maxwait} sec" /> + <echo message="Server ${url} alive" /> + </target> + +

+ +
+ + + +
+

+List of Attributes
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
AttributeDescriptionDefault value
urlSet JMX connection URL - service:jmx:rmi:///jndi/rmi://localhost:8050/jmxrmi +
hostSet the host, shortcut the very long URL syntax. + localhost
portSet the remote connection port + 8050
usernameremote JMX connection user name. +
passwordremote JMX connection password. +
refName of the internal connection reference. With this attribute you can + configure more the one connection inside the same Ant project. + jmx.server
nameFull qualified JMX ObjectName -- Catalina:type=Server +
echoEcho condition usage (access and result) + false
+

+

+Wait for server connection and that cluster backup node is accessible
+ + <target name="wait"> + <waitfor maxwait="${maxwait}" maxwaitunit="second" timeoutproperty="server.timeout" > + <and> + <socket server="${server.name}" port="${server.port}"/> + <http url="${url}"/> + <jmx:equals + host="localhost" + port="9014" + username="controlRole" + password="tomcat" + name="Catalina:type=IDataSender,host=localhost,senderAddress=192.168.111.1,senderPort=9025" + attribute="connected" + value="true" + /> + </and> + </waitfor> + <fail if="server.timeout" message="Server ${url} don't answer inside ${maxwait} sec" /> + <echo message="Server ${url} alive" /> + </target> + +

+ +
+ + +
diff --git a/webapps/docs/project.xml b/webapps/docs/project.xml new file mode 100644 index 000000000000..56ea43669b21 --- /dev/null +++ b/webapps/docs/project.xml @@ -0,0 +1,94 @@ + + + + + Apache Tomcat 7 + + + The Apache Tomcat Servlet/JSP Container + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/webapps/docs/proxy-howto.xml b/webapps/docs/proxy-howto.xml new file mode 100644 index 000000000000..4fb39fb7da48 --- /dev/null +++ b/webapps/docs/proxy-howto.xml @@ -0,0 +1,155 @@ + + + +]> + + + &project; + + + Craig R. McClanahan + Proxy Support HOW-TO + + + + +
+ +
+ +
+ +

Using standard configurations of Tomcat, web applications can ask for +the server name and port number to which the request was directed for +processing. When Tomcat is running standalone with the +Coyote HTTP/1.1 Connector, it will generally +report the server name specified in the request, and the port number on +which the Connector is listening. The servlet API +calls of interest, for this purpose, are:

+
    +
  • ServletRequest.getServerName(): Returns the host name of the server to which the request was sent.
  • +
  • ServletRequest.getServerPort(): Returns the host name of the server to which the request was sent.
  • +
  • ServletRequest.getLocalName(): Returns the host name of the Internet Protocol (IP) interface on which the request was received.
  • +
  • ServletRequest.getLocalPort(): Returns the Internet Protocol (IP) port number of the interface on which the request was received.
  • +
+ +

When you are running behind a proxy server (or a web server that is +configured to behave like a proxy server), you will sometimes prefer to +manage the values returned by these calls. In particular, you will +generally want the port number to reflect that specified in the original +request, not the one on which the Connector itself is +listening. You can use the proxyName and proxyPort +attributes on the <Connector> element to configure +these values.

+ +

Proxy support can take many forms. The following sections describe +proxy configurations for several common cases.

+ +
+ +
+ +

Apache 1.3 supports an optional module (mod_proxy) that +configures the web server to act as a proxy server. This can be used to +forward requests for a particular web application to a Tomcat instance, +without having to configure a web connector such as mod_jk. +To accomplish this, you need to perform the following tasks:

+
    +
  1. Configure your copy of Apache so that it includes the + mod_proxy module. If you are building from source, + the easiest way to do this is to include the + --enable-module=proxy directive on the + ./configure command line.
  2. +
  3. If not already added for you, make sure that you are loading the + mod_proxy module at Apache startup time, by using the + following directives in your httpd.conf file: + +LoadModule proxy_module {path-to-modules}/mod_proxy.so +AddModule mod_proxy.c +
  4. +
  5. Include two directives in your httpd.conf file for + each web application that you wish to forward to Tomcat. For + example, to forward an application at context path /myapp: + +ProxyPass /myapp http://localhost:8081/myapp +ProxyPassReverse /myapp http://localhost:8081/myapp + + which tells Apache to forward URLs of the form + http://localhost/myapp/* to the Tomcat connector + listening on port 8081.
  6. +
  7. Configure your copy of Tomcat to include a special + <Connector> element, with appropriate + proxy settings, for example: + +<Connector port="8081" ... + proxyName="www.mycompany.com" + proxyPort="80"/> + + which will cause servlets inside this web application to think that + all proxied requests were directed to www.mycompany.com + on port 80.
  8. +
  9. It is legal to omit the proxyName attribute from the + <Connector> element. If you do so, the value + returned by request.getServerName() will by the host + name on which Tomcat is running. In the example above, it would be + localhost.
  10. +
  11. If you also have a <Connector> listening on port + 8080 (nested within the same Service + element), the requests to either port will share the same set of + virtual hosts and web applications.
  12. +
  13. You might wish to use the IP filtering features of your operating + system to restrict connections to port 8081 (in this example) to + be allowed only from the server that is running + Apache.
  14. +
  15. Alternatively, you can set up a series of web applications that are + only available via proxying, as follows: +
      +
    • Configure another <Service> that contains + only a <Connector> for the proxy port.
    • +
    • Configure appropriate Engine, + Host, and + Context elements for the virtual hosts + and web applications accessible via proxying.
    • +
    • Optionally, protect port 8081 with IP filters as described + earlier.
    • +
  16. +
  17. When requests are proxied by Apache, the web server will be recording + these requests in its access log. Therefore, you will generally want to + disable any access logging performed by Tomcat itself.
  18. +
+ +

When requests are proxied in this manner, all requests +for the configured web applications will be processed by Tomcat (including +requests for static content). You can improve performance by using the +mod_jk web connector instead of mod_proxy. +mod_jk can be configured so that the web server serves static +content that is not processed by filters or security constraints defined +within the web application's deployment descriptor +(/WEB-INF/web.xml).

+ +
+ +
+The same instructions hold true as for 1.3. (Except in Apache 2.0, +you may omit AddModule mod_proxy.c) +
+ + + +
diff --git a/webapps/docs/realm-howto.xml b/webapps/docs/realm-howto.xml new file mode 100644 index 000000000000..f17590b019ce --- /dev/null +++ b/webapps/docs/realm-howto.xml @@ -0,0 +1,1232 @@ + + + +]> + + + &project; + + + Craig R. McClanahan + Yoav Shapira + Andrew R. Jaquith + Realm Configuration HOW-TO + + + + +
+ +
+ +
+ +

This document describes how to configure Tomcat to support container +managed security, by connecting to an existing "database" of usernames, +passwords, and user roles. You only need to care about this if you are using +a web application that includes one or more +<security-constraint> elements, and a +<login-config> element defining how users are required +to authenticate themselves. If you are not utilizing these features, you can +safely skip this document.

+ +

For fundamental background information about container managed security, +see the Servlet +Specification (Version 2.4), Section 12.

+ +

For information about utilizing the Single Sign On feature of +Tomcat (allowing a user to authenticate themselves once across the entire +set of web applications associated with a virtual host), see +here.

+ +
+ + +
+ + + + +

A Realm is a "database" of usernames and passwords that +identify valid users of a web application (or set of web applications), plus +an enumeration of the list of roles associated with each valid user. +You can think of roles as similar to groups in Unix-like operating +systems, because access to specific web application resources is granted to +all users possessing a particular role (rather than enumerating the list of +associated usernames). A particular user can have any number of roles +associated with their username.

+ +

Although the Servlet Specification describes a portable mechanism for +applications to declare their security requirements (in the +web.xml deployment descriptor), there is no portable API +defining the interface between a servlet container and the associated user +and role information. In many cases, however, it is desirable to "connect" +a servlet container to some existing authentication database or mechanism +that already exists in the production environment. Therefore, Tomcat +defines a Java interface (org.apache.catalina.Realm) that +can be implemented by "plug in" components to establish this connection. +Five standard plug-ins are provided, supporting connections to various +sources of authentication information:

+
    +
  • JDBCRealm - Accesses authentication information + stored in a relational database, accessed via a JDBC driver.
  • +
  • DataSourceRealm - Accesses authentication + information stored in a relational database, accessed via a named JNDI + JDBC DataSource.
  • +
  • JNDIRealm - Accesses authentication information + stored in an LDAP based directory server, accessed via a JNDI provider. +
  • +
  • UserDatabaseRealm - Accesses authentication + information stored in an UserDatabase JNDI resource, which is typically + backed by an XML document (conf/tomcat-users.xml).
  • +
  • MemoryRealm - Accesses authentication + information stored in an in-memory object collection, which is initialized + from an XML document (conf/tomcat-users.xml).
  • +
  • JAASRealm - Accesses authentication information + through the Java Authentication & Authorization Service (JAAS) + framework.
  • +
+ +

It is also possible to write your own Realm implementation, +and integrate it with Tomcat. To do so, you need to: +

    +
  • Implement org.apache.catalina.Realm,
  • +
  • Place your compiled realm in $CATALINA_HOME/lib,
  • +
  • Declare your realm as described in the "Configuring a Realm" section below,
  • +
  • Declare your realm to the MBeans Descriptor.
  • +
+

+ +
+ + + + +

Before getting into the details of the standard Realm implementations, it is +important to understand, in general terms, how a Realm is configured. In +general, you will be adding an XML element to your conf/server.xml +configuration file, that looks something like this:

+ + +<Realm className="... class name for this implementation" + ... other attributes for this implementation .../> + + +

The <Realm> element can be nested inside any one of +of the following Container elements. The location of the +Realm element has a direct impact on the "scope" of that Realm +(i.e. which web applications will share the same authentication information): +

+
    +
  • Inside an <Engine> element - This Realm will be shared + across ALL web applications on ALL virtual hosts, UNLESS it is overridden + by a Realm element nested inside a subordinate <Host> + or <Context> element.
  • +
  • Inside a <Host> element - This Realm will be shared across + ALL web applications for THIS virtual host, UNLESS it is overridden + by a Realm element nested inside a subordinate <Context> + element.
  • +
  • Inside a <Context> element - This Realm will be used ONLY + for THIS web application.
  • +
+ + +
+ + +
+ + +
+ + + + +

For each of the standard Realm implementations, the +user's password (by default) is stored in clear text. In many +environments, this is undesirable because casual observers of the +authentication data can collect enough information to log on +successfully, and impersonate other users. To avoid this problem, the +standard implementations support the concept of digesting +user passwords. This allows the stored version of the passwords to be +encoded (in a form that is not easily reversible), but that the +Realm implementation can still utilize for +authentication.

+ +

When a standard realm authenticates by retrieving the stored +password and comparing it with the value presented by the user, you +can select digested passwords by specifying the digest +attribute on your <Realm> element. The value for +this attribute must be one of the digest algorithms supported by the +java.security.MessageDigest class (SHA, MD2, or MD5). +When you select this option, the contents of the password that is +stored in the Realm must be the cleartext version of the +password, as digested by the specified algorithm.

+ +

When the authenticate() method of the Realm is called, the +(cleartext) password specified by the user is itself digested by the same +algorithm, and the result is compared with the value returned by the +Realm. An equal match implies that the cleartext version of the +original password is the same as the one presented by the user, so that this +user should be authorized.

+ +

To calculate the digested value of a cleartext password, two convenience +techniques are supported:

+
    +
  • If you are writing an application that needs to calculate digested + passwords dynamically, call the static Digest() method of the + org.apache.catalina.realm.RealmBase class, passing the + cleartext password and the digest algorithm name as arguments. This + method will return the digested password.
  • +
  • If you want to execute a command line utility to calculate the digested + password, simply execute + +java org.apache.catalina.realm.RealmBase \ + -a {algorithm} {cleartext-password} + + and the digested version of this cleartext password will be returned to + standard output.
  • +
+ +

If using digested passwords with DIGEST authentication, the cleartext used + to generate the digest is different. In the examples above + {cleartext-password} must be replaced with + {username}:{realm}:{cleartext-password}. For example, in a + development environment this might take the form + testUser:Authentication required:testPassword. The value for + {realm} is taken from the <realm-name> + element of the web application's <login-config>. If + not specified in web.xml, the default value of Authentication + required is used.

+ +

To use either of the above techniques, the +$CATALINA_HOME/lib/catalina.jar and +$CATALINA_HOME/bin/tomcat-juli.jar files will need to be +on your class path to make the RealmBase class available. +

+ +

Non-ASCII usernames and/or passwords are supported using +java org.apache.catalina.realm.RealmBase \ + -a {algorithm} -e {encoding} {input} + +but care is required to ensure that the non-ASCII input is +correctly passed to the digester. +The digester returns {input}:{digest}. If the input appears +corrupted in the return, the digest will be invalid.

+ +
+ + + + + +

The example application shipped with Tomcat includes an area that is +protected by a security constraint, utilizing form-based login. To access it, +point your browser at +http://localhost:8080/examples/jsp/security/protected/ +and log on with one of the usernames and passwords described for the default +UserDatabaseRealm.

+ +
+ + + + +

If you wish to use the Manager Application +to deploy and undeploy applications in a running Tomcat installation, you +MUST add the "manager" role to at least one username in your selected Realm +implementation. This is because the manager web application itself uses a +security constraint that requires role "manager" to access ANY request URI +within that application.

+ +

For security reasons, no username in the default Realm (i.e. using +conf/tomcat-users.xml is assigned the "manager" role. Therefore, +no one will be able to utilize the features of this application until the +Tomcat administrator specifically assigns this role to one or more users.

+ +
+ + + +

Debugging and exception messages logged by a Realm will + be recorded by the logging configuration associated with the container + for the realm: its surrounding Context, + Host, or + Engine.

+ +
+ +
+ + +
+ + + +

Introduction

+ +

JDBCRealm is an implementation of the Tomcat +Realm interface that looks up users in a relational database +accessed via a JDBC driver. There is substantial configuration flexibility +that lets you adapt to existing table and column names, as long as your +database structure conforms to the following requirements:

+
    +
  • There must be a table, referenced below as the users table, + that contains one row for every valid user that this Realm + should recognize.
  • +
  • The users table must contain at least two columns (it may + contain more if your existing applications required it): +
      +
    • Username to be recognized by Tomcat when the user logs in.
    • +
    • Password to be recognized by Tomcat when the user logs in. + This value may in cleartext or digested - see below for more + information.
    • +
  • +
  • There must be a table, referenced below as the user roles table, + that contains one row for every valid role that is assigned to a + particular user. It is legal for a user to have zero, one, or more than + one valid role.
  • +
  • The user roles table must contain at least two columns (it may + contain more if your existing applications required it): +
      +
    • Username to be recognized by Tomcat (same value as is specified + in the users table).
    • +
    • Role name of a valid role associated with this user.
    • +
  • +
+ +

Quick Start

+ +

To set up Tomcat to use JDBCRealm, you will need to follow these steps:

+
    +
  1. If you have not yet done so, create tables and columns in your database + that conform to the requirements described above.
  2. +
  3. Configure a database username and password for use by Tomcat, that has + at least read only access to the tables described above. (Tomcat will + never attempt to write to these tables.)
  4. +
  5. Place a copy of the JDBC driver you will be using inside the + $CATALINA_HOME/lib directory. + Note that only JAR files are recognized!
  6. +
  7. Set up a <Realm> element, as described below, in your + $CATALINA_BASE/conf/server.xml file.
  8. +
  9. Restart Tomcat if it is already running.
  10. +
+ +

Realm Element Attributes

+ +

To configure JDBCRealm, you will create a <Realm> +element and nest it in your $CATALINA_BASE/conf/server.xml file, +as described above. The attributes for the +JDBCRealm are defined in the Realm configuration +documentation.

+ +

Example

+ +

An example SQL script to create the needed tables might look something +like this (adapt the syntax as required for your particular database):

+ +create table users ( + user_name varchar(15) not null primary key, + user_pass varchar(15) not null +); + +create table user_roles ( + user_name varchar(15) not null, + role_name varchar(15) not null, + primary key (user_name, role_name) +); + + +

Example Realm elements are included (commented out) in the +default $CATALINA_BASE/conf/server.xml file. Here's an example +for using a MySQL database called "authority", configured with the tables +described above, and accessed with username "dbuser" and password "dbpass":

+ +<Realm className="org.apache.catalina.realm.JDBCRealm" debug="99" + driverName="org.gjt.mm.mysql.Driver" + connectionURL="jdbc:mysql://localhost/authority?user=dbuser&amp;password=dbpass" + userTable="users" userNameCol="user_name" userCredCol="user_pass" + userRoleTable="user_roles" roleNameCol="role_name"/> + + +

Additional Notes

+ +

JDBCRealm operates according to the following rules:

+
    +
  • When a user attempts to access a protected resource for the first time, + Tomcat will call the authenticate() method of this + Realm. Thus, any changes you have made to the database + directly (new users, changed passwords or roles, etc.) will be immediately + reflected.
  • +
  • Once a user has been authenticated, the user (and his or her associated + roles) are cached within Tomcat for the duration of the user's login. + (For FORM-based authentication, that means until the session times out or + is invalidated; for BASIC authentication, that means until the user + closes their browser). The cached user is not saved and + restored across sessions serialisations. Any changes to the database + information for an already authenticated user will not be + reflected until the next time that user logs on again.
  • +
  • Administering the information in the users and user roles + table is the responsibility of your own applications. Tomcat does not + provide any built-in capabilities to maintain users and roles.
  • +
+ +
+ + + + +

Introduction

+ +

DataSourceRealm is an implementation of the Tomcat +Realm interface that looks up users in a relational database +accessed via a JNDI named JDBC DataSource. There is substantial configuration +flexibility that lets you adapt to existing table and column names, as long +as your database structure conforms to the following requirements:

+
    +
  • There must be a table, referenced below as the users table, + that contains one row for every valid user that this Realm + should recognize.
  • +
  • The users table must contain at least two columns (it may + contain more if your existing applications required it): +
      +
    • Username to be recognized by Tomcat when the user logs in.
    • +
    • Password to be recognized by Tomcat when the user logs in. + This value may in cleartext or digested - see below for more + information.
    • +
  • +
  • There must be a table, referenced below as the user roles table, + that contains one row for every valid role that is assigned to a + particular user. It is legal for a user to have zero, one, or more than + one valid role.
  • +
  • The user roles table must contain at least two columns (it may + contain more if your existing applications required it): +
      +
    • Username to be recognized by Tomcat (same value as is specified + in the users table).
    • +
    • Role name of a valid role associated with this user.
    • +
  • +
+ +

Quick Start

+ +

To set up Tomcat to use DataSourceRealm, you will need to follow these steps:

+
    +
  1. If you have not yet done so, create tables and columns in your database + that conform to the requirements described above.
  2. +
  3. Configure a database username and password for use by Tomcat, that has + at least read only access to the tables described above. (Tomcat will + never attempt to write to these tables.)
  4. +
  5. Configure a JNDI named JDBC DataSource for your database. Refer to the + JNDI DataSource Example HOW-TO + for information on how to configure a JNDI named JDBC DataSource.
  6. +
  7. Set up a <Realm> element, as described below, in your + $CATALINA_BASE/conf/server.xml file.
  8. +
  9. Restart Tomcat if it is already running.
  10. +
+ +

Realm Element Attributes

+ +

To configure DataSourceRealm, you will create a <Realm> +element and nest it in your $CATALINA_BASE/conf/server.xml file, +as described above. The attributes for the +DataSourceRealm are defined in the Realm +configuration documentation.

+ +

Example

+ +

An example SQL script to create the needed tables might look something +like this (adapt the syntax as required for your particular database):

+ +create table users ( + user_name varchar(15) not null primary key, + user_pass varchar(15) not null +); + +create table user_roles ( + user_name varchar(15) not null, + role_name varchar(15) not null, + primary key (user_name, role_name) +); + + +

Here is an example for using a MySQL database called "authority", configured +with the tables described above, and accessed with the JNDI JDBC DataSource with +name "java:/comp/env/jdbc/authority".

+ +<Realm className="org.apache.catalina.realm.DataSourceRealm" debug="99" + dataSourceName="jdbc/authority" + userTable="users" userNameCol="user_name" userCredCol="user_pass" + userRoleTable="user_roles" roleNameCol="role_name"/> + + +

Additional Notes

+ +

DataSourceRealm operates according to the following rules:

+
    +
  • When a user attempts to access a protected resource for the first time, + Tomcat will call the authenticate() method of this + Realm. Thus, any changes you have made to the database + directly (new users, changed passwords or roles, etc.) will be immediately + reflected.
  • +
  • Once a user has been authenticated, the user (and his or her associated + roles) are cached within Tomcat for the duration of the user's login. + (For FORM-based authentication, that means until the session times out or + is invalidated; for BASIC authentication, that means until the user + closes their browser). The cached user is not saved and + restored across sessions serialisations. Any changes to the database + information for an already authenticated user will not be + reflected until the next time that user logs on again.
  • +
  • Administering the information in the users and user roles + table is the responsibility of your own applications. Tomcat does not + provide any built-in capabilities to maintain users and roles.
  • +
+ +
+ + + + +

Introduction

+ +

JNDIRealm is an implementation of the Tomcat +Realm interface that looks up users in an LDAP directory +server accessed by a JNDI provider (typically, the standard LDAP +provider that is available with the JNDI API classes). The realm +supports a variety of approaches to using a directory for +authentication.

+ +

Connecting to the directory

+ +

The realm's connection to the directory is defined by the +connectionURL configuration attribute. This is a URL +whose format is defined by the JNDI provider. It is usually an LDAP +URL that specifies the domain name of the directory server to connect +to, and optionally the port number and distinguished name (DN) of the +required root naming context.

+ +

If you have more than one provider you can configure an +alternateURL. If a socket connection can not be +made to the provider at the connectionURL an +attempt will be made to use the alternateURL.

+ +

When making a connection in order to search the directory and +retrieve user and role information, the realm authenticates itself to +the directory with the username and password specified by the +connectionName and +connectionPassword properties. If these properties +are not specified the connection is anonymous. This is sufficient in +many cases. +

+ + +

Selecting the user's directory entry

+ +

Each user that can be authenticated must be represented in the +directory by an individual entry that corresponds to an element in the +initial DirContext defined by the +connectionURL attribute. This user entry must have an +attribute containing the username that is presented for +authentication.

+ +

Often the distinguished name of the user's entry contains the +username presented for authentication but is otherwise the same for +all users. In this case the userPattern attribute may +be used to specify the DN, with "{0}" marking where +the username should be substituted.

+ +

Otherwise the realm must search the directory to find a unique entry +containing the username. The following attributes configure this +search: + +

    +
  • userBase - the entry that is the base of + the subtree containing users. If not specified, the search + base is the top-level context.
  • + +
  • userSubtree - the search scope. Set to + true if you wish to search the entire subtree + rooted at the userBase entry. The default value + of false requests a single-level search + including only the top level.
  • + +
  • userSearch - pattern specifying the LDAP + search filter to use after substitution of the username.
  • + +
+

+ + +

Authenticating the user

+ +
    +
  • +

    Bind mode

    + +

    By default the realm authenticates a user by binding to +the directory with the DN of the entry for that user and the password +presented by the user. If this simple bind succeeds the user is considered to +be authenticated.

    + +

    For security reasons a directory may store a digest of the user's +password rather than the clear text version (see Digested Passwords for more information). In that case, +as part of the simple bind operation the directory automatically +computes the correct digest of the plaintext password presented by the +user before validating it against the stored value. In bind mode, +therefore, the realm is not involved in digest processing. The +digest attribute is not used, and will be ignored if +set.

    +
  • + +
  • +

    Comparison mode

    +

    Alternatively, the realm may retrieve the stored +password from the directory and compare it explicitly with the value +presented by the user. This mode is configured by setting the +userPassword attribute to the name of a directory +attribute in the user's entry that contains the password.

    + +

    Comparison mode has some disadvantages. First, the +connectionName and +connectionPassword attributes must be configured to +allow the realm to read users' passwords in the directory. For +security reasons this is generally undesirable; indeed many directory +implementations will not allow even the directory manager to read +these passwords. In addition, the realm must handle password digests +itself, including variations in the algorithms used and ways of +representing password hashes in the directory. However, the realm may +sometimes need access to the stored password, for example to support +HTTP Digest Access Authentication (RFC 2069). (Note that HTTP digest +authentication is different from the storage of password digests in +the repository for user information as discussed above). +

    +
  • +
+ +

Assigning roles to the user

+ +

The directory realm supports two approaches to the representation +of roles in the directory:

+ +
    +
  • +

    Roles as explicit directory entries

    + +

    Roles may be represented by explicit directory entries. A role +entry is usually an LDAP group entry with one attribute +containing the name of the role and another whose values are the +distinguished names or usernames of the users in that role. The +following attributes configure a directory search to +find the names of roles associated with the authenticated user:

    + +
      +
    • roleBase - the base entry for the role search. + If not specified, the search base is the top-level directory + context.
    • + +
    • roleSubtree - the search + scope. Set to true if you wish to search the entire + subtree rooted at the roleBase entry. The default + value of false requests a single-level search + including the top level only.
    • + +
    • roleSearch - the LDAP search filter for + selecting role entries. It optionally includes pattern + replacements "{0}" for the distinguished name and/or "{1}" for the + username of the authenticated user.
    • + +
    • roleName - the attribute in a role entry + containing the name of that role.
    • + +
    • roleNested - enable nested roles. Set to + true if you want to nest roles in roles. If configured + every newly found roleName and distinguished + Name will be recursively tried for a new role search. + The default value is false.
    • + +
    + +
  • +
+ +
    +
  • +

    Roles as an attribute of the user entry

    + +

    Role names may also be held as the values of an attribute in the +user's directory entry. Use userRoleName to specify +the name of this attribute.

    + +
  • +
+

A combination of both approaches to role representation may be used.

+ +

Quick Start

+ +

To set up Tomcat to use JNDIRealm, you will need to follow these steps:

+
    +
  1. Make sure your directory server is configured with a schema that matches + the requirements listed above.
  2. +
  3. If required, configure a username and password for use by Tomcat, that has + read only access to the information described above. (Tomcat will + never attempt to modify this information.)
  4. +
  5. Place a copy of the JNDI driver you will be using (typically + ldap.jar available with JNDI) inside the + $CATALINA_HOME/lib directory.
  6. +
  7. Set up a <Realm> element, as described below, in your + $CATALINA_BASE/conf/server.xml file.
  8. +
  9. Restart Tomcat if it is already running.
  10. +
+ +

Realm Element Attributes

+ +

To configure JNDIRealm, you will create a <Realm> +element and nest it in your $CATALINA_BASE/conf/server.xml file, +as described above. The attributes for the +JNDIRealm are defined in the Realm configuration +documentation.

+ +

Example

+ +

Creation of the appropriate schema in your directory server is beyond the +scope of this document, because it is unique to each directory server +implementation. In the examples below, we will assume that you are using a +distribution of the OpenLDAP directory server (version 2.0.11 or later), which +can be downloaded from +http://www.openldap.org. Assume that +your slapd.conf file contains the following settings +(among others):

+ +database ldbm +suffix dc="mycompany",dc="com" +rootdn "cn=Manager,dc=mycompany,dc=com" +rootpw secret + + +

We will assume for connectionURL that the directory +server runs on the same machine as Tomcat. See http://java.sun.com/products/jndi/docs.html +for more information about configuring and using the JNDI LDAP +provider.

+ +

Next, assume that this directory server has been populated with elements +as shown below (in LDIF format):

+ + + +# Define top-level entry +dn: dc=mycompany,dc=com +objectClass: dcObject +dc:mycompany + +# Define an entry to contain people +# searches for users are based on this entry +dn: ou=people,dc=mycompany,dc=com +objectClass: organizationalUnit +ou: people + +# Define a user entry for Janet Jones +dn: uid=jjones,ou=people,dc=mycompany,dc=com +objectClass: inetOrgPerson +uid: jjones +sn: jones +cn: janet jones +mail: j.jones@mycompany.com +userPassword: janet + +# Define a user entry for Fred Bloggs +dn: uid=fbloggs,ou=people,dc=mycompany,dc=com +objectClass: inetOrgPerson +uid: fbloggs +sn: bloggs +cn: fred bloggs +mail: f.bloggs@mycompany.com +userPassword: fred + +# Define an entry to contain LDAP groups +# searches for roles are based on this entry +dn: ou=groups,dc=mycompany,dc=com +objectClass: organizationalUnit +ou: groups + +# Define an entry for the "tomcat" role +dn: cn=tomcat,ou=groups,dc=mycompany,dc=com +objectClass: groupOfUniqueNames +cn: tomcat +uniqueMember: uid=jjones,ou=people,dc=mycompany,dc=com +uniqueMember: uid=fbloggs,ou=people,dc=mycompany,dc=com + +# Define an entry for the "role1" role +dn: cn=role1,ou=groups,dc=mycompany,dc=com +objectClass: groupOfUniqueNames +cn: role1 +uniqueMember: uid=fbloggs,ou=people,dc=mycompany,dc=com + + +

An example Realm element for the OpenLDAP directory +server configured as described above might look like this, assuming +that users use their uid (e.g. jjones) to login to the +application and that an anonymous connection is sufficient to search +the directory and retrieve role information:

+ + +<Realm className="org.apache.catalina.realm.JNDIRealm" debug="99" + connectionURL="ldap://localhost:389" + userPattern="uid={0},ou=people,dc=mycompany,dc=com" + roleBase="ou=groups,dc=mycompany,dc=com" + roleName="cn" + roleSearch="(uniqueMember={0})" +/> + + +

With this configuration, the realm will determine the user's +distinguished name by substituting the username into the +userPattern, authenticate by binding to the directory +with this DN and the password received from the user, and search the +directory to find the user's roles.

+ +

Now suppose that users are expected to enter their email address +rather than their userid when logging in. In this case the realm must +search the directory for the user's entry. (A search is also necessary +when user entries are held in multiple subtrees corresponding perhaps +to different organizational units or company locations).

+ +

Further, suppose that in addition to the group entries you want to +use an attribute of the user's entry to hold roles. Now the entry for +Janet Jones might read as follows:

+ + +dn: uid=jjones,ou=people,dc=mycompany,dc=com +objectClass: inetOrgPerson +uid: jjones +sn: jones +cn: janet jones +mail: j.jones@mycompany.com +memberOf: role2 +memberOf: role3 +userPassword: janet + + +

This realm configuration would satisfy the new requirements:

+ + +<Realm className="org.apache.catalina.realm.JNDIRealm" debug="99" + connectionURL="ldap://localhost:389" + userBase="ou=people,dc=mycompany,dc=com" + userSearch="(mail={0})" + userRoleName="memberOf" + roleBase="ou=groups,dc=mycompany,dc=com" + roleName="cn" + roleSearch="(uniqueMember={0})" +/> + + +

Now when Janet Jones logs in as "j.jones@mycompany.com", the realm +searches the directory for a unique entry with that value as its mail +attribute and attempts to bind to the directory as +uid=jjones,ou=people,dc=mycompany,dc=com with the given +password. If authentication succeeds, she is assigned three roles: +"role2" and "role3", the values of the "memberOf" attribute in her +directory entry, and "tomcat", the value of the "cn" attribute in the +only group entry of which she is a member.

+ +

Finally, to authenticate the user by retrieving +the password from the directory and making a local comparison in the +realm, you might use a realm configuration like this:

+ + +<Realm className="org.apache.catalina.realm.JNDIRealm" debug="99" + connectionName="cn=Manager,dc=mycompany,dc=com" +connectionPassword="secret" + connectionURL="ldap://localhost:389" + userPassword="userPassword" + userPattern="uid={0},ou=people,dc=mycompany,dc=com" + roleBase="ou=groups,dc=mycompany,dc=com" + roleName="cn" + roleSearch="(uniqueMember={0})" +/> + + +

However, as discussed above, the default bind mode for +authentication is usually to be preferred.

+ +

Additional Notes

+ +

JNDIRealm operates according to the following rules:

+
    +
  • When a user attempts to access a protected resource for the first time, + Tomcat will call the authenticate() method of this + Realm. Thus, any changes you have made to the directory + (new users, changed passwords or roles, etc.) will be immediately + reflected.
  • +
  • Once a user has been authenticated, the user (and his or her associated + roles) are cached within Tomcat for the duration of the user's login. + (For FORM-based authentication, that means until the session times out or + is invalidated; for BASIC authentication, that means until the user + closes their browser). The cached user is not saved and + restored across sessions serialisations. Any changes to the directory + information for an already authenticated user will not be + reflected until the next time that user logs on again.
  • +
  • Administering the information in the directory server + is the responsibility of your own applications. Tomcat does not + provide any built-in capabilities to maintain users and roles.
  • +
+ +
+ + + + +

Introduction

+ +

UserDatabaseRealm is an implementation of the Tomcat +Realm interface that uses a JNDI resource to store user +information. By default, the JNDI resource is backed by an XML file. It is not +designed for large-scale production use. At startup time, the UserDatabaseRealm +loads information about all users, and their corresponding roles, from an XML +document (by default, this document is loaded from +$CATALINA_BASE/conf/tomcat-users.xml). The users, their passwords +and their roles may all be editing dynamically, typically via JMX. Changes may +be saved and will be reflected in the XMl file.

+ +

Realm Element Attributes

+ +

To configure UserDatabaseRealm, you will create a <Realm> +element and nest it in your $CATALINA_BASE/conf/server.xml file, +as described above. The attributes for the +UserDatabaseRealm are defined in the Realm +configuration documentation.

+ +

User File Format

+ +

The users file uses the same format as the +MemoryRealm.

+ +

Example

+ +

The default installation of Tomcat is configured with a UserDatabaseRealm +nested inside the <Engine> element, so that it applies +to all virtual hosts and web applications. The default contents of the +conf/tomcat-users.xml file is:

+ +<tomcat-users> + <user name="tomcat" password="tomcat" roles="tomcat" /> + <user name="role1" password="tomcat" roles="role1" /> + <user name="both" password="tomcat" roles="tomcat,role1" /> +</tomcat-users> + + +

Additional Notes

+ +

UserDatabaseRealm operates according to the following rules:

+
    +
  • When Tomcat first starts up, it loads all defined users and their + associated information from the users file. Changes made to the data in + this file will not be recognized until Tomcat is + restarted. Changes may be made via the UserDatabase resource. Tomcat + provides MBeans that may be accessed via JMX for this purpose.
  • +
  • When a user attempts to access a protected resource for the first time, + Tomcat will call the authenticate() method of this + Realm.
  • +
  • Once a user has been authenticated, the user (and his or her associated + roles) are cached within Tomcat for the duration of the user's login. + (For FORM-based authentication, that means until the session times out or + is invalidated; for BASIC authentication, that means until the user + closes their browser). The cached user is not saved and + restored across sessions serialisations.
  • +
+ + +
+ + + + +

Introduction

+ +

MemoryRealm is a simple demonstration implementation of the +Tomcat Realm interface. It is not designed for production use. +At startup time, MemoryRealm loads information about all users, and their +corresponding roles, from an XML document (by default, this document is loaded +from $CATALINA_BASE/conf/tomcat-users.xml). Changes to the data +in this file are not recognized until Tomcat is restarted.

+ +

Realm Element Attributes

+ +

To configure MemoryRealm, you will create a <Realm> +element and nest it in your $CATALINA_BASE/conf/server.xml file, +as described above. The attributes for the +MemoryRealm are defined in the Realm +configuration documentation.

+ +

User File Format

+ +

The users file (by default, conf/tomcat-users.xml must be an +XML document, with a root element <tomcat-users>. Nested +inside the root element will be a <user> element for each +valid user, consisting of the following attributes:

+
    +
  • name - Username this user must log on with.
  • +
  • password - Password this user must log on with (in + clear text if the digest attribute was not set on the + <Realm> element, or digested appropriately as + described here otherwise).
  • +
  • roles - Comma-delimited list of the role names + associated with this user.
  • +
+ +

Additional Notes

+ +

MemoryRealm operates according to the following rules:

+
    +
  • When Tomcat first starts up, it loads all defined users and their + associated information from the users file. Changes to the data in + this file will not be recognized until Tomcat is + restarted.
  • +
  • When a user attempts to access a protected resource for the first time, + Tomcat will call the authenticate() method of this + Realm.
  • +
  • Once a user has been authenticated, the user (and his or her associated + roles) are cached within Tomcat for the duration of the user's login. + (For FORM-based authentication, that means until the session times out or + is invalidated; for BASIC authentication, that means until the user + closes their browser). The cached user is not saved and + restored across sessions serialisations.
  • +
  • Administering the information in the users file is the responsibility + of your application. Tomcat does not + provide any built-in capabilities to maintain users and roles.
  • +
+ + +
+ + + + +

Introduction

+ +

JAASRealm is an implementation of the Tomcat +6 Realm interface that authenticates users through the Java +Authentication & Authorization Service (JAAS) framework which is now +provided as part of the standard Java SE API.

+

Using JAASRealm gives the developer the ability to combine +practically any conceivable security realm with Tomcat's CMA.

+

JAASRealm is prototype for Tomcat of the JAAS-based +J2EE authentication framework for J2EE v1.4, based on the JCP Specification +Request 196 to enhance container-managed security and promote +'pluggable' authentication mechanisms whose implementations would be +container-independent. +

+

Based on the JAAS login module and principal (see javax.security.auth.spi.LoginModule +and javax.security.Principal), you can develop your own +security mechanism or wrap another third-party mechanism for +integration with the CMA as implemented by Tomcat. +

+ +

Quick Start

+

To set up Tomcat to use JAASRealm with your own JAAS login module, + you will need to follow these steps:

+
    +
  1. Write your own LoginModule, User and Role classes based +on JAAS (see +the +JAAS Authentication Tutorial and +the JAAS Login Module +Developer's Guide) to be managed by the JAAS Login +Context (javax.security.auth.login.LoginContext) +When developing your LoginModule, note that JAASRealm's built-in CallbackHandler +only recognizes the NameCallback and PasswordCallback at present. +
  2. +
  3. Although not specified in JAAS, you should create +seperate classes to distinguish between users and roles, extending javax.security.Principal, +so that Tomcat can tell which Principals returned from your login +module are users and which are roles (see org.apache.catalina.realm.JAASRealm). +Regardless, the first Principal returned is always treated as the user Principal. +
  4. +
  5. Place the compiled classes on Tomcat's classpath +
  6. +
  7. Set up a login.config file for Java (see JAAS +LoginConfig file) and tell Tomcat where to find it by specifying +its location to the JVM, for instance by setting the environment +variable: JAVA_OPTS=$JAVA_OPTS -Djava.security.auth.login.config==$CATALINA_BASE/conf/jaas.config
  8. + +
  9. Configure your security-constraints in your web.xml for +the resources you want to protect
  10. +
  11. Configure the JAASRealm module in your server.xml
  12. +
  13. Restart Tomcat if it is already running.
  14. +
+

Realm Element Attributes

+

To configure JAASRealm as for step 6 above, you create +a <Realm> element and nest it in your +$CATALINA_BASE/conf/server.xml +file within your <Engine> node. The attributes for the +JAASRealm are defined in the Realm +configuration documentation.

+ +

Example

+ +

Here is an example of how your server.xml snippet should look.

+ + +<Realm className="org.apache.catalina.realm.JAASRealm" + appName="MyFooRealm" + userClassNames="org.foobar.realm.FooUser" + roleClassNames="org.foobar.realm.FooRole" + debug="99"/> + + +

It is the responsibility of your login module to create and save User and +Role objects representing Principals for the user +(javax.security.auth.Subject). If your login module doesn't +create a user object but also doesn't throw a login exception, then the +Tomcat CMA will break and you will be left at the +http://localhost:8080/myapp/j_security_check URI or at some other +unspecified location.

+ +

The flexibility of the JAAS approach is two-fold:

+
    +
  • you can carry out whatever processing you require behind +the scenes in your own login module.
  • +
  • you can plug in a completely different LoginModule by changing the configuration +and restarting the server, without any code changes to your application.
  • +
+ +

Additional Notes

+
    +
  • When a user attempts to access a protected resource for + the first time, Tomcat will call the authenticate() + method of this Realm. Thus, any changes you have made in + the security mechanism directly (new users, changed passwords or + roles, etc.) will be immediately reflected.
  • +
  • Once a user has been authenticated, the user (and his or + her associated roles) are cached within Tomcat for the duration of + the user's login. For FORM-based authentication, that means until + the session times out or is invalidated; for BASIC authentication, + that means until the user closes their browser. Any changes to the + security information for an already authenticated user will not + be reflected until the next time that user logs on again.
  • +
  • As with other Realm implementations, digested passwords + are supported if the <Realm> element in server.xml + contains a digest attribute; JAASRealm's CallbackHandler + will digest the password prior to passing it back to the LoginModule
  • +
+ +
+ + + + +

Introduction

+ +

CombinedRealm is an implementation of the Tomcat + Realm interface that authenticates users through one or more + sub-Realms.

+ +

Using CombinedRealm gives the developer the ability to combine multiple + Realms of the same or different types. This can be used to authenticate + against different sources, provide fall back in case one Realm fails or for + any other purpose that requires multiple Realms.

+ +

Sub-realms are defined by nesting Realm elements inside the + Realm element that defines the CombinedRealm. Authentication + will be attempted against each Realm in the order they are + listed. Authentication against any Realm will be sufficient to authenticate + the user.

+ +

Realm Element Attributes

+

To configure a CombinedRealm, you create a <Realm> + element and nest it in your $CATALINA_BASE/conf/server.xml + file within your <Engine> or <Host>. + You can also nest inside a <Context> node in a + context.xml file.

+ +

Example

+ +

Here is an example of how your server.xml snippet should look to use a +UserDatabase Realm and a DataSource Realm.

+ + +<Realm className="org.apache.catalina.realm.CombinedRealm" > + <Realm className="org.apache.catalina.realm.UserDatabaseRealm" + resourceName="UserDatabase"/> + <Realm className="org.apache.catalina.realm.DataSourceRealm" debug="99" + dataSourceName="jdbc/authority" + userTable="users" userNameCol="user_name" userCredCol="user_pass" + userRoleTable="user_roles" roleNameCol="role_name"/> +</Realm> + + +
+ + + +

Introduction

+ +

LockOutRealm is an implementation of the Tomcat + Realm interface that extends the CombinedRealm to provide lock + out functionality to provide a user lock out mechanism if there are too many + failed authentication attempts in a given period of time.

+ +

To ensure correct operation, there is a reasonable degree of + synchronisation in this Realm.

+ +

This Realm does not require modification to the underlying Realms or the + associated user storage mecahisms. It achieves this by recording all failed + logins, including those for users that do not exist. To prevent a DOS by + deliberating making requests with invalid users (and hence causing this + cache to grow) the size of the list of users that have failed authentication + is limited.

+ +

Sub-realms are defined by nesting Realm elements inside the + Realm element that defines the LockOutRealm. Authentication + will be attempted against each Realm in the order they are + listed. Authentication against any Realm will be sufficient to authenticate + the user.

+ +

Realm Element Attributes

+

To configure a LockOutRealm, you create a <Realm> + element and nest it in your $CATALINA_BASE/conf/server.xml + file within your <Engine> or <Host>. + You can also nest inside a <Context> node in a + context.xml file. The attributes for the + LockOutRealm are defined in the Realm + configuration documentation.

+ +

Example

+ +

Here is an example of how your server.xml snippet should look to add lock out +functionality to a UserDatabase Realm.

+ + +<Realm className="org.apache.catalina.realm.LockOutRealm" > + <Realm className="org.apache.catalina.realm.UserDatabaseRealm" + resourceName="UserDatabase"/> +</Realm> + + +
+ +
+ + + +
diff --git a/webapps/docs/security-howto.xml b/webapps/docs/security-howto.xml new file mode 100644 index 000000000000..7856bbd3da72 --- /dev/null +++ b/webapps/docs/security-howto.xml @@ -0,0 +1,327 @@ + + + +]> + + + &project; + + + Security Considerations + + + + +
+ +
+ +
+

Tomcat is configured to be reasonable secure for must use cases by + default. Some environments may require more, or less, secure configurations. + This page is to provide a single point of reference for configuration + options that may impact security and to offer some commentary on the + expected impact of changing those options. The intention is to provide a + list of configuration options that should be considered when assessing the + security of a Tomcat installation.

+ +

Note: Reading this page is not a substitute for reading + and understanding the detailed configuration documentation. Fuller + descriptions of these attributes may be found in the relevant documentation + pages.

+
+ +
+

Tomcat configuration should not be the only line of defence. The other + components in the system (operating system, network, database, etc.) should + also be secured. For the operating system, consider limiting the privileges + of the user under which Tomcat is running and limiting access to Tomcat's + files by other users. At the network level, consider using a firewall to + limit both incoming and outgoing connections to only those connections you + expect to be present.

+
+ +
+

Tomcat ships with a number of web applications by default. + Vulnerabilities have been discovered in these applications in the past. + Applications that are not required should be removed so the system will not + be at risk if another vulnerability is discovered.

+
+ +
+

Enabling the security manager causes web applications to be run in a + sandbox, significantly limiting a web applications ability to perform + malicious actions such as calling System.exit(), establishing network + connections or accessing the file system outside of the web application's + root and temporary directories.

+ +

Tomcat is tested with the security manager enabled but the majority of + Tomcat users do not run with a security manager so Tomcat is not as well + tested in this configuration. There have been, and continue to be, bugs + reported that are triggered by running under a security manager.

+ +

The restrictions imposed by a security manager are likely to break most + applications if the security manager is enabled. The security manager should + not be used without extensive testing. Ideally, the use of a security + manager should be introduced at the start of the development cycle as it can + be time-consuming to track down and fix issues caused by enabling a security + manager for a mature application.

+
+ +
+ +

The default server.xml contains a large number of comments, including + some example component definitions that are commented out. Removing these + comments makes it considerably easier to read and comprehend + server.xml.

+

If a component type is not listed, then there are no settings for that + type that directly impact security.

+
+ + +

Setting the port attribute to -1 disables + the shutdown port.

+

If the shutdown port is not disabled, a strong password should be + configured for shutdown.

+
+ + +

The APR Lifecycle Listener is not stable if compiled on Solaris using + gcc. It using the APR/native connector on Solaris, compile it with the + Sun Studio compiler.

+
+ + +

By default, an HTTP and an AJP connector are configured. Connectors + that will not be used should be removed from server.xml.

+ +

The address attribute may be used to control which IP + address the connector listens on for connections. By default, the + connector listens on all configured IP addresses.

+ +

The allowTrace attribute may be used to enable TRACE + requests which can be useful for debugging. Due to the way some browsers + handle the response from a TRACE request (which exposes the browser to an + XSS attack), support for TRACE requests is disabled by default.

+ +

The maxPostSize attribute controls the maximum size + of a POST request that will be parsed for parameters. The parameters are + cached for the duration of the request so this is limited to 2MB by + default to reduce exposure to a DOS attack.

+ +

The maxSavePostSize attribute controls the saving of + POST requests during FORM and CLIENT-CERT authentication. The parameters + are cached for the duration of the authentication (that may be many + minutes) so this is limited to 4KB by default to reduce exposure to a DOS + attack.

+ +

The xpoweredBy attribute controls whether or not the + X-Powered-By HTTP header is sent with each request. If sent, the value of + the header contains the Servlet and JSP specification versions, the full + Tomcat version (e.g. Apache Tomcat/7.0.0), the name of the JVM vendor and + the version of the JVM. This header is disabled by default. This header + can provide useful information to both legitimate clients and attackers. +

+ +

The server attribute controls the value of the Server + HTTP header. The default value of this header for Tomcat 4.1.x, 5.0.x, + 5.5.x, 6.0.x and 7.0.x is Apache-Coyote/1.1. This header can provide + limited information to both legitimate clients and attackers.

+ +

The SSLEnabled, scheme and + secure attributes may all be independently set. These are + normally used when Tomcat is located behind a reverse proxy and the proxy + is connecting to Tomcat via http or https. They allow Tomcat to see the + SSL attributes of the connections between the client and the proxy rather + than the proxy and Tomcat. For example, the client may connect to the + proxy over https but the proxy connects to Tomcat using http. If it is + necessary for Tomcat to be able to distinguish between secure and + non-secure connections received by a proxy, the proxy must use separate + connectors to pass secure and non-secure requests to Tomcat. If the + proxy uses AJP then the SSL attributes of the client connection are + passed via the AJP protocol and separate connectors are not needed.

+ +

The tomcatAuthentication attribute is used with the + AJP connectors to determine if Tomcat should authenticate the user or if + authentication can be delegated to the reverse proxy that will then pass + the authenticated username to Tomcat as part of the AJP protocol.

+ +

The allowUnsafeLegacyRenegotiation attribute provides + a workaround for + + CVE-2009-3555, a TLS man in the middle attack. This workaround applies + to the BIO connector. It is only necessary if the underlying SSL + implementation is vulnerable to CVE-2009-3555. For more information on the + current state of this vulnerability and the work-arounds available see the + Tomcat 7 security + page.

+
+ + +

The host element controls deployment. Automatic deployment allows for + simpler management but also makes it easier for an attacker to deploy a + malicious application. Automatic deployment is controlled by the + autoDeploy and deployOnStartup + attributes. If both are false, only Contexts defined in + server.xml will be deployed and any changes will require a Tomcat restart. +

+ +

In a hosted environment where web applications may not be trusted, set + the deployXml attribute to false to ignore any + context.xml packaged with the web application that may try to assigned + increased privileges to the web application.

+
+ + +

The crossContext attribute controls if a context is + allowed to access the resources of another context. It is + false by default and should only be changed for trusted web + applications.

+ +

The privileged attribute controls if a context is + allowed to use container provided servlets like the Manager servlet. It is + false by default and should only be changed for trusted web + applications.

+ +

The allowLinking attribute controls if a context is + allowed to use linked files. If enabled and the context is undeployed, the + links will be followed when deleting the context resources. To avoid this + behaviour, use the aliases attribute. Changing this + setting from the default of false on case insensitive + operating systems (this includes Windows) will disable a number of + security and allow, amongst other things, direct access to the WEB-INF + directory.

+
+ + +

It is strongly recommended that an AccessLogValve is configured. These + are normally configured per host but may also be configured per engine or + per context as required.

+ +

Any administrative application should be protected by a + RemoteAddressValve. (Note that this Valve is also available as a Filter). + The allow attribute should be used to limit access to a set of known + trusted hosts.

+ +

The default ErrorReportValve includes the Tomcat version number in the + response sent to clients. To avoid this, custom error handling can be + configured within each web application. Alternatively, the version number + can be changed by creating the following file in + CATALINA_HOME/lib/org/apache/catalina/util/ServerInfo.properties with the + content as follows:

+ +server.info=Apache Tomcat/7.0.x + +

Modify the values as required. Note that this will also change the version + number reported in some of the management tools and may make it harder to + determine the real version installed. The CATALINA_HOME/bin/version.bat|sh + script will still report the version number.

+ +

The default ErrorReportValve can display stack traces and/or JSP + source code to clients when an error occurs. To avoid this, custom error + handling can be configured within each web application.

+
+ + +

The MemoryRealm is not intended for production use as any changes to + tomcat-users.xml require a restart of Tomcat to take effect.

+ +

The JDBCRealm is not recommended for production use as it single + threaded for all authentication and authorization options. Use the + DataSourceRealm instead.

+ +

The UserDatabaseRealm is not intended for large-scale installations. It + is intended for small-scale, relatively static environments.

+ +

The JAASRealm is not widely used and therefore the code is not as + mature as the other realms. Additional testing is recommended before using + this realm.

+ +

By default, the realms not not implement any form of account lock-out. + This means that brute force attacks can be successful. To prevent a brute + force attack, the chosen realm should be wrapped in a LockOutRealm.

+
+ + +

The manager component is used to generate session IDs.

+ +

The default entropy value has been shown to generate predictable values + under certain conditions. For more secure session generation, this should + be set to a long string. This is done automatically if the APR/native + library is installed, a random value will be obtained from APR.

+ +

The class used to generate random session IDs may be changed by using + the randomClass attribute.

+ +

The length of the session ID may be changed by using the + sessionIdLength attribute.

+
+
+ +
+

Setting org.apache.catalina.connector.RECYCLE_FACADES + system property to true will cause a new facade object to be + created for each request. This reduces the chances of a bug in an + application exposing data from one request to another.

+ +

The + org.apache.catalina.connector.CoyoteAdapter.ALLOW_BACKSLASH and + org.apache.tomcat.util.buf.UDecoder.ALLOW_ENCODED_SLASH + system properties allow non-standard parsing of the request URI. Using + these options when behind a reverse proxy may enable an attacker to bypass + any security constraints enforced by the proxy.

+ +

The + org.apache.catalina.connector.Response.ENFORCE_ENCODING_IN_GET_WRITER + has security implications if disabled. Many user agents, in + breach of RFC2616, try and guess the character encoding of text media + types when the specification mandated default of ISO-8859-1 should be + used. If the response contains characters that are safe for ISO-8859-1 + but trigger an XSS if interpreted as UTF-7, some browsers will use UTF-7 + and trigger an XSS vulnerability.

+
+ +
+

The DefaultServlet is configured with readonly set to + true. Changing this to false allows clients to + delete or modify static resources on the server and to upload new + resources. This should not normally be changed without requiring + authentication.

+ +

The DefaultServlet is configured with listings set to + false. This isn't because allowing directory listings is + considered unsafe but because generating listings of directories with + thousands of files can consume significant CPU leading to a DOS attack. +

+
+ +
+

BASIC and FORM authentication pass user names and passwords in clear + text. Web applications using these authentication mechanisms with clients + connecting over untrusted networks should use SSL.

+ +

The session cookie for a session with an authenticated user are nearly + as useful as the user's password to an attacker and in nearly all + circumstances should be afforded the same level of protection as the + password itself. This usually means authenticating over SSL and continuing + to use SSL until the session ends.

+
+ + +
diff --git a/webapps/docs/security-manager-howto.xml b/webapps/docs/security-manager-howto.xml new file mode 100644 index 000000000000..63794cd13455 --- /dev/null +++ b/webapps/docs/security-manager-howto.xml @@ -0,0 +1,477 @@ + + + +]> + + + &project; + + + Glenn Nielsen + Jean-Francois Arcand + Security Manager HOW-TO + + + + +
+ +
+ +
+ +

The Java SecurityManager is what allows a web browser + to run an applet in its own sandbox to prevent untrusted code from + accessing files on the local file system, connecting to a host other + than the one the applet was loaded from, and so on. In the same way + the SecurityManager protects you from an untrusted applet running in + your browser, use of a SecurityManager while running Tomcat can protect + your server from trojan servlets, JSPs, JSP beans, and tag libraries. + Or even inadvertent mistakes.

+ +

Imagine if someone who is authorized to publish JSPs on your site + inadvertently included the following in their JSP:

+ +<% System.exit(1); %> + + +

Every time this JSP was executed by Tomcat, Tomcat would exit. + Using the Java SecurityManager is just one more line of defense a + system administrator can use to keep the server secure and reliable.

+ +

WARNING - A security audit + have been conducted using the Tomcat codebase. Most of the critical + package have been protected and a new security package protection mechanism + has been implemented. Still, make sure that you are satisfied with your SecurityManager + configuration before allowing untrusted users to publish web applications, + JSPs, servlets, beans, or tag libraries. However, running with a + SecurityManager is definitely better than running without one.

+ +
+ + +
+ +

Permission classes are used to define what Permissions a class loaded + by Tomcat will have. There are a number of Permission classes that are + a standard part of the JDK, and you can create your own Permission class + for use in your own web applications. Both techniques are used in + Tomcat.

+ + + + +

This is just a short summary of the standard system SecurityManager + Permission classes applicable to Tomcat. See + http://java.sun.com/security/ + for more information.

+ +
    +
  • java.util.PropertyPermission - Controls read/write + access to JVM properties such as java.home.
  • +
  • java.lang.RuntimePermission - Controls use of + some System/Runtime functions like exit() and + exec(). Also control the package access/definition.
  • +
  • java.io.FilePermission - Controls read/write/execute + access to files and directories.
  • +
  • java.net.SocketPermission - Controls use of + network sockets.
  • +
  • java.net.NetPermission - Controls use of + multicast network connections.
  • +
  • java.lang.reflect.ReflectPermission - Controls + use of reflection to do class introspection.
  • +
  • java.security.SecurityPermission - Controls access + to Security methods.
  • +
  • java.security.AllPermission - Allows access to all + permissions, just as if you were running Tomcat without a + SecurityManager.
  • +
+ +
+ + + + +

Tomcat utilizes a custom permission class called + org.apache.naming.JndiPermission. This permission + controls read access to JNDI named file based resources. The permission + name is the JNDI name and there are no actions. A trailing "*" can be + used to do wild card matching for a JNDI named file resource when + granting permission. For example, you might include the following + in your policy file:

+ +permission org.apache.naming.JndiPermission "jndi://localhost/examples/*"; + + +

A Permission entry like this is generated dynamically for each web + application that is deployed, to allow it to read its own static resources + but disallow it from using file access to read any other files (unless + permissions for those files are explicitly granted).

+ +

Also, Tomcat always dynamically creates the following file permissions:

+ +permission java.io.FilePermission "** your application context**", "read"; + +permission java.io.FilePermission + "** application working directory**", "read,write"; +permission java.io.FilePermission + "** application working directory**/-", "read,write,delete"; + +

Where **your application context** equals the folder (or WAR file) under which + your application has been deployed and **application working directory** is the + temporary directory provided to your application as required by the + Servlet Specification.

+ +
+ + +
+ + +
+ +

Policy File Format

+ +

The security policies implemented by the Java SecurityManager are + configured in the $CATALINA_BASE/conf/catalina.policy file. + This file completely replaces the java.policy file present + in your JDK system directories. The catalina.policy file + can be edited by hand, or you can use the + policytool + application that comes with Java 1.2 or later.

+ +

Entries in the catalina.policy file use the standard + java.policy file format, as follows:

+ +// Example policy file entry + +grant [signedBy <signer>,] [codeBase <code source>] { + permission <class> [<name> [, <action list>]]; +}; + + +

The signedBy and codeBase entries are + optional when granting permissions. Comment lines begin with "//" and + end at the end of the current line. The codeBase is in the + form of a URL, and for a file URL can use the ${java.home} + and ${catalina.home} properties (which are expanded out to + the directory paths defined for them by the JAVA_HOME, + CATALINA_HOME and CATALINA_BASE environment + variables).

+ +

The Default Policy File

+ +

The default $CATALINA_BASE/conf/catalina.policy file + looks like this:

+ +// ============================================================================ +// catalina.policy - Security Policy Permissions for Tomcat 7 +// +// This file contains a default set of security policies to be enforced (by the +// JVM) when Catalina is executed with the "-security" option. In addition +// to the permissions granted here, the following additional permissions are +// granted specific to each web application: +// +// * Read access to its document root directory +// * Read, write and delete access to its working directory +// +// ============================================================================ + + +// ========== SYSTEM CODE PERMISSIONS ========================================= + + +// These permissions apply to javac +grant codeBase "file:${java.home}/lib/-" { + permission java.security.AllPermission; +}; + +// These permissions apply to all shared system extensions +grant codeBase "file:${java.home}/jre/lib/ext/-" { + permission java.security.AllPermission; +}; + +// These permissions apply to javac when ${java.home] points at $JAVA_HOME/jre +grant codeBase "file:${java.home}/../lib/-" { + permission java.security.AllPermission; +}; + +// These permissions apply to all shared system extensions when +// ${java.home} points at $JAVA_HOME/jre +grant codeBase "file:${java.home}/lib/ext/-" { + permission java.security.AllPermission; +}; + + +// ========== CATALINA CODE PERMISSIONS ======================================= + + +// These permissions apply to the daemon code +grant codeBase "file:${catalina.home}/bin/commons-daemon.jar" { + permission java.security.AllPermission; +}; + +// These permissions apply to the logging API +// Note: If tomcat-juli.jar is in ${catalina.base} and not in ${catalina.home}, +// update this section accordingly. +// grant codeBase "file:${catalina.base}/bin/tomcat-juli.jar" {..} +grant codeBase "file:${catalina.home}/bin/tomcat-juli.jar" { + permission java.io.FilePermission + "${java.home}${file.separator}lib${file.separator}logging.properties", "read"; + + permission java.io.FilePermission + "${catalina.base}${file.separator}conf${file.separator}logging.properties", "read"; + permission java.io.FilePermission + "${catalina.base}${file.separator}logs", "read, write"; + permission java.io.FilePermission + "${catalina.base}${file.separator}logs${file.separator}*", "read, write"; + + permission java.lang.RuntimePermission "shutdownHooks"; + permission java.lang.RuntimePermission "getClassLoader"; + permission java.lang.RuntimePermission "setContextClassLoader"; + + permission java.util.logging.LoggingPermission "control"; + + permission java.util.PropertyPermission "java.util.logging.config.class", "read"; + permission java.util.PropertyPermission "java.util.logging.config.file", "read"; + permission java.util.PropertyPermission "catalina.base", "read"; + + // Note: To enable per context logging configuration, permit read access to + // the appropriate file. Be sure that the logging configuration is + // secure before enabling such access. + // E.g. for the examples web application: + // permission java.io.FilePermission "${catalina.base}${file.separator} + // webapps${file.separator}examples${file.separator}WEB-INF + // ${file.separator}classes${file.separator}logging.properties", "read"; +}; + +// These permissions apply to the server startup code +grant codeBase "file:${catalina.home}/bin/bootstrap.jar" { + permission java.security.AllPermission; +}; + +// These permissions apply to the servlet API classes +// and those that are shared across all class loaders +// located in the "lib" directory +grant codeBase "file:${catalina.home}/lib/-" { + permission java.security.AllPermission; +}; + + +// If using a per instance lib directory, i.e. ${catalina.base}/lib, +// then the following permission will need to be uncommented +// grant codeBase "file:${catalina.base}/lib/-" { +// permission java.security.AllPermission; +// }; + + +// ========== WEB APPLICATION PERMISSIONS ===================================== + + +// These permissions are granted by default to all web applications +// In addition, a web application will be given a read FilePermission +// and JndiPermission for all files and directories in its document root. +grant { + // Required for JNDI lookup of named JDBC DataSource's and + // javamail named MimePart DataSource used to send mail + permission java.util.PropertyPermission "java.home", "read"; + permission java.util.PropertyPermission "java.naming.*", "read"; + permission java.util.PropertyPermission "javax.sql.*", "read"; + + // OS Specific properties to allow read access + permission java.util.PropertyPermission "os.name", "read"; + permission java.util.PropertyPermission "os.version", "read"; + permission java.util.PropertyPermission "os.arch", "read"; + permission java.util.PropertyPermission "file.separator", "read"; + permission java.util.PropertyPermission "path.separator", "read"; + permission java.util.PropertyPermission "line.separator", "read"; + + // JVM properties to allow read access + permission java.util.PropertyPermission "java.version", "read"; + permission java.util.PropertyPermission "java.vendor", "read"; + permission java.util.PropertyPermission "java.vendor.url", "read"; + permission java.util.PropertyPermission "java.class.version", "read"; + permission java.util.PropertyPermission "java.specification.version", "read"; + permission java.util.PropertyPermission "java.specification.vendor", "read"; + permission java.util.PropertyPermission "java.specification.name", "read"; + + permission java.util.PropertyPermission "java.vm.specification.version", "read"; + permission java.util.PropertyPermission "java.vm.specification.vendor", "read"; + permission java.util.PropertyPermission "java.vm.specification.name", "read"; + permission java.util.PropertyPermission "java.vm.version", "read"; + permission java.util.PropertyPermission "java.vm.vendor", "read"; + permission java.util.PropertyPermission "java.vm.name", "read"; + + // Required for OpenJMX + permission java.lang.RuntimePermission "getAttribute"; + + // Allow read of JAXP compliant XML parser debug + permission java.util.PropertyPermission "jaxp.debug", "read"; + + // All JSPs need to be able to read this package + permission java.lang.RuntimePermission "accessClassInPackage.org.apache.tomcat"; + + // Precompiled JSPs need access to these packages. + permission java.lang.RuntimePermission "accessClassInPackage.org.apache.jasper.el"; + permission java.lang.RuntimePermission "accessClassInPackage.org.apache.jasper.runtime"; + permission java.lang.RuntimePermission + "accessClassInPackage.org.apache.jasper.runtime.*"; + + // Precompiled JSPs need access to these system properties. + permission java.util.PropertyPermission + "org.apache.jasper.runtime.BodyContentImpl.LIMIT_BUFFER", "read"; + permission java.util.PropertyPermission + "org.apache.el.parser.COERCE_TO_ZERO", "read"; + + // The cookie code needs these. + permission java.util.PropertyPermission + "org.apache.catalina.STRICT_SERVLET_COMPLIANCE", "read"; + permission java.util.PropertyPermission + "org.apache.tomcat.util.http.ServerCookie.STRICT_NAMING", "read"; + permission java.util.PropertyPermission + "org.apache.tomcat.util.http.ServerCookie.FWD_SLASH_IS_SEPARATOR", "read"; + + // Applications using Comet need to be able to access this package + permission java.lang.RuntimePermission "accessClassInPackage.org.apache.catalina.comet"; +}; + + +// The Manager application needs access to the following packages to support the +// session display functionality +grant codeBase "file:${catalina.base}/webapps/manager/-" { + permission java.lang.RuntimePermission "accessClassInPackage.org.apache.catalina"; + permission java.lang.RuntimePermission "accessClassInPackage.org.apache.catalina.manager"; + permission java.lang.RuntimePermission "accessClassInPackage.org.apache.catalina.manager.util"; +}; + +// You can assign additional permissions to particular web applications by +// adding additional "grant" entries here, based on the code base for that +// application, /WEB-INF/classes/, or /WEB-INF/lib/ jar files. +// +// Different permissions can be granted to JSP pages, classes loaded from +// the /WEB-INF/classes/ directory, all jar files in the /WEB-INF/lib/ +// directory, or even to individual jar files in the /WEB-INF/lib/ directory. +// +// For instance, assume that the standard "examples" application +// included a JDBC driver that needed to establish a network connection to the +// corresponding database and used the scrape taglib to get the weather from +// the NOAA web server. You might create a "grant" entries like this: +// +// The permissions granted to the context root directory apply to JSP pages. +// grant codeBase "file:${catalina.base}/webapps/examples/-" { +// permission java.net.SocketPermission "dbhost.mycompany.com:5432", "connect"; +// permission java.net.SocketPermission "*.noaa.gov:80", "connect"; +// }; +// +// The permissions granted to the context WEB-INF/classes directory +// grant codeBase "file:${catalina.base}/webapps/examples/WEB-INF/classes/-" { +// }; +// +// The permission granted to your JDBC driver +// grant codeBase "jar:file:${catalina.base}/webapps/examples/WEB-INF/lib/driver.jar!/-" { +// permission java.net.SocketPermission "dbhost.mycompany.com:5432", "connect"; +// }; +// The permission granted to the scrape taglib +// grant codeBase "jar:file:${catalina.base}/webapps/examples/WEB-INF/lib/scrape.jar!/-" { +// permission java.net.SocketPermission "*.noaa.gov:80", "connect"; +// }; + + +

Starting Tomcat With A SecurityManager

+ +

Once you have configured the catalina.policy file for use + with a SecurityManager, Tomcat can be started with a SecurityManager in + place by using the "-security" option:

+ +$CATALINA_HOME/bin/catalina.sh start -security (Unix) +%CATALINA_HOME%\bin\catalina start -security (Windows) + + +
+
+

Starting with Tomcat 5, it is now possible to configure which Tomcat + internal package are protected againts package definition and access. See + + http://java.sun.com/security/seccodeguide.html + for more information.

+ + +

WARNING: Be aware that removing the default package protection + could possibly open a security hole

+ +

The Default Properties File

+ +

The default $CATALINA_BASE/conf/catalina.properties file + looks like this:

+ +# +# List of comma-separated packages that start with or equal this string +# will cause a security exception to be thrown when +# passed to checkPackageAccess unless the +# corresponding RuntimePermission ("accessClassInPackage."+package) has +# been granted. +package.access=sun.,org.apache.catalina.,org.apache.coyote.,org.apache.tomcat., +org.apache.jasper. +# +# List of comma-separated packages that start with or equal this string +# will cause a security exception to be thrown when +# passed to checkPackageDefinition unless the +# corresponding RuntimePermission ("defineClassInPackage."+package) has +# been granted. +# +# by default, no packages are restricted for definition, and none of +# the class loaders supplied with the JDK call checkPackageDefinition. +# +package.definition=sun.,java.,org.apache.catalina.,org.apache.coyote., +org.apache.tomcat.,org.apache.jasper. + +

Once you have configured the catalina.properties file for use + with a SecurityManager, remember to re-start Tomcat.

+
+ +
+ +

If your web application attempts to execute an operation that is + prohibited by lack of a required Permission, it will throw an + AccessControLException or a SecurityException + when the SecurityManager detects the violation. Debugging the permission + that is missing can be challenging, and one option is to turn on debug + output of all security decisions that are made during execution. This + is done by setting a system property before starting Tomcat. The easiest + way to do this is via the CATALINA_OPTS environment variable. + Execute this command:

+ +export CATALINA_OPTS=-Djava.security.debug=all (Unix) +set CATALINA_OPTS=-Djava.security.debug=all (Windows) + + +

before starting Tomcat.

+ +

WARNING - This will generate many megabytes + of output! However, it can help you track down problems by searching + for the word "FAILED" and determining which permission was being checked + for. See the Java security documentation for more options that you can + specify here as well.

+ +
+ + + + +
diff --git a/webapps/docs/servletapi/index.html b/webapps/docs/servletapi/index.html new file mode 100644 index 000000000000..156660c03657 --- /dev/null +++ b/webapps/docs/servletapi/index.html @@ -0,0 +1,34 @@ + + + + + + API docs + + + + +The Servlet Javadoc is not installed by default. Download and install +the "fulldocs" package to get it. + +You can also access the javadoc online in the Tomcat + +documentation bundle. + + + diff --git a/webapps/docs/setup.xml b/webapps/docs/setup.xml new file mode 100644 index 000000000000..303f2ac47291 --- /dev/null +++ b/webapps/docs/setup.xml @@ -0,0 +1,151 @@ + + + +]> + + + &project; + + + Remy Maucherat + Tomcat Setup + + + + +
+ +
+ +
+

+ This document introduces several ways to set up Tomcat for running + on different platforms. Please note that some advanced setup issues + are not covered here: the full distribution (ZIP file or tarball) + includes a file called + RUNNING.txt which discusses these issues. We encourage you to refer + to it if the information below does not answer some of your questions. +

+
+ +
+ +

+ Installing Tomcat on Windows can be done easily using the Windows + installer. Its interface and functionality is similar to other wizard + based installers, with only a few items of interest. +

+ +

+

    +
  • Installation as a service: Tomcat will be + installed as a Windows + NT/2k/XP service no matter what setting is selected. Using the + checkbox on the component page sets the service as "auto" + startup, so that Tomcat is automatically started when Windows + starts. For optimal security, the service should be run as a + separate user, with reduced permissions (see the Windows Services + administration tool and its documentation).
  • +
  • Java location: The installer will use the registry + or the JAVA_HOME environment variable to determine the base path + of a Java SE 6 JRE. +
  • +
  • Tray icon: When Tomcat is run as a service, there + will not be any tray icon present when Tomcat is running. Note that + when choosing to run Tomcat at the end of installation, the tray + icon will be used even if Tomcat was installed as a service.
  • +
  • Refer to the + Windows Service HOW-TO + for information on how to manage Tomcat as Windows NT service. +
  • +
+

+ +

The installer will create shortcuts allowing starting and configuring + Tomcat. It is important to note that the Tomcat administration web + application can only be used when Tomcat is running.

+ +
+ +
+ +

Tomcat can be run as a daemon using the jsvc tool from the + commons-daemon project. Source tarballs for jsvc are included with the + Tomcat binaries, and need to be compiled. Building jsvc requires + a C ANSI compiler (such as GCC), GNU Autoconf, and a JDK.

+ +

Before running the script, the JAVA_HOME environment + variable should be set to the base path of the JDK. Alternately, when + calling the ./configure script, the path of the JDK may + be specified using the --with-java parameter, such as + ./configure --with-java=/usr/java.

+ +

Using the following commands should result in a compiled jsvc binary, + located in the $CATALINA_HOME/bin folder. This assumes + that GNU TAR is used, and that CATALINA_HOME is an + environment variable pointing to the base path of the Tomcat + installation.

+ +

Please note that you should use the GNU make (gmake) instead of + the native BSD make on FreeBSD systems.

+ + + cd $CATALINA_HOME/bin + tar xvfz commons-deamon-native.tar.gz + cd commons-daemon-1.0.x-native-src/unix + ./configure + make + cp jsvc ../.. + cd ../.. + + +

Tomcat can then be run as a daemon using the following commands.

+ + + cd $CATALINA_HOME + ./bin/jsvc -cp ./bin/bootstrap.jar \ + -outfile ./logs/catalina.out -errfile ./logs/catalina.err \ + org.apache.catalina.startup.Bootstrap + + +

jsvc has other useful parameters, such as -user which + causes it to switch to another user after the daemon initialization is + complete. This allows, for example, running Tomcat as a non privileged + user while still being able to use privileged ports. + jsvc --help will return the full jsvc usage + information. In particular, the -debug option is useful + to debug issues running jsvc.

+ +

The file + $CATALINA_HOME/bin/commons-daemon-1.0.x-native-src/unix/native/Tomcat5.sh + can be used as a template for starting Tomcat automatically at + boot time from /etc/init.d. The file is currently setup for + running Tomcat 5.5.x, so it will be necessary to edit it a little.

+ +

Note that the Commons-Daemon JAR file must be on your runtime classpath + to run Tomcat in this manner. The Commons-Daemon JAR file is in the + Class-Path entry of the bootstrap.jar manifest, but if you get a + ClassNotFoundException or a NoClassDefFoundError for a Commons-Daemon + class, add the Commons-Daemon JAR to the -cp argument when launching + jsvc.

+ +
+ + +
diff --git a/webapps/docs/ssi-howto.xml b/webapps/docs/ssi-howto.xml new file mode 100644 index 000000000000..3e8f5b21d935 --- /dev/null +++ b/webapps/docs/ssi-howto.xml @@ -0,0 +1,397 @@ + + + +]> + + +&project; + + +Glenn L. Nielsen +SSI How To + + + + +
+ +
+ +
+ +

SSI (Server Side Includes) are directives that are placed in HTML pages, +and evaluated on the server while the pages are being served. They let you +add dynamically generated content to an existing HTML page, without having +to serve the entire page via a CGI program, or other dynamic technology. +

+ +

Within Tomcat SSI support can be added when using Tomcat as your +HTTP server and you require SSI support. Typically this is done +during development when you don't want to run a web server like Apache.

+ +

Tomcat SSI support implements the same SSI directives as Apache. See the + +Apache Introduction to SSI for information on using SSI directives.

+ +

SSI support is available as a servlet and as a filter. You should use one +or the other to provide SSI support but not both.

+ +

Servlet based SSI support is implemented using the class +org.apache.catalina.ssi.SSIServlet. Traditionally, this servlet +is mapped to the URL pattern "*.shtml".

+ +

Filter based SSI support is implemented using the class +org.apache.catalina.ssi.SSIFilter. Traditionally, this filter +is mapped to the URL pattern "*.shtml", though it can be mapped to "*" as +it will selectively enable/disable SSI processing based on mime types. The +contentType init param allows you to apply SSI processing to JSP pages, +javascript, or any other content you wish.

+

By default SSI support is disabled in Tomcat.

+
+ +
+ +

CAUTION - SSI directives can be used to execute programs +external to the Tomcat JVM. If you are using the Java SecurityManager this +will bypass your security policy configuration in catalina.policy. +

+ +

To use the SSI servlet, remove the XML comments from around the SSI servlet +and servlet-mapping configuration in +$CATALINA_BASE/conf/web.xml.

+ +

To use the SSI filter, remove the XML comments from around the SSI filter +and filter-mapping configuration in +$CATALINA_BASE/conf/web.xml.

+ +

Only Contexts which are marked as privileged may use SSI features (see the +privileged property of the Context element).

+ +
+ +
+ +

There are several servlet init parameters which can be used to +configure the behaviour of the SSI servlet. +

    +
  • buffered - Should output from this servlet be buffered? +(0=false, 1=true) Default 0 (false).
  • +
  • debug - Debugging detail level for messages logged +by this servlet. Default 0.
  • +
  • expires - The number of seconds before a page with SSI +directives will expire. Default behaviour is for all SSI directives to be +evaluated for every request.
  • +
  • isVirtualWebappRelative - Should "virtual" SSI directive +paths be interpreted as relative to the context root, instead of the server +root? (0=false, 1=true) Default 0 (false).
  • +
  • inputEncoding - The encoding to be assumed for SSI +resources if one cannot be determined from the resource itself. Default is +the default platform encoding.
  • +
  • outputEncoding - The encoding to be used for the result +of the SSI processing. Default is UTF-8.
  • +
  • allowExec - Is the exec command enabled? Default is +false.
  • +
+

+ +
+ +
+ +

There are several filter init parameters which can be used to +configure the behaviour of the SSI filter. +

    +
  • contentType - A regex pattern that must be matched before +SSI processing is applied. When crafting your own pattern, don't forget that a +mime content type may be followed by an optional character set in the form +"mime/type; charset=set" that you must take into account. Default is +"text/x-server-parsed-html(;.*)?".
  • +
  • debug - Debugging detail level for messages logged +by this servlet. Default 0.
  • +
  • expires - The number of seconds before a page with SSI +directives will expire. Default behaviour is for all SSI directives to be +evaluated for every request.
  • +
  • isVirtualWebappRelative - Should "virtual" SSI directive +paths be interpreted as relative to the context root, instead of the server +root? (0=false, 1=true) Default 0 (false).
  • +
  • allowExec - Is the exec command enabled? Default is +false.
  • +
+

+ +
+ +
+

Server Side Includes are invoked by embedding SSI directives in an HTML document + whose type will be processed by the SSI servlet. The directives take the form of an HTML + comment. The directive is replaced by the results of interpreting it before sending the + page to the client. The general form of a directive is:

+

<!--#directive [parm=value] -->

+

The directives are: +

    +
  • +config - <!--#config timefmt="%B %Y" --> +Used to set the format of dates and other items processed by SSI +
  • +
  • +echo - <!--#echo var="VARIABLE_NAME" --> +will be replaced by the value of the variable. +
  • +
  • +exec - Used to run commands on the host system. +
  • +
  • +include - <!--#include virtual="file-name" --> +inserts the contents +
  • +
  • +flastmod - <!--#flastmod file="filename.shtml" --> +Returns the time that a file was lost modified. +
  • +
  • +fsize - <!--#fsize file="filename.shtml" --> +Returns the size of a file. +
  • +
  • +printenv - <!--#printenv --> +Returns the list of all the defined variables. +
  • +
  • +set - <!--#set var="foo" value="Bar" --> +is used to assign a value to a user-defind variable. +
  • +
  • +if elif endif else - Used to create conditional sections. For example:
  • +<!--#config timefmt="%A" -->
    + <!--#if expr="$DATE_LOCAL = /Monday/" -->
    + <p>Meeting at 10:00 on Mondays</p>
    + <!--#elif expr="$DATE_LOCAL = /Friday/" -->
    + <p>Turn in your time card</p>
    + <!--#else -->
    + <p>Yoga class at noon.</p>
    + <!--#endif -->
    +
+

+See the +

+Apache Introduction to SSI for more information on using SSI directives.

+
+ +
+

The SSI servlet currently implements the following variables: +

+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Variable NameDescription
AUTH_TYPE + The type of authentication used for this user: BASIC, FORM, etc.
CONTENT_LENGTH + The length of the data (in bytes or the number of + characters) passed from a form.
CONTENT_TYPE + The MIME type of the query data, such as "text/html".
DATE_GMT +Current date and time in GMT
DATE_LOCAL +Current date and time in the local time zone
DOCUMENT_NAME +The current file
DOCUMENT_URI +Virtual path to the file
GATEWAY_INTERFACE + The revision of the Common Gateway Interface that the + server uses if enabled: "CGI/1.1".
HTTP_ACCEPT + A list of the MIME types that the client can accept.
HTTP_ACCEPT_ENCODING + A list of the compression types that the client can accept.
HTTP_ACCEPT_LANGUAGE + A list of the languages that the client can accept.
HTTP_CONNECTION + The way that the connection from the client is being managed: + "Close" or "Keep-Alive".
HTTP_HOST + The web site that the client requested.
HTTP_REFERER + The URL of the document that the client linked from.
HTTP_USER_AGENT + The browser the client is using to issue the request.
LAST_MODIFIED +Last modification date and time for current file
PATH_INFO + Extra path information passed to a servlet.
PATH_TRANSLATED + The translated version of the path given by the + variable PATH_INFO.
QUERY_STRING +The query string that follows the "?" in the URL. +
QUERY_STRING_UNESCAPED +Undecoded query string with all shell metacharacters escaped +with "\"
REMOTE_ADDR + The remote IP address of the user making the request.
REMOTE_HOST + The remote hostname of the user making the request.
REMOTE_PORT + The port number at remote IP address of the user making the request.
REMOTE_USER + The authenticated name of the user.
REQUEST_METHOD + The method with which the information request was + issued: "GET", "POST" etc.
REQUEST_URI + The web page originally requested by the client.
SCRIPT_FILENAME + The location of the current web page on the server.
SCRIPT_NAME + The name of the web page.
SERVER_ADDR + The server's IP address.
SERVER_NAME + The server's hostname or IP address.
SERVER_PORT + The port on which the server received the request.
SERVER_PROTOCOL + The protocol used by the server. E.g. "HTTP/1.1".
SERVER_SOFTWARE + The name and version of the server software that is + answering the client request.
UNIQUE_ID + A token used to identify the current session if one + has been established.
+
+ + + +
diff --git a/webapps/docs/ssl-howto.xml b/webapps/docs/ssl-howto.xml new file mode 100644 index 000000000000..21beed1d0596 --- /dev/null +++ b/webapps/docs/ssl-howto.xml @@ -0,0 +1,633 @@ + + + +]> + + + &project; + + + Christopher Cain + Yoav Shapira + SSL Configuration HOW-TO + + + + +
+ +
+ +
+ +
+

The description below uses the variable name $CATALINA_BASE to refer the + base directory against which most relative paths are resolved. If you have + not configured Tomcat for multiple instances by setting a CATALINA_BASE + directory, then $CATALINA_BASE will be set to the value of $CATALINA_HOME, + the directory into which you have installed Tomcat.

+
+ +

To install and configure SSL support on Tomcat, you need to follow +these simple steps. For more information, read the rest of this HOW-TO.

+
    +
  1. Create a certificate keystore by executing the following command: +

    Windows:

    + +%JAVA_HOME%\bin\keytool -genkey -alias tomcat -keyalg RSA + +

    Unix:

    + +$JAVA_HOME/bin/keytool -genkey -alias tomcat -keyalg RSA + +

    + and specify a password value of "changeit".


  2. +
  3. Uncomment the "SSL HTTP/1.1 Connector" entry in + $CATALINA_BASE/conf/server.xml and modify as described in + the Configuration section below.
  4. +

    +
+ + +
+ + +
+ +

SSL, or Secure Socket Layer, is a technology which allows web browsers and +web servers to communicate over a secured connection. This means that the data +being sent is encrypted by one side, transmitted, then decrypted by the other +side before processing. This is a two-way process, meaning that both the +server AND the browser encrypt all traffic before sending out data.

+ +

Another important aspect of the SSL protocol is Authentication. This means +that during your initial attempt to communicate with a web server over a secure +connection, that server will present your web browser with a set of +credentials, in the form of a "Certificate", as proof the site is who and what +it claims to be. In certain cases, the server may also request a Certificate +from your web browser, asking for proof that you are who you claim +to be. This is known as "Client Authentication," although in practice this is +used more for business-to-business (B2B) transactions than with individual +users. Most SSL-enabled web servers do not request Client Authentication.

+ +
+ +
+ +

It is important to note that configuring Tomcat to take advantage of +secure sockets is usually only necessary when running it as a stand-alone +web server. When running Tomcat primarily as a Servlet/JSP container behind +another web server, such as Apache or Microsoft IIS, it is usually necessary +to configure the primary web server to handle the SSL connections from users. +Typically, this server will negotiate all SSL-related functionality, then +pass on any requests destined for the Tomcat container only after decrypting +those requests. Likewise, Tomcat will return cleartext responses, that will +be encrypted before being returned to the user's browser. In this environment, +Tomcat knows that communications between the primary web server and the +client are taking place over a secure connection (because your application +needs to be able to ask about this), but it does not participate in the +encryption or decryption itself.

+ +
+ +
+ +

In order to implement SSL, a web server must have an associated Certificate +for each external interface (IP address) that accepts secure connections. +The theory behind this design is that a server should provide some kind of +reasonable assurance that its owner is who you think it is, particularly +before receiving any sensitive information. While a broader explanation of +Certificates is beyond the scope of this document, think of a Certificate +as a "digital driver's license" for an Internet address. It states what +company the site is associated with, along with some basic contact +information about the site owner or administrator.

+ +

This "driver's license" is cryptographically signed by its owner, and is +therefore extremely difficult for anyone else to forge. For sites involved +in e-commerce, or any other business transaction in which authentication of +identity is important, a Certificate is typically purchased from a well-known +Certificate Authority (CA) such as VeriSign or Thawte. Such +certificates can be electronically verified -- in effect, the Certificate +Authority will vouch for the authenticity of the certificates that it grants, +so you can believe that that Certificate is valid if you trust the Certificate +Authority that granted it.

+ +

In many cases, however, authentication is not really a concern. An +administrator may simply want to ensure that the data being transmitted and +received by the server is private and cannot be snooped by anyone who may be +eavesdropping on the connection. Fortunately, Java provides a relatively +simple command-line tool, called keytool, which can easily create +a "self-signed" Certificate. Self-signed Certificates are simply user +generated Certificates which have not been officially registered with any +well-known CA, and are therefore not really guaranteed to be authentic at all. +Again, this may or may not even be important, depending on your needs.

+ +
+ +
+ +

The first time a user attempts to access a secured page on your site, +he or she is typically presented with a dialog containing the details of +the certificate (such as the company and contact name), and asked if he or she +wishes to accept the Certificate as valid and continue with the transaction. +Some browsers will provide an option for permanently accepting a given +Certificate as valid, in which case the user will not be bothered with a +prompt each time they visit your site. Other browsers do not provide this +option. Once approved by the user, a Certificate will be considered valid +for at least the entire browser session.

+ +

Also, while the SSL protocol was designed to be as efficient as securely +possible, encryption/decryption is a computationally expensive process from +a performance standpoint. It is not strictly necessary to run an entire +web application over SSL, and indeed a developer can pick and choose which +pages require a secure connection and which do not. For a reasonably busy +site, it is customary to only run certain pages under SSL, namely those +pages where sensitive information could possibly be exchanged. This would +include things like login pages, personal information pages, and shopping +cart checkouts, where credit card information could possibly be transmitted. +Any page within an application can be requested over a secure socket by +simply prefixing the address with https: instead of +http:. Any pages which absolutely require +a secure connection should check the protocol type associated with the +page request and take the appropriate action if https is not +specified.

+ +

Finally, using name-based virtual hosts on a secured connection can be +problematic. This is a design limitation of the SSL protocol itself. The SSL +handshake, where the client browser accepts the server certificate, must occur +before the HTTP request is accessed. As a result, the request information +containing the virtual host name cannot be determined prior to authentication, +and it is therefore not possible to assign multiple certificates to a single +IP address. If all virtual hosts on a single IP address need to authenticate +against the same certificate, the addition of multiple virtual hosts should not +interfere with normal SSL operations on the server. Be aware, however, that +most client browsers will compare the server's domain name against the domain +name listed in the certificate, if any (applicable primarily to official, +CA-signed certificates). If the domain names do not match, these browsers will +display a warning to the client user. In general, only address-based virtual +hosts are commonly used with SSL in a production environment.

+ +
+ +
+ + + +

Tomcat currently operates only on JKS, PKCS11 or +PKCS12 format keystores. The JKS format +is Java's standard "Java KeyStore" format, and is the format created by the +keytool command-line utility. This tool is included in the JDK. +The PKCS12 format is an internet standard, and can be manipulated +via (among other things) OpenSSL and Microsoft's Key-Manager. +

+ +

Each entry in a keystore is identified by an alias string. Whilst many +keystore implementations treat aliases in a case insensitive manner, case +sensitive implementations are available. The PKCS11 specification, +for example, requires that aliases are case sensitive. To avoid issues related +to the case sensitivity of aliases, it is not recommended to use aliases that +differ only in case. +

+ +

To import an existing certificate into a JKS keystore, please read the +documentation (in your JDK documentation package) about keytool. +Note that OpenSSL often adds readable comments before the key, +keytooldoes not support that, so remove the OpenSSL comments if +they exist before importing the key using keytool. +

+

To import an existing certificate signed by your own CA into a PKCS12 +keystore using OpenSSL you would execute a command like: +openssl pkcs12 -export -in mycert.crt -inkey mykey.key \ + -out mycert.p12 -name tomcat -CAfile myCA.crt \ + -caname root -chain + +For more advanced cases, consult the OpenSSL +documentation. +

+

To create a new keystore from scratch, containing a single self-signed +Certificate, execute the following from a terminal command line:

+

Windows:

+ +%JAVA_HOME%\bin\keytool -genkey -alias tomcat -keyalg RSA + +

Unix:

+ +$JAVA_HOME/bin/keytool -genkey -alias tomcat -keyalg RSA + + +

(The RSA algorithm should be preferred as a secure algorithm, and this +also ensures general compatibility with other servers and components.)

+ +

This command will create a new file, in the home directory of the user +under which you run it, named ".keystore". To specify a +different location or filename, add the -keystore parameter, +followed by the complete pathname to your keystore file, +to the keytool command shown above. You will also need to +reflect this new location in the server.xml configuration file, +as described later. For example:

+

Windows:

+ +%JAVA_HOME%\bin\keytool -genkey -alias tomcat -keyalg RSA \ + -keystore \path\to\my\keystore + +

Unix:

+ +$JAVA_HOME/bin/keytool -genkey -alias tomcat -keyalg RSA \ + -keystore /path/to/my/keystore + + +

After executing this command, you will first be prompted for the keystore +password. The default password used by Tomcat is "changeit" +(all lower case), although you can specify a custom password if you like. +You will also need to specify the custom password in the +server.xml configuration file, as described later.

+ +

Next, you will be prompted for general information about this Certificate, +such as company, contact name, and so on. This information will be displayed +to users who attempt to access a secure page in your application, so make +sure that the information provided here matches what they will expect.

+ +

Finally, you will be prompted for the key password, which is the +password specifically for this Certificate (as opposed to any other +Certificates stored in the same keystore file). You MUST +use the same password here as was used for the keystore password itself. +This is a restriction of the Tomcat implementation. +(Currently, the keytool prompt will tell you that pressing the +ENTER key does this for you automatically.)

+ +

If everything was successful, you now have a keystore file with a +Certificate that can be used by your server.

+ +

Note: your private key password and keystore password +should be the same. If they differ, you will get an error along the lines +of java.io.IOException: Cannot recover key, as documented in +Bugzilla issue 38217, +which contains further references for this issue.

+ +
+ + +

+Tomcat can use two different implementations of SSL: +

    +
  • the JSSE implementation provided as part of the Java runtime (since 1.4)
  • +
  • the APR implementation, which uses the OpenSSL engine by default.
  • +
+The exact configuration details depend on which implementation is being used. +The implementation used by Tomcat is chosen automatically unless it is overriden as described below. +If the installation uses APR +- i.e. you have installed the Tomcat native library - +then it will use the APR SSL implementation, otherwise it will use the Java JSSE implementation. +

+ +

+ To avoid auto configuration you can define which implementation to use by specifying a classname + in the protocol attribute of the Connector.
+ To define a Java (JSSE) connector, regardless of whether the APR library is loaded or not do: + +<-- Define a blocking Java SSL Coyote HTTP/1.1 Connector on port 8443 --> +<Connector protocol="org.apache.coyote.http11.Http11Protocol" + port="8443" .../> + +<-- Define a non-blocking Java SSL Coyote HTTP/1.1 Connector on port 8443 --> +<Connector protocol="org.apache.coyote.http11.Http11NioProtocol" + port="8443" .../> + +Alternatively, to specify an APR connector (the APR library must be available) use: + +<-- Define a APR SSL Coyote HTTP/1.1 Connector on port 8443 --> +<Connector protocol="org.apache.coyote.http11.Http11AprProtocol" + port="8443" .../> + + +

+ +

If you are using APR, you have the option of configuring an alternative engine to OpenSSL. + +<Listener className="org.apache.catalina.core.AprLifecycleListener" + SSLEngine="someengine" SSLRandomSeed="somedevice" /> + +The default value is + +<Listener className="org.apache.catalina.core.AprLifecycleListener" + SSLEngine="on" SSLRandomSeed="builtin" /> + +So to use SSL under APR, make sure the SSLEngine attribute is set to something other than off. +The default value is on and if you specify another value, it has to be a valid engine name. +
+If you haven't compiled in SSL support into your Tomcat Native library, then you can turn this initialization off + +<Listener className="org.apache.catalina.core.AprLifecycleListener" + SSLEngine="off" /> + +SSLRandomSeed allows to specify a source of entropy. Productive system needs a reliable source of entropy +but entropy may need a lot of time to be collected therefore test systems could use no blocking entropy +sources like "/dev/urandom" that will allow quicker starts of Tomcat. + +

+ +

The final step is to configure the Connector in the +$CATALINA_BASE/conf/server.xml file, where +$CATALINA_BASE represents the base directory for the +Tomcat instance. An example <Connector> element +for an SSL connector is included in the default server.xml +file installed with Tomcat. For JSSE, it should look something like this:

+ +<-- Define a SSL Coyote HTTP/1.1 Connector on port 8443 --> +<!-- +<Connector + port="8443" maxThreads="200" + scheme="https" secure="true" SSLEnabled="true" + keystoreFile="${user.home}/.keystore" keystorePass="changeit" + clientAuth="false" sslProtocol="TLS"/> +--> + +

+ The example above will throw an error if you have the APR and the Tomcat Native libraries in your path, + as Tomcat will try to use the APR connector. The APR connector uses different attributes for + SSL keys and certificates. An example of an APR configuration is: + +<-- Define a SSL Coyote HTTP/1.1 Connector on port 8443 --> +<!-- +<Connector + port="8443" maxThreads="200" + scheme="https" secure="true" SSLEnabled="true" + SSLCertificateFile="/usr/local/ssl/server.crt" + SSLCertificateKeyFile="/usr/local/ssl/server.pem" + clientAuth="optional" SSLProtocol="TLSv1"/> +--> + +

+ +

You will note that the Connector element itself is commented out by default, +so you will need to remove the comment tags around it. Then, you can +customize the specified attributes as necessary. For detailed information +about the various options, consult the +Server Configuration Reference. The +following discussion covers only those attributes of most interest when +setting up SSL communication.

+ +

The port attribute (default value is 8443) is the TCP/IP +port number on which Tomcat will listen for secure connections. You can +change this to any port number you wish (such as to the default port for +https communications, which is 443). However, special setup +(outside the scope of this document) is necessary to run Tomcat on port +numbers lower than 1024 on many operating systems.

+ +
+

If you change the port number here, you should also change the + value specified for the redirectPort attribute on the + non-SSL connector. This allows Tomcat to automatically redirect + users who attempt to access a page with a security constraint specifying + that SSL is required, as required by the Servlet Specification.

+
+ +

There are additional options used to configure the SSL protocol. You may +need to add or change some attributes, depending on how you configured your +keystore earlier. If you are using a Java JSSE based SSL connector then +configuration options are documented in the +Java HTTP connector configuration +reference. If you are using the APR/native connector then refer to the +APR connector configuration guide for details of the +available configuration options.

+ +

After completing these configuration changes, you must restart Tomcat as +you normally do, and you should be in business. You should be able to access +any web application supported by Tomcat via SSL. For example, try:

+ +https://localhost:8443 + + +

and you should see the usual Tomcat splash page (unless you have modified +the ROOT web application). If this does not work, the following section +contains some troubleshooting tips.

+ +
+ +
+ +
+

To obtain and install a Certificate from a Certificate Authority (like verisign.com, thawte.com +or trustcenter.de), read the previous section and then follow these instructions:

+ + +

In order to obtain a Certificate from the Certificate Authority of your choice +you have to create a so called Certificate Signing Request (CSR). That CSR will be used +by the Certificate Authority to create a Certificate that will identify your website +as "secure". To create a CSR follow these steps:

+
    +
  • Create a local Certificate (as described in the previous section): + keytool -genkey -alias tomcat -keyalg RSA \ + -keystore <your_keystore_filename> + Note: In some cases you will have to enter the domain of your website (i.e. www.myside.org) + in the field "first- and lastname" in order to create a working Certificate. +
  • +
  • The CSR is then created with: + keytool -certreq -keyalg RSA -alias tomcat -file certreq.csr \ + -keystore <your_keystore_filename> +
  • +
+

Now you have a file called certreq.csr that you can submit to the Certificate Authority (look at the +documentation of the Certificate Authority website on how to do this). In return you get a Certificate.

+
+ + +

Now that you have your Certificate you can import it into you local keystore. +First of all you have to import a so called Chain Certificate or Root Certificate into your keystore. +After that you can proceed with importing your Certificate.

+ +
    +
  • Download a Chain Certificate from the Certificate Authority you obtained the Certificate from.
    + For Verisign.com commercial certificates go to: + http://www.verisign.com/support/install/intermediate.html
    + For Verisign.com trial certificates go to: + http://www.verisign.com/support/verisign-intermediate-ca/Trial_Secure_Server_Root/index.html
    + For Trustcenter.de go to: + http://www.trustcenter.de/certservices/cacerts/en/en.htm#server
    + For Thawte.com go to: + http://www.thawte.com/certs/trustmap.html
    +
  • +
  • Import the Chain Certificate into your keystore + keytool -import -alias root -keystore <your_keystore_filename> \ + -trustcacerts -file <filename_of_the_chain_certificate> +
  • +
  • And finally import your new Certificate + keytool -import -alias tomcat -keystore <your_keystore_filename> \ + -file <your_certificate_filename> +
  • +
+
+
+ +
+ +

Here is a list of common problems that you may encounter when setting up +SSL communications, and what to do about them.

+ +
    + +
  • I get "java.security.NoSuchAlgorithmException" errors in my + log files. +
    +

    The JVM cannot find the JSSE JAR files. Follow all of the directions to + download and install JSSE.

    +
  • + +
  • When Tomcat starts up, I get an exception like + "java.io.FileNotFoundException: {some-directory}/{some-file} not found". +
    +

    A likely explanation is that Tomcat cannot find the keystore file + where it is looking. By default, Tomcat expects the keystore file to + be named .keystore in the user home directory under which + Tomcat is running (which may or may not be the same as yours :-). If + the keystore file is anywhere else, you will need to add a + keystoreFile attribute to the <Factory> + element in the Tomcat + configuration file.

    +
  • + +
  • When Tomcat starts up, I get an exception like + "java.io.FileNotFoundException: Keystore was tampered with, or + password was incorrect". +
    +

    Assuming that someone has not actually tampered with + your keystore file, the most likely cause is that Tomcat is using + a different password than the one you used when you created the + keystore file. To fix this, you can either go back and + recreate the keystore + file, or you can add or update the keystorePass + attribute on the <Connector> element in the + Tomcat configuration + file. REMINDER - Passwords are case sensitive!

    +
  • + +
  • When Tomcat starts up, I get an exception like + "java.net.SocketException: SSL handshake errorjavax.net.ssl.SSLException: No + available certificate or key corresponds to the SSL cipher suites which are + enabled." +
    +

    A likely explanation is that Tomcat cannot find the alias for the server + key withinthe specified keystore. Check that the correct + keystoreFile and keyAlias are specified in the + <Connector> element in the + Tomcat configuration file. + REMINDER - keyAlias values may be case + sensitive!

    +
  • + +
+ +

If you are still having problems, a good source of information is the +TOMCAT-USER mailing list. You can find pointers to archives +of previous messages on this list, as well as subscription and unsubscription +information, at +http://tomcat.apache.org/lists.html.

+ +
+ +
+

This is a new feature in the Servlet 3.0 specification. Because it uses the + SSL session ID associated with the physical client-server connection there + are some limitations. They are: +

    +
  • Tomcat must have a connector with the attribute + isSecure set to true.
  • +
  • If SSL conections are managed by a proxy or a hardware accelerator + they must populate the SSL request headers (see the SSLValve) so that + the SSL session ID is visibale to Tomcat.
  • +
  • If Tomcat terminates the SSL connection, it will not be possible to use + session replication as the SSL session IDs will be different on each + node.
  • +
+

+ +

+ To enable SSL session tracking you need to use a context listener to set the + tracking mode for the context to be just SSL (if any other tracking mode is + enabled, it will be used in preference). It might look something like: + +package org.apache.tomcat.example; + +import java.util.EnumSet; + +import javax.servlet.ServletContext; +import javax.servlet.ServletContextEvent; +import javax.servlet.ServletContextListener; +import javax.servlet.SessionTrackingMode; + +public class SessionTrackingModeListener implements ServletContextListener { + + @Override + public void contextDestroyed(ServletContextEvent event) { + // Do nothing + } + + @Override + public void contextInitialized(ServletContextEvent event) { + ServletContext context = event.getServletContext(); + EnumSet<SessionTrackingMode> modes = + EnumSet.of(SessionTrackingMode.SSL); + + context.setSessionTrackingModes(modes); + } + +} + +

+

Note: SSL session tracking is implemented for the BIO and NIO connetcors. + It is not yet implemented for the APR connector.

+ +
+ +
+ +

To access the SSL session ID from the request, use:
+ + + String sslID = (String)request.getAttribute("javax.servlet.request.ssl_session"); + +
+For additional discussion on this area, please see +Bugzilla. +

+ +

To terminate an SSL session, use: + +// Standard HTTP session invalidation +session.invalidate(); + +// Invalidate the SSL Session +org.apache.tomcat.util.net.SSLSessionManager mgr = + (org.apache.tomcat.util.net.SSLSessionManager) + request.getAttribute("javax.servlet.request.ssl_session_mgr"); +mgr.invalidateSession(); + +// Close the conection since the SSL session will be active until the connection +// is closed +response.setHeader("Connection", "close"); + + Note that this code is Tomcat specific due to the use of the + SSLSessionManager class. This is currently only available for the BIO and + NIO conenctors, not the APR/native connector. +

+
+ + + +
\ No newline at end of file diff --git a/webapps/docs/tomcat-docs.xsl b/webapps/docs/tomcat-docs.xsl new file mode 100644 index 000000000000..f5551baf864b --- /dev/null +++ b/webapps/docs/tomcat-docs.xsl @@ -0,0 +1,531 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + <xsl:value-of select="project/title"/> (<xsl:value-of select="$version"/>) - <xsl:value-of select="properties/title"/> + + + + + + + + + + + + + + + + + + PAGE HEADER + + + + + +
+ + + + + + + + + + + + PROJECT LOGO + + {$alt} + + + + +

+ Version , +
+
+ APACHE LOGO + + + + + Apache Logo + +
+ + + + HEADER SEPARATOR + + + + + + + LEFT SIDE NAVIGATION + + + RIGHT SIDE MAIN BODY + + + + + FOOTER SEPARATOR + + + + + PAGE FOOTER + + +
+
+
+ + +

+ +
+
+
+
+ Copyright © 1999-, Apache Software Foundation +
+
+ + + +
+ + + + +

+
    + +
+
+ + + + + + + +
  • +
    + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + () + + + + + +
    + + 2 + +
    + +
    +
    + + + + + + + + + + + + + + + + + + + + + + + + + +
    + + () + + +
    + +
    +
    + + + + +
    +
    + + + + + + + + + + + + + + + + + + +
  • + +
    +
    +
  • +
    + + + + + + + +
    + + + + + + + + + + + + + + + + +
    + + + + + +
    + +
    +            
    +          
    + +
    + + + + + +
    +
    +
    + + + + + + + + + + + + + + + +
    + Attribute + + Description +
    + + + + + + + + +
    +
    + + + + + + + + + + + + + + +
    + Property + + Description +
    + + + +
    +
    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    +
    + + + + /images/add.gif + add + + + + + + + /images/update.gif + update + + + + + + + /images/design.gif + design + + + + + + + /images/docs.gif + docs + + + + + + + /images/fix.gif + fix + + + + + + + /images/code.gif + code + + + + + + + + + + + + + + + + + + + +
    + Priority + + Action Item + + Volunteers +
    + + + + + +
    +
    + + + + + + + + + + + r + + + + + + + + + +
    diff --git a/webapps/docs/tribes/faq.xml b/webapps/docs/tribes/faq.xml new file mode 100644 index 000000000000..932b3faf2ba2 --- /dev/null +++ b/webapps/docs/tribes/faq.xml @@ -0,0 +1,37 @@ + + + +]> + + + &project; + + + Filip Hanik + Apache Tribes - Frequently Asked Questions + + + + + +
    +
    + + +
    diff --git a/webapps/docs/tribes/introduction.xml b/webapps/docs/tribes/introduction.xml new file mode 100644 index 000000000000..3fcbeb29dc26 --- /dev/null +++ b/webapps/docs/tribes/introduction.xml @@ -0,0 +1,276 @@ + + + +]> + + + &project; + + + Filip Hanik + Apache Tribes - Introduction + + + + +
    + +
    + +
    + +

    Apache Tribes is a group or peer-to-peer communication framework that enables you to easily connect + your remote objects to communicate with each other. +

    +
      +
    • Import: org.apache.catalina.tribes.Channel
    • +
    • Import: org.apache.catalina.tribes.Member
    • +
    • Import: org.apache.catalina.tribes.MembershipListener
    • +
    • Import: org.apache.catalina.tribes.ChannelListener
    • +
    • Import: org.apache.catalina.tribes.group.GroupChannel
    • +
    • Create a class that implements: org.apache.catalina.tribes.ChannelListener
    • +
    • Create a class that implements: org.apache.catalina.tribes.MembershipListener
    • +
    • Simple class to demonstrate how to send a message: + + //create a channel + Channel myChannel = new GroupChannel(); + + //create my listeners + ChannelListener msgListener = new MyMessageListener(); + MembershipListener mbrListener = new MyMemberListener(); + + //attach the listeners to the channel + myChannel.addMembershipListener(mbrListener); + myChannel.addChannelListener(msgListener); + + //start the channel + myChannel.start(Channel.DEFAULT); + + //create a message to be sent, message must implement java.io.Serializable + //for performance reasons you probably want them to implement java.io.Externalizable + Serializable myMsg = new MyMessage(); + + //retrieve my current members + Member[] group = myChannel.getMembers(); + + //send the message + channel.send(group,myMsg,Channel.SEND_OPTIONS_DEFAULT); + +
    • +
    +

    + Simple yeah? There is a lot more to Tribes than we have shown, hopefully the docs will be able + to explain more to you. Remember, that we are always interested in suggestions, improvements, bug fixes + and anything that you think would help this project. +

    +

    + Note: Tribes is currently built for JDK1.5, you can run on JDK1.4 by a small modifications to locks used from the java.util.concurrent package. +

    +
    + + +
    +

    + Tribes is a messaging framework with group communication abilities. Tribes allows you to send and receive + messages over a network, it also allows for dynamic discovery of other nodes in the network.
    + And that is the short story, it really is as simple as that. What makes Tribes useful and unique will be + described in the section below.
    +

    +

    + The Tribes module was started early 2006 and a small part of the code base comes from the clustering module + that has been existing since 2003 or 2004. + The current cluster implementation has several short comings and many workarounds were created due + to the complexity in group communication. Long story short, what should have been two modules a long time + ago, will be now. Tribes takes out the complexity of messaging from the replication module and becomes + a fully independent and highly flexible group communication module.
    +

    +

    + In Tomcat the old modules/cluster has now become modules/groupcom(Tribes) and + modules/ha (replication). This will allow development to proceed and let the developers + focus on the issues they are actually working on rather than getting boggled down in details of a module + they are not interested in. The understanding is that both communication and replication are complex enough, + and when trying to develop them in the same module, well you know, it becomes a cluster :)
    +

    +

    + Tribes allows for guaranteed messaging, and can be customized in many ways. Why is this important?
    + Well, you as a developer want to know that the messages you are sending are reaching their destination. + More than that, if a message doesn't reach its destination, the application on top of Tribes will be notified + that the message was never sent, and what node it failed. +

    + +
    + +
    +

    + I am a big fan of reusing code and would never dream of developing something if someone else has already + done it and it was available to me and the community I try to serve.
    + When I did my research to improve the clustering module I was constantly faced with a few obstacles:
    + 1. The framework wasn't flexible enough
    + 2. The framework was licensed in a way that neither I nor the community could use it
    + 3. Several features that I needed were missing
    + 4. Messaging was guaranteed, but no feedback was reported to me
    + 5. The semantics of my message delivery had to be configured before runtime
    + And the list continues... +

    +

    + So I came up with Tribes, to address these issues and other issues that came along. + When designing Tribes I wanted to make sure I didn't lose any of the flexibility and + delivery semantics that the existing frameworks already delivered. The goal was to create a framework + that could do everything that the others already did, but to provide more flexibility for the application + developer. In the next section will give you the high level overview of what features tribes offers or will offer. +

    +
    + +
    +

    + To give you an idea of the feature set I will list it out here. + Some of the features are not yet completed, if that is the case they are marked accordingly. +

    +

    + Pluggable modules
    + Tribes is built using interfaces. Any of the modules or components that are part of Tribes can be swapped out + to customize your own Tribes implementation. +

    +

    + Guaranteed Messaging
    + In the default implementation of Tribes uses TCP or UDP for messaging. TCP already has guaranteed message delivery + and flow control built in. I believe that the performance of Java TCP, will outperform an implementation of + Java/UDP/flow-control/message guarantee since the logic happens further down the stack. UDP messaging has been added in for + sending messages over UDP instead of TCP when desired. The same guarantee scenarios as described below are still available + over UDP, however, when a UDP message is lost, it's considered failed.
    + Tribes supports both non-blocking and blocking IO operations. The recommended setting is to use non blocking + as it promotes better parallelism when sending and receiving messages. The blocking implementation is available + for those platforms where NIO is still a trouble child. +

    +

    + Different Guarantee Levels
    + There are three different levels of delivery guarantee when a message is sent.
    +

      +
    1. IO Based send guarantee. - fastest, least reliable
      + This means that Tribes considers the message transfer to be successful + if the message was sent to the socket send buffer and accepted.
      + On blocking IO, this would be socket.getOutputStream().write(msg)
      + On non blocking IO, this would be socketChannel.write(), and the buffer byte buffer gets emptied + followed by a socketChannel.read() to ensure the channel still open. + The read() has been added since write() will succeed if the connection has been "closed" + when using NIO. +
    2. +
    3. ACK based. - recommended, guaranteed delivery
      + When the message has been received on a remote node, an ACK is sent back to the sender, + indicating that the message was received successfully. +
    4. +
    5. SYNC_ACK based. - guaranteed delivery, guaranteed processed, slowest
      + When the message has been received on a remote node, the node will process + the message and if the message was processed successfully, an ACK is sent back to the sender + indicating that the message was received and processed successfully. + If the message was received, but processing it failed, an ACK_FAIL will be sent back + to the sender. This is a unique feature that adds an incredible amount value to the application + developer. Most frameworks here will tell you that the message was delivered, and the application + developer has to build in logic on whether the message was actually processed properly by the application + on the remote node. If configured, Tribes will throw an exception when it receives an ACK_FAIL + and associate that exception with the member that didn't process the message. +
    6. +
    + You can of course write even more sophisticated guarantee levels, and some of them will be mentioned later on + in the documentation. One mentionable level would be a 2-Phase-Commit, where the remote applications don't receive + the message until all nodes have received the message. Sort of like a all-or-nothing protocol. +

    +

    + Per Message Delivery Attributes
    + Perhaps the feature that makes Tribes stand out from the crowd of group communication frameworks. + Tribes enables you to send to decide what delivery semantics a message transfer should have on a per + message basis. Meaning, that your messages are not delivered based on some static configuration + that remains fixed after the message framework has been started.
    + To give you an example of how powerful this feature is, I'll try to illustrate it with a simple example. + Imagine you need to send 10 different messages, you could send the the following way: + + Message_1 - asynchronous and fast, no guarantee required, fire and forget + Message_2 - all-or-nothing, either all receivers get it, or none. + Message_3 - encrypted and SYNC_ACK based + Message_4 - asynchronous, SYNC_ACK and call back when the message is processed on the remote nodes + Message_5 - totally ordered, this message should be received in the same order on all nodes that have been + send totally ordered + Message_6 - asynchronous and totally ordered + Message_7 - RPC message, send a message, wait for all remote nodes to reply before returning + Message_8 - RPC message, wait for the first reply + Message_9 - RPC message, asynchronous, don't wait for a reply, collect them via a callback + Message_10- sent to a member that is not part of this group + + As you can imagine by now, these are just examples. The number of different semantics you can apply on a + per-message-basis is almost limitless. Tribes allows you to set up to 28 different on a message + and then configure Tribes to what flag results in what action on the message.
    + Imagine a shared transactional cache, probably >90% are reads, and the dirty reads should be completely + unordered and delivered as fast as possible. But transactional writes on the other hand, have to + be ordered so that no cache gets corrupted. With tribes you would send the write messages totally ordered, + while the read messages you simple fire to achieve highest throughput.
    + There are probably better examples on how this powerful feature can be used, so use your imagination and + your experience to think of how this could benefit you in your application. +

    +

    + Interceptor based message processing
    + Tribes uses a customizable interceptor stack to process messages that are sent and received.
    + So what, all frameworks have this!
    + Yes, but in Tribes interceptors can react to a message based on the per-message-attributes + that are sent runtime. Meaning, that if you add a encryption interceptor that encrypts message + you can decide if this interceptor will encrypt all messages, or only certain messages that are decided + by the applications running on top of Tribes.
    + This is how Tribes is able to send some messages totally ordered and others fire and forget style + like the example above.
    + The number of interceptors that are available will keep growing, and we would appreciate any contributions + that you might have. +

    +

    + Threadless Interceptor stack + The interceptor don't require any separate threads to perform their message manipulation.
    + Messages that are sent will piggy back on the thread that is sending them all the way through transmission. + The exception is the MessageDispatchInterceptor that will queue up the message + and send it on a separate thread for asynchronous message delivery. + Messages received are controlled by a thread pool in the receiver component.
    + The channel object can send a heartbeat() through the interceptor stack to allow + for timeouts, cleanup and other events.
    + The MessageDispatchInterceptor is the only interceptor that is configured by default. +

    +

    + Parallel Delivery
    + Tribes support parallel delivery of messages. Meaning that node_A could send three messages to node_B in + parallel. This feature becomes useful when sending messages with different delivery semantics. + Otherwise if Message_1 was sent totally ordered, Message_2 would have to wait for that message to complete.
    + Through NIO, Tribes is also able to send a message to several receivers at the same time on the same thread. +

    +

    + Silent Member Messaging
    + With Tribes you are able to send messages to members that are not in your group. + So by default, you can already send messages over a wide area network, even though the dynamic discover + module today is limited to local area networks by using multicast for dynamic node discovery. + Of course, the membership component will be expanded to support WAN memberships in the future. + But this is very useful, when you want to hide members from the rest of the group and only communicate with them +

    +
    + +
    +

    + Tribes ships as a module with Tomcat, and is released as part of the Apache Tomcat release. +

    + + +
    + + + +
    diff --git a/webapps/docs/tribes/leader-election-initiate-election.dia b/webapps/docs/tribes/leader-election-initiate-election.dia new file mode 100644 index 000000000000..f64c84302049 Binary files /dev/null and b/webapps/docs/tribes/leader-election-initiate-election.dia differ diff --git a/webapps/docs/tribes/leader-election-initiate-election.jpg b/webapps/docs/tribes/leader-election-initiate-election.jpg new file mode 100644 index 000000000000..3e8c11cd6462 Binary files /dev/null and b/webapps/docs/tribes/leader-election-initiate-election.jpg differ diff --git a/webapps/docs/tribes/leader-election-message-arrives.dia b/webapps/docs/tribes/leader-election-message-arrives.dia new file mode 100644 index 000000000000..41fa5300db4e Binary files /dev/null and b/webapps/docs/tribes/leader-election-message-arrives.dia differ diff --git a/webapps/docs/tribes/leader-election-message-arrives.jpg b/webapps/docs/tribes/leader-election-message-arrives.jpg new file mode 100644 index 000000000000..4733d2d1b3ca Binary files /dev/null and b/webapps/docs/tribes/leader-election-message-arrives.jpg differ diff --git a/webapps/docs/tribes/project.xml b/webapps/docs/tribes/project.xml new file mode 100644 index 000000000000..467256fd1780 --- /dev/null +++ b/webapps/docs/tribes/project.xml @@ -0,0 +1,54 @@ + + + + + Apache Tribes - The Tomcat Cluster Communication Module + + Apache Tomcat + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/webapps/docs/tribes/setup.xml b/webapps/docs/tribes/setup.xml new file mode 100644 index 000000000000..cc9c2dd78bb5 --- /dev/null +++ b/webapps/docs/tribes/setup.xml @@ -0,0 +1,37 @@ + + + +]> + + + &project; + + + Filip Hanik + Apache Tribes - Configuration + + + + + +
    +
    + + +
    diff --git a/webapps/docs/tribes/tomcat-docs.xsl b/webapps/docs/tribes/tomcat-docs.xsl new file mode 100644 index 000000000000..e7176dc3e953 --- /dev/null +++ b/webapps/docs/tribes/tomcat-docs.xsl @@ -0,0 +1,452 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + <xsl:value-of select="project/title"/> - <xsl:value-of select="properties/title"/> + + + + + + + + + + + + + + + + + PAGE HEADER + + + + + +
    + + + + + + + + + + + + PROJECT LOGO + + {$alt} + + + + +

    +
    +
    + APACHE LOGO + + + + + Apache Logo + +
    + + + + HEADER SEPARATOR + + + + + + + + + LEFT SIDE NAVIGATION + + + + RIGHT SIDE MAIN BODY + + + + + FOOTER SEPARATOR + + + + + PAGE FOOTER + + +
    +
    +
    + + + + + + + +
    +

    +

    +
    + + + + + + + + + + + Printer Friendly Version +
    print-friendly
    version +
    +
    +
    + + + + + + +
    + +
    +
    +
    +
    + Copyright © 1999-2010, Apache Software Foundation +
    +
    + + + +
    + + + + +

    +
      + +
    +
    + + + + + + + +
  • +
    + + + + + + + + + + + + +
    + + + +
    + +
    +
    + + + + + + + + + + + + +
    + + + +
    + +
    +
    + + + + + + + +
    + + + + + + + + + + + + + + + + +
    + + + + + +
    + +
    +            
    +          
    + +
    + + + + + +
    +
    +
    + + + + + + + + + + + + + + + +
    + Attribute + + Description +
    + + + + + + + + +
    +
    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    +
    + + + + /images/add.gif + add + + + + + + + /images/update.gif + update + + + + + + + /images/design.gif + design + + + + + + + /images/docs.gif + docs + + + + + + + /images/fix.gif + fix + + + + + + + /images/code.gif + code + + + + + + + + + + + + + + + + + + + +
    + Priority + + Action Item + + Volunteers +
    + + + + + +
    +
    + + + + + + + + + + + + + + +
    diff --git a/webapps/docs/virtual-hosting-howto.xml b/webapps/docs/virtual-hosting-howto.xml new file mode 100644 index 000000000000..dc225d70216e --- /dev/null +++ b/webapps/docs/virtual-hosting-howto.xml @@ -0,0 +1,143 @@ + + + +]> + + + &project; + + + Virtual Hosting and Tomcat + + + + +
    + +
    + +
    +

    + For the sake of this how-to, assume you have a development host with two + host names, ren and stimpy. Let's also assume + one instance of Tomcat running, so $CATALINA_HOME refers to + wherever it's installed, perhaps /usr/local/tomcat. +

    +

    + Also, this how-to uses Unix-style path separators and commands; if you're + on Windows modify accordingly. +

    +
    + +
    +

    + At the simplest, edit the Engine portion + of your server.xml file to look like this: +

    + +<Engine name="Catalina" defaultHost="ren"> + <Host name="ren" appBase="renapps"/> + <Host name="stimpy" appBase="stimpyapps"/> +</Engine> + +

    + Note that the directory structures under the appBase for each host should + not overlap each other. +

    +

    + Consult the configuration documentation for other attributes of the + Engine and + Host elements. +

    +
    + +
    +

    + Create directories for each of the virtual hosts: +

    + +mkdir $CATALINA_HOME/renapps +mkdir $CATALINA_HOME/stimpyapps + +
    + +
    + +

    Contexts are normally located underneath the appBase directory. For + example, to deploy the foobar context as a war file in + the ren host, use + $CATALINA_HOME/renapps/foobar.war. Note that the + default or ROOT context for ren would be deployed as + $CATALINA_HOME/renapps/ROOT.war (WAR) or + $CATALINA_HOME/renapps/ROOT (directory). +

    +

    NOTE: The docBase for a context should never be + the same as the appBase for a host. +

    +
    + +

    + Within your Context, create a META-INF directory and then + place your Context definition in it in a file named + context.xml. i.e. + $CATALINA_HOME/renapps/ROOT/META-INF/context.xml + This makes deployment easier, particularly if you're distributing a WAR + file. +

    +
    + +

    + Create a structure under $CATALINA_HOME/conf/Catalina + corresponding to your virtual hosts, e.g.: +

    + +mkdir $CATALINA_HOME/conf/Catalina/ren +mkdir $CATALINA_HOME/conf/Catalina/stimpy + +

    + Note that the ending directory name "Catalina" represents the + name attribute of the + Engine element as shown above. +

    +

    + Now, for your default webapps, add: +

    + +$CATALINA_HOME/conf/Catalina/ren/ROOT.xml +$CATALINA_HOME/conf/Catalina/stimpy/ROOT.xml + +

    + If you want to use the Tomcat manager webapp for each host, you'll also + need to add it here: +

    + +cd $CATALINA_HOME/conf/Catalina +cp localhost/manager.xml ren/ +cp localhost/manager.xml stimpy/ + +
    + +

    + Consult the configuration documentation for other attributes of the + Context element. +

    +
    +
    + +
    diff --git a/webapps/docs/windows-service-howto.xml b/webapps/docs/windows-service-howto.xml new file mode 100644 index 000000000000..d8b190c4f31e --- /dev/null +++ b/webapps/docs/windows-service-howto.xml @@ -0,0 +1,381 @@ + + + +]> + + + &project; + + + Mladen Turk + Windows service HOW-TO + + + + +
    + +
    + +
    +

    + Tomcat7 is a service application for running Tomcat7 as NT service. +

    +
    +
    +

    + Tomcat7w is a GUI application for monitoring and configuring Tomcat + services. +

    +

    The available command line options are:

    +

    + + + + + + + + + +
    //ES//Edit service configurationThis is the default operation. It is called if the no option is + provided but the executable is renamed to servicenameW.exe
    //MS//Monitor servicePut the icon in the system try
    +

    +
    +
    +

    + Each command line directive is in the form of //XX//ServiceName +

    +

    The available command line options are:

    +

    + + + + + + + + + + + + + + + + + + + + + + + + + +
    //TS//Run the service as console applicationThis is the default operation. It is called if the no option is + provided. The ServiceName is the name of the executable without + exe suffix, meaning Tomcat7
    //RS//Run the serviceCalled only from ServiceManager
    //SS//Stop the service
    //US//Update service parameters
    //IS//Install service
    //DS//Delete serviceStops the service if running
    +

    +
    +
    +

    + Each command parameter is prefixed with --. + If the command line is prefixed with ++ then it's value will + be appended to the existing option. + If the environment variable with the same name as command line parameter but + prefixed with PR_ exists it will take precedence. + For example: +set PR_CLASSPATH=xx.jar +

    +

    is equivalent to providing +--Classpath=xx.jar +

    +

    as command line parameter.

    +

    Note: PR_DEPENDSON, PR_ENVIRONMENT, PR_JVMOPTIONS, + PR_JVMMS, PR_JVMMX, PR_JVMSS, PR_STARTPARAMS, PR_STOPPARAMS and + PR_STOPTIMEOUT will not work until this bug is fixed: + DAEMON-49

    +

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    ParameterNameDefaultDescription
    --DescriptionService name description (maximum 1024 characters)
    --DisplayNameServiceNameService display name
    --Installprocrun.exe //RS//ServiceNameInstall image
    --StartupmanualService startup mode can be either auto or manual
    --DependsOnList of services that this service depend on. Dependent services + are separated using either # or ; characters
    --EnvironmentList of environment variables that will be provided to the service + in the form key=value. They are separated using either + # or ; characters
    --UserUser account used for running executable. It is used only for + StartMode java or exe and enables running applications + as service under account without LogonAsService privilege.
    --PasswordPassword for user account set by --User parameter
    --JavaHomeJAVA_HOMESet a different JAVA_HOME then defined by JAVA_HOME environment + variable
    --JvmautoUse either auto or specify the full path to the jvm.dll. + You can use the environment variable expansion here.
    --JvmOptions-XrsList of options in the form of -D or -X that will be + passed to the JVM. The options are separated using either + # or ; characters.
    --ClasspathSet the Java classpath
    --JvmMsInitial memory pool size in MB
    --JvmMxMaximum memory pool size in MB
    --JvmSsThread stack size in KB
    --StartImageExecutable that will be run.
    --StartPathWorking path for the start image executable.
    --StartClassClass that will be used for startup.
    --StartParamsList of parameters that will be passed to either StartImage or + StartClass. Parameters are separated using either # or + ; character.
    --StartMethodMainMethod name if differs then main
    --StartModeexecutableCan one of jvm java or exe
    --StopImageExecutable that will be run on Stop service signal.
    --StopPathWorking path for the stop image executable.
    --StopClassClass that will be used on Stop service signal.
    --StopParamsList of parameters that will be passed to either StopImage or + StopClass. Parameters are separated using either # or + ; character.
    --StopMethodMainMethod name if differs then main
    --StopModeexecutableCan one of jvm java or exe
    --StopTimeoutNo TimeoutDefines the timeout in seconds that procrun waits for service to + exit gracefully.
    --LogPathworking pathDefines the path for logging
    --LogPrefixjakarta_serviceDefines the service log filename
    --LogLevelINFODefines the logging level and can be either error, + info, warn or debug
    --StdOutputRedirected stdout filename
    --StdErrorRedirected stderr filename
    +

    +
    +
    +

    +The safest way to manually install the service is to use the provided +service.bat script. Administrator privileges are required to run this +script. If necessary, you can use the /user switch to specify +a user to use for the installation of the service. +

    +

    +NOTE: On Windows Vista or any other operating system with User +Account Control (UAC) you must either disable UAC or right-click on cmd.exe and +select "Run as administrator" in order to run this script. If UAC is enabled +neither being logged on with an Administrator account, nor using the +/user switch is sufficient. +

    +

    + +Install the service named 'Tomcat7' +C:\> service.bat install + +

    +

    +If using tomcat7.exe, you need to use the //IS// parameter. +

    +

    + +Install the service named 'Tomcat7' +C:\> tomcat7 //IS//Tomcat7 --DisplayName="Apache Tomcat 7" \ +C:\> --Install="C:\Program Files\Tomcat\bin\tomcat7.exe" --Jvm=auto \ +C:\> --StartMode=jvm --StopMode=jvm \ +C:\> --StartClass=org.apache.catalina.startup.Bootstrap --StartParams=start \ +C:\> --StopClass=org.apache.catalina.startup.Bootstrap --StopParams=stop + +

    +
    +
    +

    +To update the service parameters, you need to use the //US// parameter. +

    +

    + +Update the service named 'Tomcat7' +C:\> tomcat7 //US//Tomcat7 --Description="Apache Tomcat Server - http://tomcat.apache.org/ " \ +C:\> --Startup=auto --Classpath=%JAVA_HOME%\lib\tools.jar;%CATALINA_HOME%\bin\bootstrap.jar + +

    +
    +
    +

    +To remove the service, you need to use the //DS// parameter.
    +If the service is running it will be stopped and then deleted. +

    +

    + +Remove the service named 'Tomcat7' +C:\> tomcat7 //DS//Tomcat7 + +

    +
    +
    +

    +To run the service in console mode, you need to use the //TS// parameter. +The service shutdown can be initiated by pressing CTRL+C or +CTRL+BREAK. +If you rename the tomcat7.exe to testservice.exe then you can just execute the +testservice.exe and this command mode will be executed by default. +

    +

    + +Run the service named 'Tomcat7' in console mode +C:\> tomcat7 //TS//Tomcat7 [additional arguments] +Or simply execute: +C:\> tomcat7 + +

    +
    + +
    diff --git a/webapps/examples/WEB-INF/classes/CookieExample.java b/webapps/examples/WEB-INF/classes/CookieExample.java new file mode 100644 index 000000000000..c49abeabda79 --- /dev/null +++ b/webapps/examples/WEB-INF/classes/CookieExample.java @@ -0,0 +1,130 @@ +/* +* Licensed to the Apache Software Foundation (ASF) under one or more +* contributor license agreements. See the NOTICE file distributed with +* this work for additional information regarding copyright ownership. +* The ASF licenses this file to You under the Apache License, Version 2.0 +* (the "License"); you may not use this file except in compliance with +* the License. You may obtain a copy of the License at +* +* http://www.apache.org/licenses/LICENSE-2.0 +* +* Unless required by applicable law or agreed to in writing, software +* distributed under the License is distributed on an "AS IS" BASIS, +* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +* See the License for the specific language governing permissions and +* limitations under the License. +*/ +/* $Id$ + * + */ + +import java.io.IOException; +import java.io.PrintWriter; +import java.util.ResourceBundle; + +import javax.servlet.ServletException; +import javax.servlet.http.Cookie; +import javax.servlet.http.HttpServlet; +import javax.servlet.http.HttpServletRequest; +import javax.servlet.http.HttpServletResponse; + +import util.HTMLFilter; + +/** + * Example servlet showing request headers + * + * @author James Duncan Davidson + */ + +public class CookieExample extends HttpServlet { + + private static final long serialVersionUID = 1L; + + private static final ResourceBundle RB = ResourceBundle.getBundle("LocalStrings"); + + @Override + public void doGet(HttpServletRequest request, + HttpServletResponse response) + throws IOException, ServletException + { + response.setContentType("text/html"); + + PrintWriter out = response.getWriter(); + out.println(""); + out.println(""); + out.println(""); + + String title = RB.getString("cookies.title"); + out.println("" + title + ""); + out.println(""); + out.println(""); + + // relative links + + // XXX + // making these absolute till we work out the + // addition of a PathInfo issue + + out.println(""); + out.println("\"view"); + out.println(""); + out.println("\"return\""); + + out.println("

    " + title + "

    "); + + Cookie[] cookies = request.getCookies(); + if ((cookies != null) && (cookies.length > 0)) { + out.println(RB.getString("cookies.cookies") + "
    "); + for (int i = 0; i < cookies.length; i++) { + Cookie cookie = cookies[i]; + out.print("Cookie Name: " + HTMLFilter.filter(cookie.getName()) + + "
    "); + out.println(" Cookie Value: " + + HTMLFilter.filter(cookie.getValue()) + + "

    "); + } + } else { + out.println(RB.getString("cookies.no-cookies")); + } + + String cookieName = request.getParameter("cookiename"); + String cookieValue = request.getParameter("cookievalue"); + if (cookieName != null && cookieValue != null) { + Cookie cookie = new Cookie(cookieName, cookieValue); + response.addCookie(cookie); + out.println("

    "); + out.println(RB.getString("cookies.set") + "
    "); + out.print(RB.getString("cookies.name") + " " + + HTMLFilter.filter(cookieName) + "
    "); + out.print(RB.getString("cookies.value") + " " + + HTMLFilter.filter(cookieValue)); + } + + out.println("

    "); + out.println(RB.getString("cookies.make-cookie") + "
    "); + out.print("

    "); + out.print(RB.getString("cookies.name") + " "); + out.println("
    "); + out.print(RB.getString("cookies.value") + " "); + out.println("
    "); + out.println("
    "); + + + out.println(""); + out.println(""); + } + + @Override + public void doPost(HttpServletRequest request, + HttpServletResponse response) + throws IOException, ServletException + { + doGet(request, response); + } + +} + + diff --git a/webapps/examples/WEB-INF/classes/HelloWorldExample.java b/webapps/examples/WEB-INF/classes/HelloWorldExample.java new file mode 100644 index 000000000000..f44cee0af2a7 --- /dev/null +++ b/webapps/examples/WEB-INF/classes/HelloWorldExample.java @@ -0,0 +1,82 @@ + +/* +* Licensed to the Apache Software Foundation (ASF) under one or more +* contributor license agreements. See the NOTICE file distributed with +* this work for additional information regarding copyright ownership. +* The ASF licenses this file to You under the Apache License, Version 2.0 +* (the "License"); you may not use this file except in compliance with +* the License. You may obtain a copy of the License at +* +* http://www.apache.org/licenses/LICENSE-2.0 +* +* Unless required by applicable law or agreed to in writing, software +* distributed under the License is distributed on an "AS IS" BASIS, +* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +* See the License for the specific language governing permissions and +* limitations under the License. +*/ +/* $Id$ + * + */ + +import java.io.IOException; +import java.io.PrintWriter; +import java.util.ResourceBundle; + +import javax.servlet.ServletException; +import javax.servlet.http.HttpServlet; +import javax.servlet.http.HttpServletRequest; +import javax.servlet.http.HttpServletResponse; + +/** + * The simplest possible servlet. + * + * @author James Duncan Davidson + */ + +public class HelloWorldExample extends HttpServlet { + + private static final long serialVersionUID = 1L; + + @Override + public void doGet(HttpServletRequest request, + HttpServletResponse response) + throws IOException, ServletException + { + ResourceBundle rb = + ResourceBundle.getBundle("LocalStrings",request.getLocale()); + response.setContentType("text/html"); + PrintWriter out = response.getWriter(); + + out.println(""); + out.println(""); + + String title = rb.getString("helloworld.title"); + + out.println("" + title + ""); + out.println(""); + out.println(""); + + // note that all links are created to be relative. this + // ensures that we can move the web application that this + // servlet belongs to to a different place in the url + // tree and not have any harmful side effects. + + // XXX + // making these absolute till we work out the + // addition of a PathInfo issue + + out.println(""); + out.println("\"view"); + out.println(""); + out.println("\"return\""); + out.println("

    " + title + "

    "); + out.println(""); + out.println(""); + } +} + + + diff --git a/webapps/examples/WEB-INF/classes/LocalStrings.properties b/webapps/examples/WEB-INF/classes/LocalStrings.properties new file mode 100644 index 000000000000..ff95cd1e224c --- /dev/null +++ b/webapps/examples/WEB-INF/classes/LocalStrings.properties @@ -0,0 +1,53 @@ +# Licensed to the Apache Software Foundation (ASF) under one or more +# contributor license agreements. See the NOTICE file distributed with +# this work for additional information regarding copyright ownership. +# The ASF licenses this file to You under the Apache License, Version 2.0 +# (the "License"); you may not use this file except in compliance with +# the License. You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. + +# $Id$ + +# Default localized resources for example servlets +# This locale is en_US + +helloworld.title=Hello World! + +requestinfo.title=Request Information Example +requestinfo.label.method=Method: +requestinfo.label.requesturi=Request URI: +requestinfo.label.protocol=Protocol: +requestinfo.label.pathinfo=Path Info: +requestinfo.label.remoteaddr=Remote Address: + +requestheader.title=Request Header Example + +requestparams.title=Request Parameters Example +requestparams.params-in-req=Parameters in this request: +requestparams.no-params=No Parameters, Please enter some +requestparams.firstname=First Name: +requestparams.lastname=Last Name: + +cookies.title=Cookies Example +cookies.cookies=Your browser is sending the following cookies: +cookies.no-cookies=Your browser isn't sending any cookies +cookies.make-cookie=Create a cookie to send to your browser +cookies.name=Name: +cookies.value=Value: +cookies.set=You just sent the following cookie to your browser: + +sessions.title=Sessions Example +sessions.id=Session ID: +sessions.created=Created: +sessions.lastaccessed=Last Accessed: +sessions.data=The following data is in your session: +sessions.adddata=Add data to your session +sessions.dataname=Name of Session Attribute: +sessions.datavalue=Value of Session Attribute: diff --git a/webapps/examples/WEB-INF/classes/LocalStrings_en.properties b/webapps/examples/WEB-INF/classes/LocalStrings_en.properties new file mode 100644 index 000000000000..ff95cd1e224c --- /dev/null +++ b/webapps/examples/WEB-INF/classes/LocalStrings_en.properties @@ -0,0 +1,53 @@ +# Licensed to the Apache Software Foundation (ASF) under one or more +# contributor license agreements. See the NOTICE file distributed with +# this work for additional information regarding copyright ownership. +# The ASF licenses this file to You under the Apache License, Version 2.0 +# (the "License"); you may not use this file except in compliance with +# the License. You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. + +# $Id$ + +# Default localized resources for example servlets +# This locale is en_US + +helloworld.title=Hello World! + +requestinfo.title=Request Information Example +requestinfo.label.method=Method: +requestinfo.label.requesturi=Request URI: +requestinfo.label.protocol=Protocol: +requestinfo.label.pathinfo=Path Info: +requestinfo.label.remoteaddr=Remote Address: + +requestheader.title=Request Header Example + +requestparams.title=Request Parameters Example +requestparams.params-in-req=Parameters in this request: +requestparams.no-params=No Parameters, Please enter some +requestparams.firstname=First Name: +requestparams.lastname=Last Name: + +cookies.title=Cookies Example +cookies.cookies=Your browser is sending the following cookies: +cookies.no-cookies=Your browser isn't sending any cookies +cookies.make-cookie=Create a cookie to send to your browser +cookies.name=Name: +cookies.value=Value: +cookies.set=You just sent the following cookie to your browser: + +sessions.title=Sessions Example +sessions.id=Session ID: +sessions.created=Created: +sessions.lastaccessed=Last Accessed: +sessions.data=The following data is in your session: +sessions.adddata=Add data to your session +sessions.dataname=Name of Session Attribute: +sessions.datavalue=Value of Session Attribute: diff --git a/webapps/examples/WEB-INF/classes/LocalStrings_es.properties b/webapps/examples/WEB-INF/classes/LocalStrings_es.properties new file mode 100644 index 000000000000..f68299efe092 --- /dev/null +++ b/webapps/examples/WEB-INF/classes/LocalStrings_es.properties @@ -0,0 +1,53 @@ +# Licensed to the Apache Software Foundation (ASF) under one or more +# contributor license agreements. See the NOTICE file distributed with +# this work for additional information regarding copyright ownership. +# The ASF licenses this file to You under the Apache License, Version 2.0 +# (the "License"); you may not use this file except in compliance with +# the License. You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. + +# $Id$ +# +# Default localized string information +# Localized para Locale es_ES + +helloworld.title=Hola Mundo! + +requestinfo.title=Ejemplo de Informacion de Request +requestinfo.label.method=Metodo: +requestinfo.label.requesturi=Request URI: +requestinfo.label.protocol=Protocolo: +requestinfo.label.pathinfo=Path Info: +requestinfo.label.remoteaddr=Direccion Remota: + +requestheader.title=Ejemplo de Cabecera de Request + +requestparams.title=Ejemplo de parametros de Request +requestparams.params-in-req=Parametros en este Request: +requestparams.no-params=No hay parametro. por favor usa alguno +requestparams.firstname=Nombre: +requestparams.lastname=Apellidos: + +cookies.title=Ejemplo de Cookies +cookies.cookies=Tu navegador esta enviando los siguientes cookies: +cookies.no-cookies=Tu navegador no esta enviando cookies +cookies.make-cookie=Crea un cookie para enviarlo a tu navegador +cookies.name=Nombre: +cookies.value=Valor: +cookies.set=Acabas de enviar a tu navegador estos cookies: + +sessions.title=ejemplo de Sesiones +sessions.id=ID de Sesion: +sessions.created=Creado: +sessions.lastaccessed=Ultimo Acceso: +sessions.data=Lo siguientes datos estan en tu sesion: +sessions.adddata=A\u00f1ade datos a tu sesion: +sessions.dataname=Nombre del atributo de sesion: +sessions.datavalue=Valor del atributo de sesion: diff --git a/webapps/examples/WEB-INF/classes/LocalStrings_fr.properties b/webapps/examples/WEB-INF/classes/LocalStrings_fr.properties new file mode 100644 index 000000000000..99c8b50827e3 --- /dev/null +++ b/webapps/examples/WEB-INF/classes/LocalStrings_fr.properties @@ -0,0 +1,53 @@ +# Licensed to the Apache Software Foundation (ASF) under one or more +# contributor license agreements. See the NOTICE file distributed with +# this work for additional information regarding copyright ownership. +# The ASF licenses this file to You under the Apache License, Version 2.0 +# (the "License"); you may not use this file except in compliance with +# the License. You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. + +# $Id$ + +# Default localized resources for example servlets +# This locale is fr_FR + +helloworld.title=Salut le Monde! + +requestinfo.title=Exemple d''information sur la requ\u00eate +requestinfo.label.method=M\u00e9thode: +requestinfo.label.requesturi=URI de requ\u00eate: +requestinfo.label.protocol=Protocole: +requestinfo.label.pathinfo=Info de chemin: +requestinfo.label.remoteaddr=Adresse distante: + +requestheader.title=Exemple d''information sur les ent\u00eate de requ\u00eate + +requestparams.title=Exemple de requ\u00eate avec param\u00eatres +requestparams.params-in-req=Param\u00eatres dans la requ\u00eate: +requestparams.no-params=Pas de param\u00eatre, merci dans saisir quelqu'uns +requestparams.firstname=Pr\u00e9nom: +requestparams.lastname=Nom: + +cookies.title=Exemple d''utilisation de Cookies +cookies.cookies=Votre navigateur retourne les cookies suivant: +cookies.no-cookies=Votre navigateur ne retourne aucun cookie +cookies.make-cookie=Cr\u00e9ation d''un cookie \u00e0 retourner \u00e0 votre navigateur +cookies.name=Nom: +cookies.value=Valeur: +cookies.set=Vous venez d''envoyer le cookie suivant \u00e0 votre navigateur: + +sessions.title=Exemple de Sessions +sessions.id=ID de Session: +sessions.created=Cr\u00e9e le: +sessions.lastaccessed=Dernier acc\u00e8s: +sessions.data=Les donn\u00e9es existantes dans votre session: +sessions.adddata=Ajouter des donn\u00e9es \u00e0 votre session +sessions.dataname=Nom de l''Attribut de Session: +sessions.datavalue=Valeur de l''Attribut de Session: diff --git a/webapps/examples/WEB-INF/classes/LocalStrings_pt.properties b/webapps/examples/WEB-INF/classes/LocalStrings_pt.properties new file mode 100644 index 000000000000..647e9179e477 --- /dev/null +++ b/webapps/examples/WEB-INF/classes/LocalStrings_pt.properties @@ -0,0 +1,53 @@ +# Licensed to the Apache Software Foundation (ASF) under one or more +# contributor license agreements. See the NOTICE file distributed with +# this work for additional information regarding copyright ownership. +# The ASF licenses this file to You under the Apache License, Version 2.0 +# (the "License"); you may not use this file except in compliance with +# the License. You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. + +# $Id$ + +# Default localized resources for example servlets +# This locale is pt_PT + +helloworld.title=Ola Mundo! + +requestinfo.title=Exemplo da Informacao do Pedido +requestinfo.label.method=Metodo: +requestinfo.label.requesturi=URI do Pedido: +requestinfo.label.protocol=Protocolo: +requestinfo.label.pathinfo=Informacao do Caminho: +requestinfo.label.remoteaddr=Endereco Remoto: + +requestheader.title=Exemplo da Cebeceira do Pedido + +requestparams.title=Examplo de Parametros do Pedido +requestparams.params-in-req=Parametros neste pedido: +requestparams.no-params=Sem Parametros, Por favor entre alguns +requestparams.firstname=Primeiro Nome: +requestparams.lastname=Apelido: + +cookies.title=CExamplo de Cookies +cookies.cookies=O se browser esta a enviar os seguintes cookies: +cookies.no-cookies=O seu browser nao esta a enviar nenhuns cookies +cookies.make-cookie=Crie um cookie para enviar para o seu browser +cookies.name=Nome: +cookies.value=Valor: +cookies.set=Acabou de enviar o seguinte cookie para o seu browser: + +sessions.title=Examplo de sessoes +sessions.id=Identificador da Sessao: +sessions.created=Criada: +sessions.lastaccessed=Ultima vez acedida: +sessions.data=Os seguintes dados fazem parte da sua sessao: +sessions.adddata=Adicione data a sua sessao +sessions.dataname=Nome do atributo da sessao: +sessions.datavalue=Valor do atributo da Sessao: diff --git a/webapps/examples/WEB-INF/classes/RequestHeaderExample.java b/webapps/examples/WEB-INF/classes/RequestHeaderExample.java new file mode 100644 index 000000000000..b42da02b4baa --- /dev/null +++ b/webapps/examples/WEB-INF/classes/RequestHeaderExample.java @@ -0,0 +1,99 @@ +/* +* Licensed to the Apache Software Foundation (ASF) under one or more +* contributor license agreements. See the NOTICE file distributed with +* this work for additional information regarding copyright ownership. +* The ASF licenses this file to You under the Apache License, Version 2.0 +* (the "License"); you may not use this file except in compliance with +* the License. You may obtain a copy of the License at +* +* http://www.apache.org/licenses/LICENSE-2.0 +* +* Unless required by applicable law or agreed to in writing, software +* distributed under the License is distributed on an "AS IS" BASIS, +* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +* See the License for the specific language governing permissions and +* limitations under the License. +*/ +/* $Id$ + * + */ + +import java.io.IOException; +import java.io.PrintWriter; +import java.util.Enumeration; +import java.util.ResourceBundle; + +import javax.servlet.ServletException; +import javax.servlet.http.HttpServlet; +import javax.servlet.http.HttpServletRequest; +import javax.servlet.http.HttpServletResponse; + +import util.HTMLFilter; + +/** + * Example servlet showing request headers + * + * @author James Duncan Davidson + */ + +public class RequestHeaderExample extends HttpServlet { + + private static final long serialVersionUID = 1L; + + private static final ResourceBundle RB = ResourceBundle.getBundle("LocalStrings"); + + @Override + public void doGet(HttpServletRequest request, + HttpServletResponse response) + throws IOException, ServletException + { + response.setContentType("text/html"); + + PrintWriter out = response.getWriter(); + out.println(""); + out.println(""); + out.println(""); + + String title = RB.getString("requestheader.title"); + out.println("" + title + ""); + out.println(""); + out.println(""); + + // all links relative + + // XXX + // making these absolute till we work out the + // addition of a PathInfo issue + + out.println(""); + out.println("\"view"); + out.println(""); + out.println("\"return\""); + + out.println("

    " + title + "

    "); + out.println(""); + Enumeration e = request.getHeaderNames(); + while (e.hasMoreElements()) { + String headerName = e.nextElement(); + String headerValue = request.getHeader(headerName); + out.println(""); + } + out.println("
    "); + out.println(HTMLFilter.filter(headerName)); + out.println(""); + out.println(HTMLFilter.filter(headerValue)); + out.println("
    "); + } + + @Override + public void doPost(HttpServletRequest request, + HttpServletResponse response) + throws IOException, ServletException + { + doGet(request, response); + } + +} + diff --git a/webapps/examples/WEB-INF/classes/RequestInfoExample.java b/webapps/examples/WEB-INF/classes/RequestInfoExample.java new file mode 100644 index 000000000000..ecb31316b52d --- /dev/null +++ b/webapps/examples/WEB-INF/classes/RequestInfoExample.java @@ -0,0 +1,120 @@ +/* +* Licensed to the Apache Software Foundation (ASF) under one or more +* contributor license agreements. See the NOTICE file distributed with +* this work for additional information regarding copyright ownership. +* The ASF licenses this file to You under the Apache License, Version 2.0 +* (the "License"); you may not use this file except in compliance with +* the License. You may obtain a copy of the License at +* +* http://www.apache.org/licenses/LICENSE-2.0 +* +* Unless required by applicable law or agreed to in writing, software +* distributed under the License is distributed on an "AS IS" BASIS, +* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +* See the License for the specific language governing permissions and +* limitations under the License. +*/ +/* $Id$ + * + */ + +import java.io.IOException; +import java.io.PrintWriter; +import java.util.ResourceBundle; + +import javax.servlet.ServletException; +import javax.servlet.http.HttpServlet; +import javax.servlet.http.HttpServletRequest; +import javax.servlet.http.HttpServletResponse; + +import util.HTMLFilter; + +/** + * Example servlet showing request information. + * + * @author James Duncan Davidson + */ + +public class RequestInfoExample extends HttpServlet { + + private static final long serialVersionUID = 1L; + + private static final ResourceBundle RB = ResourceBundle.getBundle("LocalStrings"); + + @Override + public void doGet(HttpServletRequest request, + HttpServletResponse response) + throws IOException, ServletException + { + response.setContentType("text/html"); + + PrintWriter out = response.getWriter(); + out.println(""); + out.println(""); + out.println(""); + + String title = RB.getString("requestinfo.title"); + out.println("" + title + ""); + out.println(""); + out.println(""); + + // img stuff not req'd for source code html showing + // all links relative! + + // XXX + // making these absolute till we work out the + // addition of a PathInfo issue + + out.println(""); + out.println("\"view"); + out.println(""); + out.println("\"return\""); + + out.println("

    " + title + "

    "); + out.println("
    "); + out.println(RB.getString("requestinfo.label.method")); + out.println(""); + out.println(request.getMethod()); + out.println("
    "); + out.println(RB.getString("requestinfo.label.requesturi")); + out.println(""); + out.println(HTMLFilter.filter(request.getRequestURI())); + out.println("
    "); + out.println(RB.getString("requestinfo.label.protocol")); + out.println(""); + out.println(request.getProtocol()); + out.println("
    "); + out.println(RB.getString("requestinfo.label.pathinfo")); + out.println(""); + out.println(HTMLFilter.filter(request.getPathInfo())); + out.println("
    "); + out.println(RB.getString("requestinfo.label.remoteaddr")); + + String cipherSuite= + (String)request.getAttribute("javax.servlet.request.cipher_suite"); + out.println(""); + out.println(request.getRemoteAddr()); + out.println("
    "); + + if(cipherSuite!=null){ + out.println(""); + out.println("SSLCipherSuite:"); + out.println(""); + out.println(""); + out.println(request.getAttribute("javax.servlet.request.cipher_suite")); + out.println(""); + } + } + + @Override + public void doPost(HttpServletRequest request, + HttpServletResponse response) + throws IOException, ServletException + { + doGet(request, response); + } + +} + diff --git a/webapps/examples/WEB-INF/classes/RequestParamExample.java b/webapps/examples/WEB-INF/classes/RequestParamExample.java new file mode 100644 index 000000000000..aceea086fafe --- /dev/null +++ b/webapps/examples/WEB-INF/classes/RequestParamExample.java @@ -0,0 +1,113 @@ +/* +* Licensed to the Apache Software Foundation (ASF) under one or more +* contributor license agreements. See the NOTICE file distributed with +* this work for additional information regarding copyright ownership. +* The ASF licenses this file to You under the Apache License, Version 2.0 +* (the "License"); you may not use this file except in compliance with +* the License. You may obtain a copy of the License at +* +* http://www.apache.org/licenses/LICENSE-2.0 +* +* Unless required by applicable law or agreed to in writing, software +* distributed under the License is distributed on an "AS IS" BASIS, +* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +* See the License for the specific language governing permissions and +* limitations under the License. +*/ +/* $Id$ + * + */ + +import java.io.IOException; +import java.io.PrintWriter; +import java.util.ResourceBundle; + +import javax.servlet.ServletException; +import javax.servlet.http.HttpServlet; +import javax.servlet.http.HttpServletRequest; +import javax.servlet.http.HttpServletResponse; + +import util.HTMLFilter; + +/** + * Example servlet showing request headers + * + * @author James Duncan Davidson + */ + +public class RequestParamExample extends HttpServlet { + + private static final long serialVersionUID = 1L; + + private static final ResourceBundle RB = ResourceBundle.getBundle("LocalStrings"); + + @Override + public void doGet(HttpServletRequest request, + HttpServletResponse response) + throws IOException, ServletException + { + response.setContentType("text/html"); + + PrintWriter out = response.getWriter(); + out.println(""); + out.println(""); + out.println(""); + + String title = RB.getString("requestparams.title"); + out.println("" + title + ""); + out.println(""); + out.println(""); + + // img stuff not req'd for source code html showing + + // all links relative + + // XXX + // making these absolute till we work out the + // addition of a PathInfo issue + + out.println(""); + out.println("\"view"); + out.println(""); + out.println("\"return\""); + + out.println("

    " + title + "

    "); + String firstName = request.getParameter("firstname"); + String lastName = request.getParameter("lastname"); + out.println(RB.getString("requestparams.params-in-req") + "
    "); + if (firstName != null || lastName != null) { + out.println(RB.getString("requestparams.firstname")); + out.println(" = " + HTMLFilter.filter(firstName) + "
    "); + out.println(RB.getString("requestparams.lastname")); + out.println(" = " + HTMLFilter.filter(lastName)); + } else { + out.println(RB.getString("requestparams.no-params")); + } + out.println("

    "); + out.print("

    "); + out.println(RB.getString("requestparams.firstname")); + out.println(""); + out.println("
    "); + out.println(RB.getString("requestparams.lastname")); + out.println(""); + out.println("
    "); + out.println(""); + out.println("
    "); + + out.println(""); + out.println(""); + } + + @Override + public void doPost(HttpServletRequest request, + HttpServletResponse response) + throws IOException, ServletException + { + doGet(request, response); + } + +} diff --git a/webapps/examples/WEB-INF/classes/SessionExample.java b/webapps/examples/WEB-INF/classes/SessionExample.java new file mode 100644 index 000000000000..34b393ec419c --- /dev/null +++ b/webapps/examples/WEB-INF/classes/SessionExample.java @@ -0,0 +1,151 @@ +/* +* Licensed to the Apache Software Foundation (ASF) under one or more +* contributor license agreements. See the NOTICE file distributed with +* this work for additional information regarding copyright ownership. +* The ASF licenses this file to You under the Apache License, Version 2.0 +* (the "License"); you may not use this file except in compliance with +* the License. You may obtain a copy of the License at +* +* http://www.apache.org/licenses/LICENSE-2.0 +* +* Unless required by applicable law or agreed to in writing, software +* distributed under the License is distributed on an "AS IS" BASIS, +* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +* See the License for the specific language governing permissions and +* limitations under the License. +*/ +/* $Id$ + * + */ + +import java.io.IOException; +import java.io.PrintWriter; +import java.util.Date; +import java.util.Enumeration; +import java.util.ResourceBundle; + +import javax.servlet.ServletException; +import javax.servlet.http.HttpServlet; +import javax.servlet.http.HttpServletRequest; +import javax.servlet.http.HttpServletResponse; +import javax.servlet.http.HttpSession; + +import util.HTMLFilter; + +/** + * Example servlet showing request headers + * + * @author James Duncan Davidson + */ + +public class SessionExample extends HttpServlet { + + private static final long serialVersionUID = 1L; + + private static final ResourceBundle RB = ResourceBundle.getBundle("LocalStrings"); + + @Override + public void doGet(HttpServletRequest request, + HttpServletResponse response) + throws IOException, ServletException + { + response.setContentType("text/html"); + + PrintWriter out = response.getWriter(); + out.println(""); + out.println(""); + out.println(""); + + String title = RB.getString("sessions.title"); + out.println("" + title + ""); + out.println(""); + out.println(""); + + // img stuff not req'd for source code html showing + // relative links everywhere! + + // XXX + // making these absolute till we work out the + // addition of a PathInfo issue + + out.println(""); + out.println("\"view"); + out.println(""); + out.println("\"return\""); + + out.println("

    " + title + "

    "); + + HttpSession session = request.getSession(true); + out.println(RB.getString("sessions.id") + " " + session.getId()); + out.println("
    "); + out.println(RB.getString("sessions.created") + " "); + out.println(new Date(session.getCreationTime()) + "
    "); + out.println(RB.getString("sessions.lastaccessed") + " "); + out.println(new Date(session.getLastAccessedTime())); + + String dataName = request.getParameter("dataname"); + String dataValue = request.getParameter("datavalue"); + if (dataName != null && dataValue != null) { + session.setAttribute(dataName, dataValue); + } + + out.println("

    "); + out.println(RB.getString("sessions.data") + "
    "); + Enumeration names = session.getAttributeNames(); + while (names.hasMoreElements()) { + String name = names.nextElement(); + String value = session.getAttribute(name).toString(); + out.println(HTMLFilter.filter(name) + " = " + + HTMLFilter.filter(value) + "
    "); + } + + out.println("

    "); + out.print("

    "); + out.println(RB.getString("sessions.dataname")); + out.println(""); + out.println("
    "); + out.println(RB.getString("sessions.datavalue")); + out.println(""); + out.println("
    "); + out.println(""); + out.println("
    "); + + out.println("

    GET based form:
    "); + out.print("

    "); + out.println(RB.getString("sessions.dataname")); + out.println(""); + out.println("
    "); + out.println(RB.getString("sessions.datavalue")); + out.println(""); + out.println("
    "); + out.println(""); + out.println("
    "); + + out.print("

    URL encoded "); + + out.println(""); + out.println(""); + + out.println(""); + out.println(""); + } + + @Override + public void doPost(HttpServletRequest request, + HttpServletResponse response) + throws IOException, ServletException + { + doGet(request, response); + } + +} diff --git a/webapps/examples/WEB-INF/classes/async/Async0.java b/webapps/examples/WEB-INF/classes/async/Async0.java new file mode 100644 index 000000000000..fabafe3d97c5 --- /dev/null +++ b/webapps/examples/WEB-INF/classes/async/Async0.java @@ -0,0 +1,68 @@ +/* +* Licensed to the Apache Software Foundation (ASF) under one or more +* contributor license agreements. See the NOTICE file distributed with +* this work for additional information regarding copyright ownership. +* The ASF licenses this file to You under the Apache License, Version 2.0 +* (the "License"); you may not use this file except in compliance with +* the License. You may obtain a copy of the License at +* +* http://www.apache.org/licenses/LICENSE-2.0 +* +* Unless required by applicable law or agreed to in writing, software +* distributed under the License is distributed on an "AS IS" BASIS, +* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +* See the License for the specific language governing permissions and +* limitations under the License. +*/ +package async; + +import java.io.IOException; + +import javax.servlet.AsyncContext; +import javax.servlet.ServletException; +import javax.servlet.http.HttpServlet; +import javax.servlet.http.HttpServletRequest; +import javax.servlet.http.HttpServletResponse; + +import org.apache.juli.logging.Log; +import org.apache.juli.logging.LogFactory; + +public class Async0 extends HttpServlet { + + private static final long serialVersionUID = 1L; + + private static final Log log = LogFactory.getLog(Async0.class); + + @Override + protected void service(final HttpServletRequest req, final HttpServletResponse resp) throws ServletException, IOException { + if (Boolean.TRUE == req.getAttribute("dispatch")) { + log.info("Received dispatch, completing on the worker thread."); + req.getAsyncContext().complete(); + log.info("After complete called started:"+req.isAsyncStarted()); + resp.getWriter().write("Async dispatch worked:+"+System.currentTimeMillis()+"\n"); + } else { + resp.setContentType("text/plain"); + final AsyncContext actx = req.startAsync(); + actx.setTimeout(Long.MAX_VALUE); + Runnable run = new Runnable() { + @Override + public void run() { + try { + req.setAttribute("dispatch", Boolean.TRUE); + Thread.currentThread().setName("Async0-Thread"); + log.info("Putting AsyncThread to sleep"); + Thread.sleep(2*1000); + log.info("Dispatching"); + actx.dispatch(); + }catch (InterruptedException x) { + log.error("Async1",x); + }catch (IllegalStateException x) { + log.error("Async1",x); + } + } + }; + Thread t = new Thread(run); + t.start(); + } + } +} diff --git a/webapps/examples/WEB-INF/classes/async/Async1.java b/webapps/examples/WEB-INF/classes/async/Async1.java new file mode 100644 index 000000000000..a2a3e462ae17 --- /dev/null +++ b/webapps/examples/WEB-INF/classes/async/Async1.java @@ -0,0 +1,62 @@ +/* +* Licensed to the Apache Software Foundation (ASF) under one or more +* contributor license agreements. See the NOTICE file distributed with +* this work for additional information regarding copyright ownership. +* The ASF licenses this file to You under the Apache License, Version 2.0 +* (the "License"); you may not use this file except in compliance with +* the License. You may obtain a copy of the License at +* +* http://www.apache.org/licenses/LICENSE-2.0 +* +* Unless required by applicable law or agreed to in writing, software +* distributed under the License is distributed on an "AS IS" BASIS, +* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +* See the License for the specific language governing permissions and +* limitations under the License. +*/ +package async; + +import java.io.IOException; + +import javax.servlet.AsyncContext; +import javax.servlet.ServletException; +import javax.servlet.http.HttpServlet; +import javax.servlet.http.HttpServletRequest; +import javax.servlet.http.HttpServletResponse; + +import org.apache.juli.logging.Log; +import org.apache.juli.logging.LogFactory; + +public class Async1 extends HttpServlet { + + private static final long serialVersionUID = 1L; + + private static final Log log = LogFactory.getLog(Async1.class); + + @Override + protected void service(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException { + final AsyncContext actx = req.startAsync(); + actx.setTimeout(30*1000); + Runnable run = new Runnable() { + @Override + public void run() { + try { + String path = "/jsp/async/async1.jsp"; + Thread.currentThread().setName("Async1-Thread"); + log.info("Putting AsyncThread to sleep"); + Thread.sleep(2*1000); + log.info("Dispatching to "+path); + actx.dispatch(path); + }catch (InterruptedException x) { + log.error("Async1",x); + }catch (IllegalStateException x) { + log.error("Async1",x); + } + } + }; + Thread t = new Thread(run); + t.start(); + } + + +} diff --git a/webapps/examples/WEB-INF/classes/async/Async2.java b/webapps/examples/WEB-INF/classes/async/Async2.java new file mode 100644 index 000000000000..ac37e506afa3 --- /dev/null +++ b/webapps/examples/WEB-INF/classes/async/Async2.java @@ -0,0 +1,64 @@ +/* +* Licensed to the Apache Software Foundation (ASF) under one or more +* contributor license agreements. See the NOTICE file distributed with +* this work for additional information regarding copyright ownership. +* The ASF licenses this file to You under the Apache License, Version 2.0 +* (the "License"); you may not use this file except in compliance with +* the License. You may obtain a copy of the License at +* +* http://www.apache.org/licenses/LICENSE-2.0 +* +* Unless required by applicable law or agreed to in writing, software +* distributed under the License is distributed on an "AS IS" BASIS, +* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +* See the License for the specific language governing permissions and +* limitations under the License. +*/ +package async; + +import java.io.IOException; + +import javax.servlet.AsyncContext; +import javax.servlet.ServletException; +import javax.servlet.http.HttpServlet; +import javax.servlet.http.HttpServletRequest; +import javax.servlet.http.HttpServletResponse; + +import org.apache.juli.logging.Log; +import org.apache.juli.logging.LogFactory; + +public class Async2 extends HttpServlet { + + private static final long serialVersionUID = 1L; + + private static final Log log = LogFactory.getLog(Async2.class); + + @Override + protected void service(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException { + final AsyncContext actx = req.startAsync(); + actx.setTimeout(30*1000); + Runnable run = new Runnable() { + @Override + public void run() { + try { + Thread.currentThread().setName("Async2-Thread"); + log.info("Putting AsyncThread to sleep"); + Thread.sleep(2*1000); + log.info("Writing data."); + actx.getResponse().getWriter().write("Output from background thread. Time:"+System.currentTimeMillis()+"\n"); + actx.complete(); + }catch (InterruptedException x) { + log.error("Async2",x); + }catch (IllegalStateException x) { + log.error("Async2",x); + }catch (IOException x) { + log.error("Async2",x); + } + } + }; + Thread t = new Thread(run); + t.start(); + } + + +} diff --git a/webapps/examples/WEB-INF/classes/async/Async3.java b/webapps/examples/WEB-INF/classes/async/Async3.java new file mode 100644 index 000000000000..37b7ed1b3102 --- /dev/null +++ b/webapps/examples/WEB-INF/classes/async/Async3.java @@ -0,0 +1,39 @@ +/* +* Licensed to the Apache Software Foundation (ASF) under one or more +* contributor license agreements. See the NOTICE file distributed with +* this work for additional information regarding copyright ownership. +* The ASF licenses this file to You under the Apache License, Version 2.0 +* (the "License"); you may not use this file except in compliance with +* the License. You may obtain a copy of the License at +* +* http://www.apache.org/licenses/LICENSE-2.0 +* +* Unless required by applicable law or agreed to in writing, software +* distributed under the License is distributed on an "AS IS" BASIS, +* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +* See the License for the specific language governing permissions and +* limitations under the License. +*/ +package async; + +import java.io.IOException; + +import javax.servlet.AsyncContext; +import javax.servlet.ServletException; +import javax.servlet.http.HttpServlet; +import javax.servlet.http.HttpServletRequest; +import javax.servlet.http.HttpServletResponse; + +public class Async3 extends HttpServlet { + + private static final long serialVersionUID = 1L; + + @Override + protected void service(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException { + final AsyncContext actx = req.startAsync(); + actx.setTimeout(30*1000); + actx.dispatch("/jsp/async/async3.jsp"); + } + + +} diff --git a/webapps/examples/WEB-INF/classes/async/AsyncStockServlet.java b/webapps/examples/WEB-INF/classes/async/AsyncStockServlet.java new file mode 100644 index 000000000000..f21ba56c2ffc --- /dev/null +++ b/webapps/examples/WEB-INF/classes/async/AsyncStockServlet.java @@ -0,0 +1,127 @@ +/* + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed with + * this work for additional information regarding copyright ownership. + * The ASF licenses this file to You under the Apache License, Version 2.0 + * (the "License"); you may not use this file except in compliance with + * the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +package async; + +import java.io.IOException; +import java.io.PrintWriter; +import java.util.ArrayList; +import java.util.Iterator; +import java.util.concurrent.ConcurrentLinkedQueue; +import java.util.concurrent.atomic.AtomicInteger; + +import javax.servlet.AsyncContext; +import javax.servlet.AsyncEvent; +import javax.servlet.AsyncListener; +import javax.servlet.ServletException; +import javax.servlet.http.HttpServlet; +import javax.servlet.http.HttpServletRequest; +import javax.servlet.http.HttpServletResponse; + +import async.Stockticker.Stock; +import async.Stockticker.TickListener; + +public class AsyncStockServlet extends HttpServlet implements TickListener, AsyncListener{ + + private static final long serialVersionUID = 1L; + + public static final String POLL = "POLL"; + public static final String LONG_POLL = "LONG-POLL"; + public static final String STREAM = "STREAM"; + + static ArrayList ticks = new ArrayList(); + static ConcurrentLinkedQueue clients = new ConcurrentLinkedQueue(); + static AtomicInteger clientcount = new AtomicInteger(0); + static Stockticker ticker = new Stockticker(); + + public AsyncStockServlet() { + System.out.println("AsyncStockServlet created"); + } + + + @Override + protected void service(HttpServletRequest req, HttpServletResponse resp) + throws ServletException, IOException { + if (req.isAsyncStarted()) { + req.getAsyncContext().complete(); + } else if (req.isAsyncSupported()) { + AsyncContext actx = req.startAsync(); + actx.addListener(this); + resp.setContentType("text/plain"); + clients.add(actx); + if (clientcount.incrementAndGet()==1) { + ticker.addTickListener(this); + } + } else { + new Exception("Async Not Supported").printStackTrace(); + resp.sendError(400,"Async is not supported."); + } + } + + + @Override + public void tick(Stock stock) { + ticks.add((Stock)stock.clone()); + Iterator it = clients.iterator(); + while (it.hasNext()) { + AsyncContext actx = it.next(); + writeStock(actx, stock); + } + } + + public void writeStock(AsyncContext actx, Stock stock) { + HttpServletResponse response = (HttpServletResponse)actx.getResponse(); + try { + PrintWriter writer = response.getWriter(); + writer.write("STOCK#");//make client parsing easier + writer.write(stock.getSymbol()); + writer.write("#"); + writer.write(stock.getValueAsString()); + writer.write("#"); + writer.write(stock.getLastChangeAsString()); + writer.write("#"); + writer.write(String.valueOf(stock.getCnt())); + writer.write("\n"); + writer.flush(); + response.flushBuffer(); + }catch (IOException x) { + try {actx.complete();}catch (Exception ignore){/* Ignore */} + } + } + + @Override + public void onComplete(AsyncEvent event) throws IOException { + if (clients.remove(event.getAsyncContext()) && clientcount.decrementAndGet()==0) { + ticker.removeTickListener(this); + } + } + + @Override + public void onError(AsyncEvent event) throws IOException { + event.getAsyncContext().complete(); + } + + @Override + public void onTimeout(AsyncEvent event) throws IOException { + event.getAsyncContext().complete(); + } + + + @Override + public void onStartAsync(AsyncEvent event) throws IOException { + // NOOP + } +} diff --git a/webapps/examples/WEB-INF/classes/async/Stockticker.java b/webapps/examples/WEB-INF/classes/async/Stockticker.java new file mode 100644 index 000000000000..efe404ccbaeb --- /dev/null +++ b/webapps/examples/WEB-INF/classes/async/Stockticker.java @@ -0,0 +1,188 @@ +/* + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed with + * this work for additional information regarding copyright ownership. + * The ASF licenses this file to You under the Apache License, Version 2.0 + * (the "License"); you may not use this file except in compliance with + * the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +package async; + +import java.text.DecimalFormat; +import java.util.ArrayList; +import java.util.Random; +import java.util.concurrent.atomic.AtomicInteger; + +public class Stockticker implements Runnable { + public volatile boolean run = true; + protected AtomicInteger counter = new AtomicInteger(0); + ArrayList listeners = new ArrayList(); + protected volatile Thread ticker = null; + protected volatile int ticknr = 0; + + public synchronized void start() { + run = true; + ticker = new Thread(this); + ticker.setName("Ticker Thread"); + ticker.start(); + } + + public synchronized void stop() { + run = false; + try { + ticker.join(); + }catch (InterruptedException x) { + Thread.interrupted(); + } + + ticker = null; + } + + public void addTickListener(TickListener listener) { + if (listeners.add(listener)) { + if (counter.incrementAndGet()==1) start(); + } + + } + + public void removeTickListener(TickListener listener) { + if (listeners.remove(listener)) { + if (counter.decrementAndGet()==0) stop(); + } + } + + @Override + public void run() { + try { + + Stock[] stocks = new Stock[] { new Stock("GOOG", 435.43), + new Stock("YHOO", 27.88), new Stock("ASF", 1015.55), }; + Random r = new Random(System.currentTimeMillis()); + while (run) { + for (int j = 0; j < 1; j++) { + int i = r.nextInt() % 3; + if (i < 0) + i = i * (-1); + Stock stock = stocks[i]; + double change = r.nextDouble(); + boolean plus = r.nextBoolean(); + if (plus) { + stock.setValue(stock.getValue() + change); + } else { + stock.setValue(stock.getValue() - change); + } + stock.setCnt(++ticknr); + for (TickListener l : listeners) { + l.tick(stock); + } + + } + Thread.sleep(850); + } + } catch (InterruptedException ix) { + // Ignore + } catch (Exception x) { + x.printStackTrace(); + } + } + + + public static interface TickListener { + public void tick(Stock stock); + } + + public static class Stock { + protected static DecimalFormat df = new DecimalFormat("0.00"); + protected String symbol = ""; + protected double value = 0.0d; + protected double lastchange = 0.0d; + protected int cnt = 0; + + public Stock(String symbol, double initvalue) { + this.symbol = symbol; + this.value = initvalue; + } + + public void setCnt(int c) { + this.cnt = c; + } + + public int getCnt() { + return cnt; + } + + public String getSymbol() { + return symbol; + } + + public double getValue() { + return value; + } + + public void setValue(double value) { + double old = this.value; + this.value = value; + this.lastchange = value - old; + } + + public String getValueAsString() { + return df.format(value); + } + + public double getLastChange() { + return this.lastchange; + } + + public void setLastChange(double lastchange) { + this.lastchange = lastchange; + } + + public String getLastChangeAsString() { + return df.format(lastchange); + } + + @Override + public int hashCode() { + return symbol.hashCode(); + } + + @Override + public boolean equals(Object other) { + if (other instanceof Stock) { + return this.symbol.equals(((Stock) other).symbol); + } + + return false; + } + + @Override + public String toString() { + StringBuilder buf = new StringBuilder("STOCK#"); + buf.append(getSymbol()); + buf.append("#"); + buf.append(getValueAsString()); + buf.append("#"); + buf.append(getLastChangeAsString()); + buf.append("#"); + buf.append(String.valueOf(getCnt())); + return buf.toString(); + + } + + @Override + public Object clone() { + Stock s = new Stock(this.getSymbol(), this.getValue()); + s.setLastChange(this.getLastChange()); + s.setCnt(this.cnt); + return s; + } + } +} diff --git a/webapps/examples/WEB-INF/classes/cal/Entries.java b/webapps/examples/WEB-INF/classes/cal/Entries.java new file mode 100644 index 000000000000..e95f3a0d51b1 --- /dev/null +++ b/webapps/examples/WEB-INF/classes/cal/Entries.java @@ -0,0 +1,60 @@ +/* + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed with + * this work for additional information regarding copyright ownership. + * The ASF licenses this file to You under the Apache License, Version 2.0 + * (the "License"); you may not use this file except in compliance with + * the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +package cal; + +import java.util.Hashtable; + +import javax.servlet.http.HttpServletRequest; + +public class Entries { + + private Hashtable entries; + private static final String[] time = { "8am", "9am", "10am", "11am", + "12pm", "1pm", "2pm", "3pm", "4pm", "5pm", "6pm", "7pm", "8pm" }; + public static final int rows = 12; + + public Entries() { + entries = new Hashtable(rows); + for (int i = 0; i < rows; i++) { + entries.put(time[i], new Entry(time[i])); + } + } + + public int getRows() { + return rows; + } + + public Entry getEntry(int index) { + return this.entries.get(time[index]); + } + + public int getIndex(String tm) { + for (int i = 0; i < rows; i++) + if (tm.equals(time[i])) + return i; + return -1; + } + + public void processRequest(HttpServletRequest request, String tm) { + int index = getIndex(tm); + if (index >= 0) { + String descr = request.getParameter("description"); + entries.get(time[index]).setDescription(descr); + } + } + +} diff --git a/webapps/examples/WEB-INF/classes/cal/Entry.java b/webapps/examples/WEB-INF/classes/cal/Entry.java new file mode 100644 index 000000000000..85f81cf95588 --- /dev/null +++ b/webapps/examples/WEB-INF/classes/cal/Entry.java @@ -0,0 +1,53 @@ +/* + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed with + * this work for additional information regarding copyright ownership. + * The ASF licenses this file to You under the Apache License, Version 2.0 + * (the "License"); you may not use this file except in compliance with + * the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +package cal; + +public class Entry { + + String hour; + String description; + + public Entry(String hour) { + this.hour = hour; + this.description = ""; + + } + + public String getHour() { + return this.hour; + } + + public String getColor() { + if (description.equals("")) { + return "lightblue"; + } + return "red"; + } + + public String getDescription() { + if (description.equals("")) { + return "None"; + } + return this.description; + } + + public void setDescription(String descr) { + description = descr; + } + +} diff --git a/webapps/examples/WEB-INF/classes/cal/JspCalendar.java b/webapps/examples/WEB-INF/classes/cal/JspCalendar.java new file mode 100644 index 000000000000..110944340972 --- /dev/null +++ b/webapps/examples/WEB-INF/classes/cal/JspCalendar.java @@ -0,0 +1,151 @@ +/* +* Licensed to the Apache Software Foundation (ASF) under one or more +* contributor license agreements. See the NOTICE file distributed with +* this work for additional information regarding copyright ownership. +* The ASF licenses this file to You under the Apache License, Version 2.0 +* (the "License"); you may not use this file except in compliance with +* the License. You may obtain a copy of the License at +* +* http://www.apache.org/licenses/LICENSE-2.0 +* +* Unless required by applicable law or agreed to in writing, software +* distributed under the License is distributed on an "AS IS" BASIS, +* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +* See the License for the specific language governing permissions and +* limitations under the License. +*/ + +package cal; + +import java.util.Calendar; +import java.util.Date; + +public class JspCalendar { + Calendar calendar = null; + + public JspCalendar() { + calendar = Calendar.getInstance(); + Date trialTime = new Date(); + calendar.setTime(trialTime); + } + + + public int getYear() { + return calendar.get(Calendar.YEAR); + } + + public String getMonth() { + int m = getMonthInt(); + String[] months = new String [] { "January", "February", "March", + "April", "May", "June", + "July", "August", "September", + "October", "November", "December" }; + if (m > 12) + return "Unknown to Man"; + + return months[m - 1]; + + } + + public String getDay() { + int x = getDayOfWeek(); + String[] days = new String[] {"Sunday", "Monday", "Tuesday", "Wednesday", + "Thursday", "Friday", "Saturday"}; + + if (x > 7) + return "Unknown to Man"; + + return days[x - 1]; + + } + + public int getMonthInt() { + return 1 + calendar.get(Calendar.MONTH); + } + + public String getDate() { + return getMonthInt() + "/" + getDayOfMonth() + "/" + getYear(); + } + + public String getCurrentDate() { + Date dt = new Date (); + calendar.setTime (dt); + return getMonthInt() + "/" + getDayOfMonth() + "/" + getYear(); + + } + + public String getNextDate() { + calendar.set (Calendar.DAY_OF_MONTH, getDayOfMonth() + 1); + return getDate (); + } + + public String getPrevDate() { + calendar.set (Calendar.DAY_OF_MONTH, getDayOfMonth() - 1); + return getDate (); + } + + public String getTime() { + return getHour() + ":" + getMinute() + ":" + getSecond(); + } + + public int getDayOfMonth() { + return calendar.get(Calendar.DAY_OF_MONTH); + } + + public int getDayOfYear() { + return calendar.get(Calendar.DAY_OF_YEAR); + } + + public int getWeekOfYear() { + return calendar.get(Calendar.WEEK_OF_YEAR); + } + + public int getWeekOfMonth() { + return calendar.get(Calendar.WEEK_OF_MONTH); + } + + public int getDayOfWeek() { + return calendar.get(Calendar.DAY_OF_WEEK); + } + + public int getHour() { + return calendar.get(Calendar.HOUR_OF_DAY); + } + + public int getMinute() { + return calendar.get(Calendar.MINUTE); + } + + + public int getSecond() { + return calendar.get(Calendar.SECOND); + } + + + public int getEra() { + return calendar.get(Calendar.ERA); + } + + public String getUSTimeZone() { + String[] zones = new String[] {"Hawaii", "Alaskan", "Pacific", + "Mountain", "Central", "Eastern"}; + + return zones[10 + getZoneOffset()]; + } + + public int getZoneOffset() { + return calendar.get(Calendar.ZONE_OFFSET)/(60*60*1000); + } + + + public int getDSTOffset() { + return calendar.get(Calendar.DST_OFFSET)/(60*60*1000); + } + + + public int getAMPM() { + return calendar.get(Calendar.AM_PM); + } +} + + diff --git a/webapps/examples/WEB-INF/classes/cal/TableBean.java b/webapps/examples/WEB-INF/classes/cal/TableBean.java new file mode 100644 index 000000000000..6db467206676 --- /dev/null +++ b/webapps/examples/WEB-INF/classes/cal/TableBean.java @@ -0,0 +1,101 @@ +/* + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed with + * this work for additional information regarding copyright ownership. + * The ASF licenses this file to You under the Apache License, Version 2.0 + * (the "License"); you may not use this file except in compliance with + * the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +package cal; + +import java.util.Hashtable; + +import javax.servlet.http.HttpServletRequest; + +public class TableBean { + + Hashtable table; + JspCalendar JspCal; + Entries entries; + String date; + String name = null; + String email = null; + boolean processError = false; + + public TableBean() { + this.table = new Hashtable(10); + this.JspCal = new JspCalendar(); + this.date = JspCal.getCurrentDate(); + } + + public void setName(String nm) { + this.name = nm; + } + + public String getName() { + return this.name; + } + + public void setEmail(String mail) { + this.email = mail; + } + + public String getEmail() { + return this.email; + } + + public String getDate() { + return this.date; + } + + public Entries getEntries() { + return this.entries; + } + + public void processRequest(HttpServletRequest request) { + + // Get the name and e-mail. + this.processError = false; + if (name == null || name.equals("")) + setName(request.getParameter("name")); + if (email == null || email.equals("")) + setEmail(request.getParameter("email")); + if (name == null || email == null || name.equals("") + || email.equals("")) { + this.processError = true; + return; + } + + // Get the date. + String dateR = request.getParameter("date"); + if (dateR == null) + date = JspCal.getCurrentDate(); + else if (dateR.equalsIgnoreCase("next")) + date = JspCal.getNextDate(); + else if (dateR.equalsIgnoreCase("prev")) + date = JspCal.getPrevDate(); + + entries = table.get(date); + if (entries == null) { + entries = new Entries(); + table.put(date, entries); + } + + // If time is provided add the event. + String time = request.getParameter("time"); + if (time != null) + entries.processRequest(request, time); + } + + public boolean getProcessError() { + return this.processError; + } +} diff --git a/webapps/examples/WEB-INF/classes/chat/ChatServlet.java b/webapps/examples/WEB-INF/classes/chat/ChatServlet.java new file mode 100644 index 000000000000..3cf518867f70 --- /dev/null +++ b/webapps/examples/WEB-INF/classes/chat/ChatServlet.java @@ -0,0 +1,292 @@ +/* + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed with + * this work for additional information regarding copyright ownership. + * The ASF licenses this file to You under the Apache License, Version 2.0 + * (the "License"); you may not use this file except in compliance with + * the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + + +package chat; + + +import java.io.IOException; +import java.io.InputStream; +import java.io.PrintWriter; +import java.util.ArrayList; + +import javax.servlet.ServletException; +import javax.servlet.http.HttpServlet; +import javax.servlet.http.HttpServletRequest; +import javax.servlet.http.HttpServletResponse; + +import org.apache.catalina.comet.CometEvent; +import org.apache.catalina.comet.CometProcessor; + + +/** + * Helper class to implement Comet functionality. + */ +public class ChatServlet + extends HttpServlet implements CometProcessor { + + private static final long serialVersionUID = 1L; + + private static final String CHARSET = "UTF-8"; + + protected ArrayList connections = + new ArrayList(); + protected transient MessageSender messageSender = null; + + @Override + public void init() throws ServletException { + messageSender = new MessageSender(); + Thread messageSenderThread = + new Thread(messageSender, "MessageSender[" + getServletContext().getContextPath() + "]"); + messageSenderThread.setDaemon(true); + messageSenderThread.start(); + } + + @Override + public void destroy() { + connections.clear(); + messageSender.stop(); + messageSender = null; + } + + /** + * Process the given Comet event. + * + * @param event The Comet event that will be processed + * @throws IOException + * @throws ServletException + */ + @Override + public void event(CometEvent event) + throws IOException, ServletException { + + // Note: There should really be two servlets in this example, to avoid + // mixing Comet stuff with regular connection processing + HttpServletRequest request = event.getHttpServletRequest(); + HttpServletResponse response = event.getHttpServletResponse(); + + if (event.getEventType() == CometEvent.EventType.BEGIN) { + String action = request.getParameter("action"); + if (action != null) { + if ("login".equals(action)) { + String nickname = request.getParameter("nickname"); + request.getSession(true).setAttribute("nickname", nickname); + response.sendRedirect("index.jsp"); + event.close(); + return; + } + String nickname = (String) request.getSession(true).getAttribute("nickname"); + String message = request.getParameter("message"); + messageSender.send(nickname, message); + response.sendRedirect("post.jsp"); + event.close(); + return; + } + if (request.getSession(true).getAttribute("nickname") == null) { + // Redirect to "login" + log("Redirect to login for session: " + request.getSession(true).getId()); + response.sendRedirect("login.jsp"); + event.close(); + return; + } + begin(event, request, response); + } else if (event.getEventType() == CometEvent.EventType.ERROR) { + error(event, request, response); + } else if (event.getEventType() == CometEvent.EventType.END) { + end(event, request, response); + } else if (event.getEventType() == CometEvent.EventType.READ) { + read(event, request, response); + } + } + + protected void begin(@SuppressWarnings("unused") CometEvent event, + HttpServletRequest request, HttpServletResponse response) + throws IOException { + log("Begin for session: " + request.getSession(true).getId()); + + response.setContentType("text/html; charset=" + CHARSET); + + PrintWriter writer = response.getWriter(); + writer.println(""); + writer.println("JSP Chat"); + writer.println("

    "); + writer.flush(); + + synchronized(connections) { + connections.add(response); + } + + messageSender.send("Tomcat", request.getSession(true).getAttribute("nickname") + " joined the chat."); + } + + protected void end(CometEvent event, HttpServletRequest request, HttpServletResponse response) + throws IOException { + log("End for session: " + request.getSession(true).getId()); + synchronized(connections) { + connections.remove(response); + } + + PrintWriter writer = response.getWriter(); + writer.println(""); + + event.close(); + } + + protected void error(CometEvent event, HttpServletRequest request, HttpServletResponse response) + throws IOException { + log("Error for session: " + request.getSession(true).getId()); + synchronized(connections) { + connections.remove(response); + } + event.close(); + } + + protected void read(CometEvent event, HttpServletRequest request, HttpServletResponse response) + throws IOException { + InputStream is = request.getInputStream(); + byte[] buf = new byte[512]; + while (is.available() > 0) { + log("Available: " + is.available()); + int n = is.read(buf); + if (n > 0) { + log("Read " + n + " bytes: " + new String(buf, 0, n) + + " for session: " + request.getSession(true).getId()); + } else if (n < 0) { + log("End of file: " + n); + end(event, request, response); + return; + } + } + } + + @Override + protected void service(HttpServletRequest request, HttpServletResponse response) + throws IOException, ServletException { + // Compatibility method: equivalent method using the regular connection model + response.setContentType("text/html; charset=" + CHARSET); + PrintWriter writer = response.getWriter(); + writer.println(""); + writer.println("JSP Chat"); + writer.println("Chat example only supports Comet processing. "); + writer.println("Configure a connector that supports Comet and try again."); + writer.println(""); + } + + + /** + * Poller class. + */ + public class MessageSender implements Runnable { + + protected boolean running = true; + protected ArrayList messages = new ArrayList(); + + public MessageSender() { + // Default contructor + } + + public void stop() { + running = false; + synchronized (messages) { + messages.notify(); + } + } + + public void send(String user, String message) { + synchronized (messages) { + messages.add("[" + user + "]: " + message); + messages.notify(); + } + } + + /** + * The background thread that listens for incoming TCP/IP connections and + * hands them off to an appropriate processor. + */ + @Override + public void run() { + + // Loop until we receive a shutdown command + while (running) { + String[] pendingMessages; + synchronized (messages) { + try { + if (messages.size() == 0) { + messages.wait(); + } + } catch (InterruptedException e) { + // Ignore + } + pendingMessages = messages.toArray(new String[0]); + messages.clear(); + } + + synchronized (connections) { + for (int i = 0; i < connections.size(); i++) { + try { + PrintWriter writer = connections.get(i).getWriter(); + for (int j = 0; j < pendingMessages.length; j++) { + writer.println("
    "+filter(pendingMessages[j]) + "
    "); + } + writer.flush(); + } catch (IOException e) { + log("IOException sending message", e); + } + } + } + + } + + } + + } + + /** + * Filter the specified message string for characters that are sensitive + * in HTML. + * + * @param message The message string to be filtered + * @author Copied from org.apache.catalina.util.RequestUtil#filter(String) + */ + protected static String filter(String message) { + if (message == null) + return (null); + + char content[] = new char[message.length()]; + message.getChars(0, message.length(), content, 0); + StringBuilder result = new StringBuilder(content.length + 50); + for (int i = 0; i < content.length; i++) { + switch (content[i]) { + case '<': + result.append("<"); + break; + case '>': + result.append(">"); + break; + case '&': + result.append("&"); + break; + case '"': + result.append("""); + break; + default: + result.append(content[i]); + } + } + return (result.toString()); + } +} diff --git a/webapps/examples/WEB-INF/classes/checkbox/CheckTest.java b/webapps/examples/WEB-INF/classes/checkbox/CheckTest.java new file mode 100644 index 000000000000..e38269c95af5 --- /dev/null +++ b/webapps/examples/WEB-INF/classes/checkbox/CheckTest.java @@ -0,0 +1,31 @@ +/* +* Licensed to the Apache Software Foundation (ASF) under one or more +* contributor license agreements. See the NOTICE file distributed with +* this work for additional information regarding copyright ownership. +* The ASF licenses this file to You under the Apache License, Version 2.0 +* (the "License"); you may not use this file except in compliance with +* the License. You may obtain a copy of the License at +* +* http://www.apache.org/licenses/LICENSE-2.0 +* +* Unless required by applicable law or agreed to in writing, software +* distributed under the License is distributed on an "AS IS" BASIS, +* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +* See the License for the specific language governing permissions and +* limitations under the License. +*/ + +package checkbox; + +public class CheckTest { + + String b[] = new String[] { "1", "2", "3", "4" }; + + public String[] getFruit() { + return b; + } + + public void setFruit(String [] b) { + this.b = b; + } +} diff --git a/webapps/examples/WEB-INF/classes/colors/ColorGameBean.java b/webapps/examples/WEB-INF/classes/colors/ColorGameBean.java new file mode 100644 index 000000000000..20b85d8125ed --- /dev/null +++ b/webapps/examples/WEB-INF/classes/colors/ColorGameBean.java @@ -0,0 +1,113 @@ +/* +* Licensed to the Apache Software Foundation (ASF) under one or more +* contributor license agreements. See the NOTICE file distributed with +* this work for additional information regarding copyright ownership. +* The ASF licenses this file to You under the Apache License, Version 2.0 +* (the "License"); you may not use this file except in compliance with +* the License. You may obtain a copy of the License at +* +* http://www.apache.org/licenses/LICENSE-2.0 +* +* Unless required by applicable law or agreed to in writing, software +* distributed under the License is distributed on an "AS IS" BASIS, +* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +* See the License for the specific language governing permissions and +* limitations under the License. +*/ +package colors; + +public class ColorGameBean { + + private String background = "yellow"; + private String foreground = "red"; + private String color1 = foreground; + private String color2 = background; + private String hint = "no"; + private int attempts = 0; + private int intval = 0; + private boolean tookHints = false; + + public void processRequest() { + + // background = "yellow"; + // foreground = "red"; + + if (! color1.equals(foreground)) { + if (color1.equalsIgnoreCase("black") || + color1.equalsIgnoreCase("cyan")) { + background = color1; + } + } + + if (! color2.equals(background)) { + if (color2.equalsIgnoreCase("black") || + color2.equalsIgnoreCase("cyan")) { + foreground = color2; + } + } + + attempts++; + } + + public void setColor2(String x) { + color2 = x; + } + + public void setColor1(String x) { + color1 = x; + } + + public void setAction(String x) { + if (!tookHints) + tookHints = x.equalsIgnoreCase("Hint"); + hint = x; + } + + public String getColor2() { + return background; + } + + public String getColor1() { + return foreground; + } + + public int getAttempts() { + return attempts; + } + + public boolean getHint() { + return hint.equalsIgnoreCase("Hint"); + } + + public boolean getSuccess() { + if (background.equalsIgnoreCase("black") || + background.equalsIgnoreCase("cyan")) { + + if (foreground.equalsIgnoreCase("black") || + foreground.equalsIgnoreCase("cyan")) { + return true; + } + return false; + } + + return false; + } + + public boolean getHintTaken() { + return tookHints; + } + + public void reset() { + foreground = "red"; + background = "yellow"; + } + + public void setIntval(int value) { + intval = value; + } + + public int getIntval() { + return intval; + } +} + diff --git a/webapps/examples/WEB-INF/classes/compressionFilters/CompressionFilter.java b/webapps/examples/WEB-INF/classes/compressionFilters/CompressionFilter.java new file mode 100644 index 000000000000..b1081630bb10 --- /dev/null +++ b/webapps/examples/WEB-INF/classes/compressionFilters/CompressionFilter.java @@ -0,0 +1,223 @@ +/* +* Licensed to the Apache Software Foundation (ASF) under one or more +* contributor license agreements. See the NOTICE file distributed with +* this work for additional information regarding copyright ownership. +* The ASF licenses this file to You under the Apache License, Version 2.0 +* (the "License"); you may not use this file except in compliance with +* the License. You may obtain a copy of the License at +* +* http://www.apache.org/licenses/LICENSE-2.0 +* +* Unless required by applicable law or agreed to in writing, software +* distributed under the License is distributed on an "AS IS" BASIS, +* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +* See the License for the specific language governing permissions and +* limitations under the License. +*/ + +package compressionFilters; + +import java.io.IOException; +import java.util.Enumeration; + +import javax.servlet.Filter; +import javax.servlet.FilterChain; +import javax.servlet.FilterConfig; +import javax.servlet.ServletException; +import javax.servlet.ServletRequest; +import javax.servlet.ServletResponse; +import javax.servlet.http.HttpServletRequest; +import javax.servlet.http.HttpServletResponse; + + +/** + * Implementation of javax.servlet.Filter used to compress + * the ServletResponse if it is bigger than a threshold. + * + * @author Amy Roh + * @author Dmitri Valdin + * @version $Id$ + */ + +public class CompressionFilter implements Filter{ + + /** + * The filter configuration object we are associated with. If this value + * is null, this filter instance is not currently configured. + */ + private FilterConfig config = null; + + /** + * Minimal reasonable threshold + */ + private int minThreshold = 128; + + + /** + * The threshold number to compress + */ + protected int compressionThreshold; + + /** + * Debug level for this filter + */ + private int debug = 0; + + /** + * Place this filter into service. + * + * @param filterConfig The filter configuration object + */ + + @Override + public void init(FilterConfig filterConfig) { + + config = filterConfig; + if (filterConfig != null) { + String value = filterConfig.getInitParameter("debug"); + if (value!=null) { + debug = Integer.parseInt(value); + } else { + debug = 0; + } + String str = filterConfig.getInitParameter("compressionThreshold"); + if (str!=null) { + compressionThreshold = Integer.parseInt(str); + if (compressionThreshold != 0 && compressionThreshold < minThreshold) { + if (debug > 0) { + System.out.println("compressionThreshold should be either 0 - no compression or >= " + minThreshold); + System.out.println("compressionThreshold set to " + minThreshold); + } + compressionThreshold = minThreshold; + } + } else { + compressionThreshold = 0; + } + + } else { + compressionThreshold = 0; + } + + } + + /** + * Take this filter out of service. + */ + @Override + public void destroy() { + + this.config = null; + + } + + /** + * The doFilter method of the Filter is called by the container + * each time a request/response pair is passed through the chain due + * to a client request for a resource at the end of the chain. + * The FilterChain passed into this method allows the Filter to pass on the + * request and response to the next entity in the chain.

    + * This method first examines the request to check whether the client support + * compression.
    + * It simply just pass the request and response if there is no support for + * compression.
    + * If the compression support is available, it creates a + * CompressionServletResponseWrapper object which compresses the content and + * modifies the header if the content length is big enough. + * It then invokes the next entity in the chain using the FilterChain object + * (chain.doFilter()),
    + **/ + + @Override + public void doFilter ( ServletRequest request, ServletResponse response, + FilterChain chain ) throws IOException, ServletException { + + if (debug > 0) { + System.out.println("@doFilter"); + } + + if (compressionThreshold == 0) { + if (debug > 0) { + System.out.println("doFilter gets called, but compressionTreshold is set to 0 - no compression"); + } + chain.doFilter(request, response); + return; + } + + boolean supportCompression = false; + if (request instanceof HttpServletRequest) { + if (debug > 1) { + System.out.println("requestURI = " + ((HttpServletRequest)request).getRequestURI()); + } + + // Are we allowed to compress ? + String s = ((HttpServletRequest)request).getParameter("gzip"); + if ("false".equals(s)) { + if (debug > 0) { + System.out.println("got parameter gzip=false --> don't compress, just chain filter"); + } + chain.doFilter(request, response); + return; + } + + Enumeration e = + ((HttpServletRequest)request).getHeaders("Accept-Encoding"); + while (e.hasMoreElements()) { + String name = e.nextElement(); + if (name.indexOf("gzip") != -1) { + if (debug > 0) { + System.out.println("supports compression"); + } + supportCompression = true; + } else { + if (debug > 0) { + System.out.println("no support for compresion"); + } + } + } + } + + if (!supportCompression) { + if (debug > 0) { + System.out.println("doFilter gets called wo compression"); + } + chain.doFilter(request, response); + return; + } + + if (response instanceof HttpServletResponse) { + CompressionServletResponseWrapper wrappedResponse = + new CompressionServletResponseWrapper((HttpServletResponse)response); + wrappedResponse.setDebugLevel(debug); + wrappedResponse.setCompressionThreshold(compressionThreshold); + if (debug > 0) { + System.out.println("doFilter gets called with compression"); + } + try { + chain.doFilter(request, wrappedResponse); + } finally { + wrappedResponse.finishResponse(); + } + return; + } + } + + /** + * Set filter config + * This function is equivalent to init. Required by Weblogic 6.1 + * + * @param filterConfig The filter configuration object + */ + public void setFilterConfig(FilterConfig filterConfig) { + init(filterConfig); + } + + /** + * Return filter config + * Required by Weblogic 6.1 + */ + public FilterConfig getFilterConfig() { + return config; + } + +} + diff --git a/webapps/examples/WEB-INF/classes/compressionFilters/CompressionFilterTestServlet.java b/webapps/examples/WEB-INF/classes/compressionFilters/CompressionFilterTestServlet.java new file mode 100644 index 000000000000..7d873fb8ee57 --- /dev/null +++ b/webapps/examples/WEB-INF/classes/compressionFilters/CompressionFilterTestServlet.java @@ -0,0 +1,64 @@ +/* +* Licensed to the Apache Software Foundation (ASF) under one or more +* contributor license agreements. See the NOTICE file distributed with +* this work for additional information regarding copyright ownership. +* The ASF licenses this file to You under the Apache License, Version 2.0 +* (the "License"); you may not use this file except in compliance with +* the License. You may obtain a copy of the License at +* +* http://www.apache.org/licenses/LICENSE-2.0 +* +* Unless required by applicable law or agreed to in writing, software +* distributed under the License is distributed on an "AS IS" BASIS, +* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +* See the License for the specific language governing permissions and +* limitations under the License. +*/ + +package compressionFilters; + +import java.io.IOException; +import java.util.Enumeration; + +import javax.servlet.ServletException; +import javax.servlet.ServletOutputStream; +import javax.servlet.http.HttpServlet; +import javax.servlet.http.HttpServletRequest; +import javax.servlet.http.HttpServletResponse; + +/** + * Very Simple test servlet to test compression filter + * @author Amy Roh + * @version $Id$ + */ + +public class CompressionFilterTestServlet extends HttpServlet { + + private static final long serialVersionUID = 1L; + + @Override + public void doGet(HttpServletRequest request, HttpServletResponse response) + throws ServletException, IOException { + + ServletOutputStream out = response.getOutputStream(); + response.setContentType("text/plain"); + + Enumeration e = request.getHeaders("Accept-Encoding"); + while (e.hasMoreElements()) { + String name = e.nextElement(); + out.println(name); + if (name.indexOf("gzip") != -1) { + out.println("gzip supported -- able to compress"); + } + else { + out.println("gzip not supported"); + } + } + + + out.println("Compression Filter Test Servlet"); + out.close(); + } + +} + diff --git a/webapps/examples/WEB-INF/classes/compressionFilters/CompressionResponseStream.java b/webapps/examples/WEB-INF/classes/compressionFilters/CompressionResponseStream.java new file mode 100644 index 000000000000..77610789b3f5 --- /dev/null +++ b/webapps/examples/WEB-INF/classes/compressionFilters/CompressionResponseStream.java @@ -0,0 +1,340 @@ +/* +* Licensed to the Apache Software Foundation (ASF) under one or more +* contributor license agreements. See the NOTICE file distributed with +* this work for additional information regarding copyright ownership. +* The ASF licenses this file to You under the Apache License, Version 2.0 +* (the "License"); you may not use this file except in compliance with +* the License. You may obtain a copy of the License at +* +* http://www.apache.org/licenses/LICENSE-2.0 +* +* Unless required by applicable law or agreed to in writing, software +* distributed under the License is distributed on an "AS IS" BASIS, +* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +* See the License for the specific language governing permissions and +* limitations under the License. +*/ +package compressionFilters; + +import java.io.IOException; +import java.io.OutputStream; +import java.util.zip.GZIPOutputStream; + +import javax.servlet.ServletOutputStream; +import javax.servlet.http.HttpServletResponse; + + +/** + * Implementation of ServletOutputStream that works with + * the CompressionServletResponseWrapper implementation. + * + * @author Amy Roh + * @author Dmitri Valdin + * @version $Id$ + */ + +public class CompressionResponseStream + extends ServletOutputStream { + + + // ----------------------------------------------------------- Constructors + + + /** + * Construct a servlet output stream associated with the specified Response. + * + * @param response The associated response + */ + public CompressionResponseStream(HttpServletResponse response) throws IOException{ + + super(); + closed = false; + this.response = response; + this.output = response.getOutputStream(); + + } + + + // ----------------------------------------------------- Instance Variables + + + /** + * The threshold number which decides to compress or not. + * Users can configure in web.xml to set it to fit their needs. + */ + protected int compressionThreshold = 0; + + /** + * Debug level + */ + private int debug = 0; + + /** + * The buffer through which all of our output bytes are passed. + */ + protected byte[] buffer = null; + + /** + * The number of data bytes currently in the buffer. + */ + protected int bufferCount = 0; + + /** + * The underlying gzip output stream to which we should write data. + */ + protected OutputStream gzipstream = null; + + /** + * Has this stream been closed? + */ + protected boolean closed = false; + + /** + * The content length past which we will not write, or -1 if there is + * no defined content length. + */ + protected int length = -1; + + /** + * The response with which this servlet output stream is associated. + */ + protected HttpServletResponse response = null; + + /** + * The underlying servket output stream to which we should write data. + */ + protected ServletOutputStream output = null; + + + // --------------------------------------------------------- Public Methods + + /** + * Set debug level + */ + public void setDebugLevel(int debug) { + this.debug = debug; + } + + + /** + * Set the compressionThreshold number and create buffer for this size + */ + protected void setBuffer(int threshold) { + compressionThreshold = threshold; + buffer = new byte[compressionThreshold]; + if (debug > 1) { + System.out.println("buffer is set to "+compressionThreshold); + } + } + + /** + * Close this output stream, causing any buffered data to be flushed and + * any further output data to throw an IOException. + */ + @Override + public void close() throws IOException { + + if (debug > 1) { + System.out.println("close() @ CompressionResponseStream"); + } + if (closed) + throw new IOException("This output stream has already been closed"); + + if (gzipstream != null) { + flushToGZip(); + gzipstream.close(); + gzipstream = null; + } else { + if (bufferCount > 0) { + if (debug > 2) { + System.out.print("output.write("); + System.out.write(buffer, 0, bufferCount); + System.out.println(")"); + } + output.write(buffer, 0, bufferCount); + bufferCount = 0; + } + } + + output.close(); + closed = true; + + } + + + /** + * Flush any buffered data for this output stream, which also causes the + * response to be committed. + */ + @Override + public void flush() throws IOException { + + if (debug > 1) { + System.out.println("flush() @ CompressionResponseStream"); + } + if (closed) { + throw new IOException("Cannot flush a closed output stream"); + } + + if (gzipstream != null) { + gzipstream.flush(); + } + + } + + public void flushToGZip() throws IOException { + + if (debug > 1) { + System.out.println("flushToGZip() @ CompressionResponseStream"); + } + if (bufferCount > 0) { + if (debug > 1) { + System.out.println("flushing out to GZipStream, bufferCount = " + bufferCount); + } + writeToGZip(buffer, 0, bufferCount); + bufferCount = 0; + } + + } + + /** + * Write the specified byte to our output stream. + * + * @param b The byte to be written + * + * @exception IOException if an input/output error occurs + */ + @Override + public void write(int b) throws IOException { + + if (debug > 1) { + System.out.println("write "+b+" in CompressionResponseStream "); + } + if (closed) + throw new IOException("Cannot write to a closed output stream"); + + if (bufferCount >= buffer.length) { + flushToGZip(); + } + + buffer[bufferCount++] = (byte) b; + + } + + + /** + * Write b.length bytes from the specified byte array + * to our output stream. + * + * @param b The byte array to be written + * + * @exception IOException if an input/output error occurs + */ + @Override + public void write(byte b[]) throws IOException { + + write(b, 0, b.length); + + } + + + /** + * Write len bytes from the specified byte array, starting + * at the specified offset, to our output stream. + * + * @param b The byte array containing the bytes to be written + * @param off Zero-relative starting offset of the bytes to be written + * @param len The number of bytes to be written + * + * @exception IOException if an input/output error occurs + */ + @Override + public void write(byte b[], int off, int len) throws IOException { + + if (debug > 1) { + System.out.println("write, bufferCount = " + bufferCount + " len = " + len + " off = " + off); + } + if (debug > 2) { + System.out.print("write("); + System.out.write(b, off, len); + System.out.println(")"); + } + + if (closed) + throw new IOException("Cannot write to a closed output stream"); + + if (len == 0) + return; + + // Can we write into buffer ? + if (len <= (buffer.length - bufferCount)) { + System.arraycopy(b, off, buffer, bufferCount, len); + bufferCount += len; + return; + } + + // There is not enough space in buffer. Flush it ... + flushToGZip(); + + // ... and try again. Note, that bufferCount = 0 here ! + if (len <= (buffer.length - bufferCount)) { + System.arraycopy(b, off, buffer, bufferCount, len); + bufferCount += len; + return; + } + + // write direct to gzip + writeToGZip(b, off, len); + } + + public void writeToGZip(byte b[], int off, int len) throws IOException { + + if (debug > 1) { + System.out.println("writeToGZip, len = " + len); + } + if (debug > 2) { + System.out.print("writeToGZip("); + System.out.write(b, off, len); + System.out.println(")"); + } + if (gzipstream == null) { + if (debug > 1) { + System.out.println("new GZIPOutputStream"); + } + if (response.isCommitted()) { + if (debug > 1) + System.out.print("Response already committed. Using original output stream"); + gzipstream = output; + } else { + response.addHeader("Content-Encoding", "gzip"); + String vary = response.getHeader("Vary"); + if (vary == null) { + // Add a new Vary header + response.setHeader("Vary", "Accept-Encoding"); + } else if (vary.equals("*")) { + // No action required + } else { + // Merge into current header + response.setHeader("Vary", vary + ",Accept-Encoding"); + } + gzipstream = new GZIPOutputStream(output); + } + } + gzipstream.write(b, off, len); + + } + + + // -------------------------------------------------------- Package Methods + + + /** + * Has this response stream been closed? + */ + public boolean closed() { + + return (this.closed); + + } + +} diff --git a/webapps/examples/WEB-INF/classes/compressionFilters/CompressionServletResponseWrapper.java b/webapps/examples/WEB-INF/classes/compressionFilters/CompressionServletResponseWrapper.java new file mode 100644 index 000000000000..164390ae2624 --- /dev/null +++ b/webapps/examples/WEB-INF/classes/compressionFilters/CompressionServletResponseWrapper.java @@ -0,0 +1,253 @@ +/* +* Licensed to the Apache Software Foundation (ASF) under one or more +* contributor license agreements. See the NOTICE file distributed with +* this work for additional information regarding copyright ownership. +* The ASF licenses this file to You under the Apache License, Version 2.0 +* (the "License"); you may not use this file except in compliance with +* the License. You may obtain a copy of the License at +* +* http://www.apache.org/licenses/LICENSE-2.0 +* +* Unless required by applicable law or agreed to in writing, software +* distributed under the License is distributed on an "AS IS" BASIS, +* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +* See the License for the specific language governing permissions and +* limitations under the License. +*/ +package compressionFilters; + +import java.io.IOException; +import java.io.OutputStreamWriter; +import java.io.PrintWriter; + +import javax.servlet.ServletOutputStream; +import javax.servlet.http.HttpServletResponse; +import javax.servlet.http.HttpServletResponseWrapper; + +/** + * Implementation of HttpServletResponseWrapper that works with + * the CompressionServletResponseStream implementation.. + * + * @author Amy Roh + * @author Dmitri Valdin + * @version $Id$ + */ + +public class CompressionServletResponseWrapper extends HttpServletResponseWrapper { + + // ----------------------------------------------------- Constructor + + /** + * Calls the parent constructor which creates a ServletResponse adaptor + * wrapping the given response object. + */ + + public CompressionServletResponseWrapper(HttpServletResponse response) { + super(response); + origResponse = response; + if (debug > 1) { + System.out.println("CompressionServletResponseWrapper constructor gets called"); + } + } + + + // ----------------------------------------------------- Instance Variables + + /** + * Original response + */ + + protected HttpServletResponse origResponse = null; + + /** + * Descriptive information about this Response implementation. + */ + + protected static final String info = "CompressionServletResponseWrapper"; + + /** + * The ServletOutputStream that has been returned by + * getOutputStream(), if any. + */ + + protected ServletOutputStream stream = null; + + + /** + * The PrintWriter that has been returned by + * getWriter(), if any. + */ + + protected PrintWriter writer = null; + + /** + * The threshold number to compress + */ + protected int threshold = 0; + + /** + * Debug level + */ + private int debug = 0; + + /** + * Content type + */ + protected String contentType = null; + + // --------------------------------------------------------- Public Methods + + + /** + * Set content type + */ + @Override + public void setContentType(String contentType) { + if (debug > 1) { + System.out.println("setContentType to "+contentType); + } + this.contentType = contentType; + origResponse.setContentType(contentType); + } + + + /** + * Set threshold number + */ + public void setCompressionThreshold(int threshold) { + if (debug > 1) { + System.out.println("setCompressionThreshold to " + threshold); + } + this.threshold = threshold; + } + + + /** + * Set debug level + */ + public void setDebugLevel(int debug) { + this.debug = debug; + } + + + /** + * Create and return a ServletOutputStream to write the content + * associated with this Response. + * + * @exception IOException if an input/output error occurs + */ + public ServletOutputStream createOutputStream() throws IOException { + if (debug > 1) { + System.out.println("createOutputStream gets called"); + } + + CompressionResponseStream compressedStream = + new CompressionResponseStream(origResponse); + compressedStream.setDebugLevel(debug); + compressedStream.setBuffer(threshold); + + return compressedStream; + + } + + + /** + * Finish a response. + */ + public void finishResponse() { + try { + if (writer != null) { + writer.close(); + } else { + if (stream != null) + stream.close(); + } + } catch (IOException e) { + // Ignore + } + } + + + // ------------------------------------------------ ServletResponse Methods + + + /** + * Flush the buffer and commit this response. + * + * @exception IOException if an input/output error occurs + */ + @Override + public void flushBuffer() throws IOException { + if (debug > 1) { + System.out.println("flush buffer @ CompressionServletResponseWrapper"); + } + ((CompressionResponseStream)stream).flush(); + + } + + /** + * Return the servlet output stream associated with this Response. + * + * @exception IllegalStateException if getWriter has + * already been called for this response + * @exception IOException if an input/output error occurs + */ + @Override + public ServletOutputStream getOutputStream() throws IOException { + + if (writer != null) + throw new IllegalStateException("getWriter() has already been called for this response"); + + if (stream == null) + stream = createOutputStream(); + if (debug > 1) { + System.out.println("stream is set to "+stream+" in getOutputStream"); + } + + return (stream); + + } + + /** + * Return the writer associated with this Response. + * + * @exception IllegalStateException if getOutputStream has + * already been called for this response + * @exception IOException if an input/output error occurs + */ + @Override + public PrintWriter getWriter() throws IOException { + + if (writer != null) + return (writer); + + if (stream != null) + throw new IllegalStateException("getOutputStream() has already been called for this response"); + + stream = createOutputStream(); + if (debug > 1) { + System.out.println("stream is set to "+stream+" in getWriter"); + } + //String charset = getCharsetFromContentType(contentType); + String charEnc = origResponse.getCharacterEncoding(); + if (debug > 1) { + System.out.println("character encoding is " + charEnc); + } + // HttpServletResponse.getCharacterEncoding() shouldn't return null + // according the spec, so feel free to remove that "if" + if (charEnc != null) { + writer = new PrintWriter(new OutputStreamWriter(stream, charEnc)); + } else { + writer = new PrintWriter(stream); + } + + return (writer); + + } + + @Override + public void setContentLength(int length) { + // Don't, as compression will change it + } + +} diff --git a/webapps/examples/WEB-INF/classes/dates/JspCalendar.java b/webapps/examples/WEB-INF/classes/dates/JspCalendar.java new file mode 100644 index 000000000000..77ad2a3b0b08 --- /dev/null +++ b/webapps/examples/WEB-INF/classes/dates/JspCalendar.java @@ -0,0 +1,153 @@ +/* +* Licensed to the Apache Software Foundation (ASF) under one or more +* contributor license agreements. See the NOTICE file distributed with +* this work for additional information regarding copyright ownership. +* The ASF licenses this file to You under the Apache License, Version 2.0 +* (the "License"); you may not use this file except in compliance with +* the License. You may obtain a copy of the License at +* +* http://www.apache.org/licenses/LICENSE-2.0 +* +* Unless required by applicable law or agreed to in writing, software +* distributed under the License is distributed on an "AS IS" BASIS, +* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +* See the License for the specific language governing permissions and +* limitations under the License. +*/ +package dates; + +import java.util.Calendar; +import java.util.Date; + +public class JspCalendar { + Calendar calendar = null; + + public JspCalendar() { + calendar = Calendar.getInstance(); + Date trialTime = new Date(); + calendar.setTime(trialTime); + } + + public int getYear() { + return calendar.get(Calendar.YEAR); + } + + public String getMonth() { + int m = getMonthInt(); + String[] months = new String [] { "January", "February", "March", + "April", "May", "June", + "July", "August", "September", + "October", "November", "December" }; + if (m > 12) + return "Unknown to Man"; + + return months[m - 1]; + + } + + public String getDay() { + int x = getDayOfWeek(); + String[] days = new String[] {"Sunday", "Monday", "Tuesday", "Wednesday", + "Thursday", "Friday", "Saturday"}; + + if (x > 7) + return "Unknown to Man"; + + return days[x - 1]; + + } + + public int getMonthInt() { + return 1 + calendar.get(Calendar.MONTH); + } + + public String getDate() { + return getMonthInt() + "/" + getDayOfMonth() + "/" + getYear(); + + } + + public String getTime() { + return getHour() + ":" + getMinute() + ":" + getSecond(); + } + + public int getDayOfMonth() { + return calendar.get(Calendar.DAY_OF_MONTH); + } + + public int getDayOfYear() { + return calendar.get(Calendar.DAY_OF_YEAR); + } + + public int getWeekOfYear() { + return calendar.get(Calendar.WEEK_OF_YEAR); + } + + public int getWeekOfMonth() { + return calendar.get(Calendar.WEEK_OF_MONTH); + } + + public int getDayOfWeek() { + return calendar.get(Calendar.DAY_OF_WEEK); + } + + public int getHour() { + return calendar.get(Calendar.HOUR_OF_DAY); + } + + public int getMinute() { + return calendar.get(Calendar.MINUTE); + } + + + public int getSecond() { + return calendar.get(Calendar.SECOND); + } + + public static void main(String args[]) { + JspCalendar db = new JspCalendar(); + p("date: " + db.getDayOfMonth()); + p("year: " + db.getYear()); + p("month: " + db.getMonth()); + p("time: " + db.getTime()); + p("date: " + db.getDate()); + p("Day: " + db.getDay()); + p("DayOfYear: " + db.getDayOfYear()); + p("WeekOfYear: " + db.getWeekOfYear()); + p("era: " + db.getEra()); + p("ampm: " + db.getAMPM()); + p("DST: " + db.getDSTOffset()); + p("ZONE Offset: " + db.getZoneOffset()); + p("TIMEZONE: " + db.getUSTimeZone()); + } + + private static void p(String x) { + System.out.println(x); + } + + + public int getEra() { + return calendar.get(Calendar.ERA); + } + + public String getUSTimeZone() { + String[] zones = new String[] {"Hawaii", "Alaskan", "Pacific", + "Mountain", "Central", "Eastern"}; + + return zones[10 + getZoneOffset()]; + } + + public int getZoneOffset() { + return calendar.get(Calendar.ZONE_OFFSET)/(60*60*1000); + } + + + public int getDSTOffset() { + return calendar.get(Calendar.DST_OFFSET)/(60*60*1000); + } + + + public int getAMPM() { + return calendar.get(Calendar.AM_PM); + } +} + diff --git a/webapps/examples/WEB-INF/classes/error/Smart.java b/webapps/examples/WEB-INF/classes/error/Smart.java new file mode 100644 index 000000000000..82c22f6f5218 --- /dev/null +++ b/webapps/examples/WEB-INF/classes/error/Smart.java @@ -0,0 +1,30 @@ +/* + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed with + * this work for additional information regarding copyright ownership. + * The ASF licenses this file to You under the Apache License, Version 2.0 + * (the "License"); you may not use this file except in compliance with + * the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +package error; + +public class Smart { + + String name = "JSP"; + + public String getName() { + return name; + } + + public void setName(String name) { + this.name = name; + } +} diff --git a/webapps/examples/WEB-INF/classes/examples/ExampleTagBase.java b/webapps/examples/WEB-INF/classes/examples/ExampleTagBase.java new file mode 100644 index 000000000000..254af4776bde --- /dev/null +++ b/webapps/examples/WEB-INF/classes/examples/ExampleTagBase.java @@ -0,0 +1,81 @@ +/* +* Licensed to the Apache Software Foundation (ASF) under one or more +* contributor license agreements. See the NOTICE file distributed with +* this work for additional information regarding copyright ownership. +* The ASF licenses this file to You under the Apache License, Version 2.0 +* (the "License"); you may not use this file except in compliance with +* the License. You may obtain a copy of the License at +* +* http://www.apache.org/licenses/LICENSE-2.0 +* +* Unless required by applicable law or agreed to in writing, software +* distributed under the License is distributed on an "AS IS" BASIS, +* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +* See the License for the specific language governing permissions and +* limitations under the License. +*/ +package examples; + +import javax.servlet.jsp.JspException; +import javax.servlet.jsp.PageContext; +import javax.servlet.jsp.tagext.BodyContent; +import javax.servlet.jsp.tagext.BodyTagSupport; +import javax.servlet.jsp.tagext.Tag; + +public abstract class ExampleTagBase extends BodyTagSupport { + + private static final long serialVersionUID = 1L; + + @Override + public void setParent(Tag parent) { + this.parent = parent; + } + + @Override + public void setBodyContent(BodyContent bodyOut) { + this.bodyOut = bodyOut; + } + + @Override + public void setPageContext(PageContext pageContext) { + this.pageContext = pageContext; + } + + @Override + public Tag getParent() { + return this.parent; + } + + @Override + public int doStartTag() throws JspException { + return SKIP_BODY; + } + + @Override + public int doEndTag() throws JspException { + return EVAL_PAGE; + } + + + @Override + public void doInitBody() throws JspException { + // Default implementations for BodyTag methods as well + // just in case a tag decides to implement BodyTag. + } + + @Override + public int doAfterBody() throws JspException { + return SKIP_BODY; + } + + @Override + public void release() { + bodyOut = null; + pageContext = null; + parent = null; + } + + protected BodyContent bodyOut; + protected PageContext pageContext; + protected Tag parent; +} diff --git a/webapps/examples/WEB-INF/classes/examples/FooTag.java b/webapps/examples/WEB-INF/classes/examples/FooTag.java new file mode 100644 index 000000000000..a8bba6a9a59a --- /dev/null +++ b/webapps/examples/WEB-INF/classes/examples/FooTag.java @@ -0,0 +1,87 @@ +/* +* Licensed to the Apache Software Foundation (ASF) under one or more +* contributor license agreements. See the NOTICE file distributed with +* this work for additional information regarding copyright ownership. +* The ASF licenses this file to You under the Apache License, Version 2.0 +* (the "License"); you may not use this file except in compliance with +* the License. You may obtain a copy of the License at +* +* http://www.apache.org/licenses/LICENSE-2.0 +* +* Unless required by applicable law or agreed to in writing, software +* distributed under the License is distributed on an "AS IS" BASIS, +* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +* See the License for the specific language governing permissions and +* limitations under the License. +*/ +package examples; + +import java.io.IOException; + +import javax.servlet.jsp.JspException; +import javax.servlet.jsp.JspTagException; + +/** + * Example1: the simplest tag + * Collect attributes and call into some actions + * + * + */ + +public class FooTag extends ExampleTagBase { + + private static final long serialVersionUID = 1L; + + private String atts[] = new String[3]; + int i = 0; + + private final void setAtt(int index, String value) { + atts[index] = value; + } + + public void setAtt1(String value) { + setAtt(0, value); + } + + public void setAtt2(String value) { + setAtt(1, value); + } + + public void setAtt3(String value) { + setAtt(2, value); + } + + /** + * Process start tag + * + * @return EVAL_BODY_INCLUDE + */ + @Override + public int doStartTag() throws JspException { + i = 0; + return EVAL_BODY_BUFFERED; + } + + @Override + public void doInitBody() throws JspException { + pageContext.setAttribute("member", atts[i]); + i++; + } + + @Override + public int doAfterBody() throws JspException { + try { + if (i == 3) { + bodyOut.writeOut(bodyOut.getEnclosingWriter()); + return SKIP_BODY; + } + + pageContext.setAttribute("member", atts[i]); + i++; + return EVAL_BODY_BUFFERED; + } catch (IOException ex) { + throw new JspTagException(ex.toString()); + } + } +} + diff --git a/webapps/examples/WEB-INF/classes/examples/FooTagExtraInfo.java b/webapps/examples/WEB-INF/classes/examples/FooTagExtraInfo.java new file mode 100644 index 000000000000..470bfcda11af --- /dev/null +++ b/webapps/examples/WEB-INF/classes/examples/FooTagExtraInfo.java @@ -0,0 +1,36 @@ +/* +* Licensed to the Apache Software Foundation (ASF) under one or more +* contributor license agreements. See the NOTICE file distributed with +* this work for additional information regarding copyright ownership. +* The ASF licenses this file to You under the Apache License, Version 2.0 +* (the "License"); you may not use this file except in compliance with +* the License. You may obtain a copy of the License at +* +* http://www.apache.org/licenses/LICENSE-2.0 +* +* Unless required by applicable law or agreed to in writing, software +* distributed under the License is distributed on an "AS IS" BASIS, +* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +* See the License for the specific language governing permissions and +* limitations under the License. +*/ +package examples; + +import javax.servlet.jsp.tagext.TagData; +import javax.servlet.jsp.tagext.TagExtraInfo; +import javax.servlet.jsp.tagext.VariableInfo; + +public class FooTagExtraInfo extends TagExtraInfo { + @Override + public VariableInfo[] getVariableInfo(TagData data) { + return new VariableInfo[] + { + new VariableInfo("member", + "String", + true, + VariableInfo.NESTED) + }; + } +} + + diff --git a/webapps/examples/WEB-INF/classes/examples/LogTag.java b/webapps/examples/WEB-INF/classes/examples/LogTag.java new file mode 100644 index 000000000000..bb0289e24c66 --- /dev/null +++ b/webapps/examples/WEB-INF/classes/examples/LogTag.java @@ -0,0 +1,61 @@ +/* +* Licensed to the Apache Software Foundation (ASF) under one or more +* contributor license agreements. See the NOTICE file distributed with +* this work for additional information regarding copyright ownership. +* The ASF licenses this file to You under the Apache License, Version 2.0 +* (the "License"); you may not use this file except in compliance with +* the License. You may obtain a copy of the License at +* +* http://www.apache.org/licenses/LICENSE-2.0 +* +* Unless required by applicable law or agreed to in writing, software +* distributed under the License is distributed on an "AS IS" BASIS, +* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +* See the License for the specific language governing permissions and +* limitations under the License. +*/ +package examples; + +import java.io.IOException; + +import javax.servlet.jsp.JspException; +import javax.servlet.jsp.JspTagException; + +/** + * Log the contents of the body. Could be used to handle errors etc. + */ +public class LogTag extends ExampleTagBase { + + private static final long serialVersionUID = 1L; + + boolean toBrowser = false; + + public void setToBrowser(String value) { + if (value == null) + toBrowser = false; + else if (value.equalsIgnoreCase("true")) + toBrowser = true; + else + toBrowser = false; + } + + @Override + public int doStartTag() throws JspException { + return EVAL_BODY_BUFFERED; + } + + @Override + public int doAfterBody() throws JspException { + try { + String s = bodyOut.getString(); + System.err.println(s); + if (toBrowser) + bodyOut.writeOut(bodyOut.getEnclosingWriter()); + return SKIP_BODY; + } catch (IOException ex) { + throw new JspTagException(ex.toString()); + } + } +} + + diff --git a/webapps/examples/WEB-INF/classes/examples/ShowSource.java b/webapps/examples/WEB-INF/classes/examples/ShowSource.java new file mode 100644 index 000000000000..9194bda5eb21 --- /dev/null +++ b/webapps/examples/WEB-INF/classes/examples/ShowSource.java @@ -0,0 +1,74 @@ +/* +* Licensed to the Apache Software Foundation (ASF) under one or more +* contributor license agreements. See the NOTICE file distributed with +* this work for additional information regarding copyright ownership. +* The ASF licenses this file to You under the Apache License, Version 2.0 +* (the "License"); you may not use this file except in compliance with +* the License. You may obtain a copy of the License at +* +* http://www.apache.org/licenses/LICENSE-2.0 +* +* Unless required by applicable law or agreed to in writing, software +* distributed under the License is distributed on an "AS IS" BASIS, +* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +* See the License for the specific language governing permissions and +* limitations under the License. +*/ +package examples; + +import java.io.IOException; +import java.io.InputStream; +import java.util.Locale; + +import javax.servlet.jsp.JspException; +import javax.servlet.jsp.JspTagException; +import javax.servlet.jsp.JspWriter; +import javax.servlet.jsp.tagext.TagSupport; + +/** + * Display the sources of the JSP file. + */ +public class ShowSource extends TagSupport { + + private static final long serialVersionUID = 1L; + + String jspFile; + + public void setJspFile(String jspFile) { + this.jspFile = jspFile; + } + + @Override + public int doEndTag() throws JspException { + if ((jspFile.indexOf( ".." ) >= 0) || + (jspFile.toUpperCase(Locale.ENGLISH).indexOf("/WEB-INF/") != 0) || + (jspFile.toUpperCase(Locale.ENGLISH).indexOf("/META-INF/") != 0)) + throw new JspTagException("Invalid JSP file " + jspFile); + + InputStream in + = pageContext.getServletContext().getResourceAsStream(jspFile); + + if (in == null) + throw new JspTagException("Unable to find JSP file: "+jspFile); + + JspWriter out = pageContext.getOut(); + + + try { + out.println(""); + out.println("

    ");
    +            for(int ch = in.read(); ch != -1; ch = in.read())
    +                if (ch == '<')
    +                    out.print("<");
    +                else
    +                    out.print((char) ch);
    +            out.println("
    "); + out.println(""); + } catch (IOException ex) { + throw new JspTagException("IOException: "+ex.toString()); + } + return super.doEndTag(); + } +} + + diff --git a/webapps/examples/WEB-INF/classes/examples/ValuesTag.java b/webapps/examples/WEB-INF/classes/examples/ValuesTag.java new file mode 100644 index 000000000000..b33586059d78 --- /dev/null +++ b/webapps/examples/WEB-INF/classes/examples/ValuesTag.java @@ -0,0 +1,79 @@ +/* + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed with + * this work for additional information regarding copyright ownership. + * The ASF licenses this file to You under the Apache License, Version 2.0 + * (the "License"); you may not use this file except in compliance with + * the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +package examples; + +import java.io.IOException; + +import javax.servlet.jsp.JspException; +import javax.servlet.jsp.JspTagException; +import javax.servlet.jsp.JspWriter; +import javax.servlet.jsp.tagext.TagSupport; + +/** + * Accept and display a value. + */ +public class ValuesTag extends TagSupport { + + private static final long serialVersionUID = 1L; + + // Using "-1" as the default value, + // in the assumption that it won't be used as the value. + // Cannot use null here, because null is an important case + // that should be present in the tests. + private Object objectValue = "-1"; + private String stringValue = "-1"; + private long longValue = -1; + private double doubleValue = -1; + + public void setObject(Object objectValue) { + this.objectValue = objectValue; + } + + public void setString(String stringValue) { + this.stringValue = stringValue; + } + + public void setLong(long longValue) { + this.longValue = longValue; + } + + public void setDouble(double doubleValue) { + this.doubleValue = doubleValue; + } + + @Override + public int doEndTag() throws JspException { + JspWriter out = pageContext.getOut(); + + try { + if (!"-1".equals(objectValue)) { + out.print(objectValue); + } else if (!"-1".equals(stringValue)) { + out.print(stringValue); + } else if (longValue != -1) { + out.print(longValue); + } else if (doubleValue != -1) { + out.print(doubleValue); + } else { + out.print("-1"); + } + } catch (IOException ex) { + throw new JspTagException("IOException: " + ex.toString(), ex); + } + return super.doEndTag(); + } +} diff --git a/webapps/examples/WEB-INF/classes/filters/ExampleFilter.java b/webapps/examples/WEB-INF/classes/filters/ExampleFilter.java new file mode 100644 index 000000000000..004fda519f66 --- /dev/null +++ b/webapps/examples/WEB-INF/classes/filters/ExampleFilter.java @@ -0,0 +1,144 @@ +/* +* Licensed to the Apache Software Foundation (ASF) under one or more +* contributor license agreements. See the NOTICE file distributed with +* this work for additional information regarding copyright ownership. +* The ASF licenses this file to You under the Apache License, Version 2.0 +* (the "License"); you may not use this file except in compliance with +* the License. You may obtain a copy of the License at +* +* http://www.apache.org/licenses/LICENSE-2.0 +* +* Unless required by applicable law or agreed to in writing, software +* distributed under the License is distributed on an "AS IS" BASIS, +* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +* See the License for the specific language governing permissions and +* limitations under the License. +*/ + +package filters; + + +import java.io.IOException; + +import javax.servlet.Filter; +import javax.servlet.FilterChain; +import javax.servlet.FilterConfig; +import javax.servlet.ServletException; +import javax.servlet.ServletRequest; +import javax.servlet.ServletResponse; + + +/** + * Example filter that can be attached to either an individual servlet + * or to a URL pattern. This filter performs the following functions: + *
      + *
    • Attaches itself as a request attribute, under the attribute name + * defined by the value of the attribute initialization + * parameter.
    • + *
    • Calculates the number of milliseconds required to perform the + * servlet processing required by this request, including any + * subsequently defined filters, and logs the result to the servlet + * context log for this application. + *
    + * + * @author Craig McClanahan + * @version $Id$ + */ + +public final class ExampleFilter implements Filter { + + + // ----------------------------------------------------- Instance Variables + + + /** + * The request attribute name under which we store a reference to ourself. + */ + private String attribute = null; + + + /** + * The filter configuration object we are associated with. If this value + * is null, this filter instance is not currently configured. + */ + private FilterConfig filterConfig = null; + + + // --------------------------------------------------------- Public Methods + + + /** + * Take this filter out of service. + */ + @Override + public void destroy() { + + this.attribute = null; + this.filterConfig = null; + + } + + + /** + * Time the processing that is performed by all subsequent filters in the + * current filter stack, including the ultimately invoked servlet. + * + * @param request The servlet request we are processing + * @param response The servlet response we are creating + * @param chain The filter chain we are processing + * + * @exception IOException if an input/output error occurs + * @exception ServletException if a servlet error occurs + */ + @Override + public void doFilter(ServletRequest request, ServletResponse response, + FilterChain chain) + throws IOException, ServletException { + + // Store ourselves as a request attribute (if requested) + if (attribute != null) + request.setAttribute(attribute, this); + + // Time and log the subsequent processing + long startTime = System.currentTimeMillis(); + chain.doFilter(request, response); + long stopTime = System.currentTimeMillis(); + filterConfig.getServletContext().log + (this.toString() + ": " + (stopTime - startTime) + + " milliseconds"); + + } + + + /** + * Place this filter into service. + * + * @param fConfig The filter configuration object + */ + @Override + public void init(FilterConfig fConfig) throws ServletException { + + this.filterConfig = fConfig; + this.attribute = fConfig.getInitParameter("attribute"); + + } + + + /** + * Return a String representation of this object. + */ + @Override + public String toString() { + + if (filterConfig == null) + return ("TimingFilter()"); + StringBuilder sb = new StringBuilder("TimingFilter("); + sb.append(filterConfig); + sb.append(")"); + return (sb.toString()); + + } + + +} + diff --git a/webapps/examples/WEB-INF/classes/filters/SetCharacterEncodingFilter.java b/webapps/examples/WEB-INF/classes/filters/SetCharacterEncodingFilter.java new file mode 100644 index 000000000000..ad74d058c276 --- /dev/null +++ b/webapps/examples/WEB-INF/classes/filters/SetCharacterEncodingFilter.java @@ -0,0 +1,176 @@ +/* +* Licensed to the Apache Software Foundation (ASF) under one or more +* contributor license agreements. See the NOTICE file distributed with +* this work for additional information regarding copyright ownership. +* The ASF licenses this file to You under the Apache License, Version 2.0 +* (the "License"); you may not use this file except in compliance with +* the License. You may obtain a copy of the License at +* +* http://www.apache.org/licenses/LICENSE-2.0 +* +* Unless required by applicable law or agreed to in writing, software +* distributed under the License is distributed on an "AS IS" BASIS, +* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +* See the License for the specific language governing permissions and +* limitations under the License. +*/ + +package filters; + + +import java.io.IOException; + +import javax.servlet.Filter; +import javax.servlet.FilterChain; +import javax.servlet.FilterConfig; +import javax.servlet.ServletException; +import javax.servlet.ServletRequest; +import javax.servlet.ServletResponse; + + +/** + *

    Example filter that sets the character encoding to be used in parsing the + * incoming request, either unconditionally or only if the client did not + * specify a character encoding. Configuration of this filter is based on + * the following initialization parameters:

    + *
      + *
    • encoding - The character encoding to be configured + * for this request, either conditionally or unconditionally based on + * the ignore initialization parameter. This parameter + * is required, so there is no default.
    • + *
    • ignore - If set to "true", any character encoding + * specified by the client is ignored, and the value returned by the + * selectEncoding() method is set. If set to "false, + * selectEncoding() is called only if the + * client has not already specified an encoding. By default, this + * parameter is set to "true".
    • + *
    + * + *

    Although this filter can be used unchanged, it is also easy to + * subclass it and make the selectEncoding() method more + * intelligent about what encoding to choose, based on characteristics of + * the incoming request (such as the values of the Accept-Language + * and User-Agent headers, or a value stashed in the current + * user's session.

    + * + * @author Craig McClanahan + * @version $Id$ + */ + +public class SetCharacterEncodingFilter implements Filter { + + + // ----------------------------------------------------- Instance Variables + + + /** + * The default character encoding to set for requests that pass through + * this filter. + */ + protected String encoding = null; + + + /** + * The filter configuration object we are associated with. If this value + * is null, this filter instance is not currently configured. + */ + protected FilterConfig filterConfig = null; + + + /** + * Should a character encoding specified by the client be ignored? + */ + protected boolean ignore = true; + + + // --------------------------------------------------------- Public Methods + + + /** + * Take this filter out of service. + */ + @Override + public void destroy() { + + this.encoding = null; + this.filterConfig = null; + + } + + + /** + * Select and set (if specified) the character encoding to be used to + * interpret request parameters for this request. + * + * @param request The servlet request we are processing + * @param response The servlet response we are creating + * @param chain The filter chain we are processing + * + * @exception IOException if an input/output error occurs + * @exception ServletException if a servlet error occurs + */ + @Override + public void doFilter(ServletRequest request, ServletResponse response, + FilterChain chain) + throws IOException, ServletException { + + // Conditionally select and set the character encoding to be used + if (ignore || (request.getCharacterEncoding() == null)) { + String characterEncoding = selectEncoding(request); + if (characterEncoding != null) + request.setCharacterEncoding(characterEncoding); + } + + // Pass control on to the next filter + chain.doFilter(request, response); + + } + + + /** + * Place this filter into service. + * + * @param fConfig The filter configuration object + */ + @Override + public void init(FilterConfig fConfig) throws ServletException { + + this.filterConfig = fConfig; + this.encoding = fConfig.getInitParameter("encoding"); + String value = fConfig.getInitParameter("ignore"); + if (value == null) + this.ignore = true; + else if (value.equalsIgnoreCase("true")) + this.ignore = true; + else if (value.equalsIgnoreCase("yes")) + this.ignore = true; + else + this.ignore = false; + + } + + + // ------------------------------------------------------ Protected Methods + + + /** + * Select an appropriate character encoding to be used, based on the + * characteristics of the current request and/or filter initialization + * parameters. If no character encoding should be set, return + * null. + *

    + * The default implementation unconditionally returns the value configured + * by the encoding initialization parameter for this + * filter. + * + * @param request The servlet request we are processing + */ + protected String selectEncoding( + @SuppressWarnings("unused") ServletRequest request) { + + return (this.encoding); + + } + + +} diff --git a/webapps/examples/WEB-INF/classes/jsp2/examples/BookBean.java b/webapps/examples/WEB-INF/classes/jsp2/examples/BookBean.java new file mode 100644 index 000000000000..0f7b514cfdb7 --- /dev/null +++ b/webapps/examples/WEB-INF/classes/jsp2/examples/BookBean.java @@ -0,0 +1,44 @@ +/* +* Licensed to the Apache Software Foundation (ASF) under one or more +* contributor license agreements. See the NOTICE file distributed with +* this work for additional information regarding copyright ownership. +* The ASF licenses this file to You under the Apache License, Version 2.0 +* (the "License"); you may not use this file except in compliance with +* the License. You may obtain a copy of the License at +* +* http://www.apache.org/licenses/LICENSE-2.0 +* +* Unless required by applicable law or agreed to in writing, software +* distributed under the License is distributed on an "AS IS" BASIS, +* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +* See the License for the specific language governing permissions and +* limitations under the License. +*/ + + +package jsp2.examples; + +public class BookBean { + private String title; + private String author; + private String isbn; + + public BookBean( String title, String author, String isbn ) { + this.title = title; + this.author = author; + this.isbn = isbn; + } + + public String getTitle() { + return this.title; + } + + public String getAuthor() { + return this.author; + } + + public String getIsbn() { + return this.isbn; + } + +} diff --git a/webapps/examples/WEB-INF/classes/jsp2/examples/FooBean.java b/webapps/examples/WEB-INF/classes/jsp2/examples/FooBean.java new file mode 100644 index 000000000000..330511f71463 --- /dev/null +++ b/webapps/examples/WEB-INF/classes/jsp2/examples/FooBean.java @@ -0,0 +1,36 @@ +/* +* Licensed to the Apache Software Foundation (ASF) under one or more +* contributor license agreements. See the NOTICE file distributed with +* this work for additional information regarding copyright ownership. +* The ASF licenses this file to You under the Apache License, Version 2.0 +* (the "License"); you may not use this file except in compliance with +* the License. You may obtain a copy of the License at +* +* http://www.apache.org/licenses/LICENSE-2.0 +* +* Unless required by applicable law or agreed to in writing, software +* distributed under the License is distributed on an "AS IS" BASIS, +* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +* See the License for the specific language governing permissions and +* limitations under the License. +*/ + + +package jsp2.examples; + +public class FooBean { + private String bar; + + public FooBean() { + bar = "Initial value"; + } + + public String getBar() { + return this.bar; + } + + public void setBar(String bar) { + this.bar = bar; + } + +} diff --git a/webapps/examples/WEB-INF/classes/jsp2/examples/ValuesBean.java b/webapps/examples/WEB-INF/classes/jsp2/examples/ValuesBean.java new file mode 100644 index 000000000000..686039c7d7fd --- /dev/null +++ b/webapps/examples/WEB-INF/classes/jsp2/examples/ValuesBean.java @@ -0,0 +1,52 @@ +/* +* Licensed to the Apache Software Foundation (ASF) under one or more +* contributor license agreements. See the NOTICE file distributed with +* this work for additional information regarding copyright ownership. +* The ASF licenses this file to You under the Apache License, Version 2.0 +* (the "License"); you may not use this file except in compliance with +* the License. You may obtain a copy of the License at +* +* http://www.apache.org/licenses/LICENSE-2.0 +* +* Unless required by applicable law or agreed to in writing, software +* distributed under the License is distributed on an "AS IS" BASIS, +* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +* See the License for the specific language governing permissions and +* limitations under the License. +*/ + + +package jsp2.examples; + +/** + * Accept and display a value. + */ +public class ValuesBean { + private String string; + private double doubleValue; + private long longValue; + + public String getStringValue() { + return this.string; + } + + public void setStringValue(String string) { + this.string = string; + } + + public double getDoubleValue() { + return doubleValue; + } + + public void setDoubleValue(double doubleValue) { + this.doubleValue = doubleValue; + } + + public long getLongValue() { + return longValue; + } + + public void setLongValue(long longValue) { + this.longValue = longValue; + } +} diff --git a/webapps/examples/WEB-INF/classes/jsp2/examples/el/Functions.java b/webapps/examples/WEB-INF/classes/jsp2/examples/el/Functions.java new file mode 100644 index 000000000000..e8ccb8271c6e --- /dev/null +++ b/webapps/examples/WEB-INF/classes/jsp2/examples/el/Functions.java @@ -0,0 +1,45 @@ +/* +* Licensed to the Apache Software Foundation (ASF) under one or more +* contributor license agreements. See the NOTICE file distributed with +* this work for additional information regarding copyright ownership. +* The ASF licenses this file to You under the Apache License, Version 2.0 +* (the "License"); you may not use this file except in compliance with +* the License. You may obtain a copy of the License at +* +* http://www.apache.org/licenses/LICENSE-2.0 +* +* Unless required by applicable law or agreed to in writing, software +* distributed under the License is distributed on an "AS IS" BASIS, +* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +* See the License for the specific language governing permissions and +* limitations under the License. +*/ +package jsp2.examples.el; + +import java.util.Locale; + +/** + * Defines the functions for the jsp2 example tag library. + * + *

    Each function is defined as a static method.

    + */ +public class Functions { + public static String reverse( String text ) { + return new StringBuilder( text ).reverse().toString(); + } + + public static int numVowels( String text ) { + String vowels = "aeiouAEIOU"; + int result = 0; + for( int i = 0; i < text.length(); i++ ) { + if( vowels.indexOf( text.charAt( i ) ) != -1 ) { + result++; + } + } + return result; + } + + public static String caps( String text ) { + return text.toUpperCase(Locale.ENGLISH); + } +} diff --git a/webapps/examples/WEB-INF/classes/jsp2/examples/simpletag/EchoAttributesTag.java b/webapps/examples/WEB-INF/classes/jsp2/examples/simpletag/EchoAttributesTag.java new file mode 100644 index 000000000000..c6186af17c52 --- /dev/null +++ b/webapps/examples/WEB-INF/classes/jsp2/examples/simpletag/EchoAttributesTag.java @@ -0,0 +1,57 @@ +/* +* Licensed to the Apache Software Foundation (ASF) under one or more +* contributor license agreements. See the NOTICE file distributed with +* this work for additional information regarding copyright ownership. +* The ASF licenses this file to You under the Apache License, Version 2.0 +* (the "License"); you may not use this file except in compliance with +* the License. You may obtain a copy of the License at +* +* http://www.apache.org/licenses/LICENSE-2.0 +* +* Unless required by applicable law or agreed to in writing, software +* distributed under the License is distributed on an "AS IS" BASIS, +* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +* See the License for the specific language governing permissions and +* limitations under the License. +*/ + + +package jsp2.examples.simpletag; + +import java.io.IOException; +import java.util.ArrayList; + +import javax.servlet.jsp.JspException; +import javax.servlet.jsp.JspWriter; +import javax.servlet.jsp.tagext.DynamicAttributes; +import javax.servlet.jsp.tagext.SimpleTagSupport; + +/** + * SimpleTag handler that echoes all its attributes + */ +public class EchoAttributesTag + extends SimpleTagSupport + implements DynamicAttributes +{ + private ArrayList keys = new ArrayList(); + private ArrayList values = new ArrayList(); + + @Override + public void doTag() throws JspException, IOException { + JspWriter out = getJspContext().getOut(); + for( int i = 0; i < keys.size(); i++ ) { + String key = keys.get( i ); + Object value = values.get( i ); + out.println( "
  • " + key + " = " + value + "
  • " ); + } + } + + @Override + public void setDynamicAttribute( String uri, String localName, + Object value ) + throws JspException + { + keys.add( localName ); + values.add( value ); + } +} diff --git a/webapps/examples/WEB-INF/classes/jsp2/examples/simpletag/FindBookSimpleTag.java b/webapps/examples/WEB-INF/classes/jsp2/examples/simpletag/FindBookSimpleTag.java new file mode 100644 index 000000000000..db7f2b8f21aa --- /dev/null +++ b/webapps/examples/WEB-INF/classes/jsp2/examples/simpletag/FindBookSimpleTag.java @@ -0,0 +1,46 @@ +/* +* Licensed to the Apache Software Foundation (ASF) under one or more +* contributor license agreements. See the NOTICE file distributed with +* this work for additional information regarding copyright ownership. +* The ASF licenses this file to You under the Apache License, Version 2.0 +* (the "License"); you may not use this file except in compliance with +* the License. You may obtain a copy of the License at +* +* http://www.apache.org/licenses/LICENSE-2.0 +* +* Unless required by applicable law or agreed to in writing, software +* distributed under the License is distributed on an "AS IS" BASIS, +* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +* See the License for the specific language governing permissions and +* limitations under the License. +*/ + + +package jsp2.examples.simpletag; + +import javax.servlet.jsp.JspException; +import javax.servlet.jsp.tagext.SimpleTagSupport; + +import jsp2.examples.BookBean; + +/** + * SimpleTag handler that pretends to search for a book, and stores + * the result in a scoped variable. + */ +public class FindBookSimpleTag extends SimpleTagSupport { + private String var; + + private static final String BOOK_TITLE = "The Lord of the Rings"; + private static final String BOOK_AUTHOR = "J. R. R. Tolkein"; + private static final String BOOK_ISBN = "0618002251"; + + @Override + public void doTag() throws JspException { + BookBean book = new BookBean( BOOK_TITLE, BOOK_AUTHOR, BOOK_ISBN ); + getJspContext().setAttribute( this.var, book ); + } + + public void setVar( String var ) { + this.var = var; + } +} diff --git a/webapps/examples/WEB-INF/classes/jsp2/examples/simpletag/HelloWorldSimpleTag.java b/webapps/examples/WEB-INF/classes/jsp2/examples/simpletag/HelloWorldSimpleTag.java new file mode 100644 index 000000000000..f87736f9b769 --- /dev/null +++ b/webapps/examples/WEB-INF/classes/jsp2/examples/simpletag/HelloWorldSimpleTag.java @@ -0,0 +1,34 @@ +/* +* Licensed to the Apache Software Foundation (ASF) under one or more +* contributor license agreements. See the NOTICE file distributed with +* this work for additional information regarding copyright ownership. +* The ASF licenses this file to You under the Apache License, Version 2.0 +* (the "License"); you may not use this file except in compliance with +* the License. You may obtain a copy of the License at +* +* http://www.apache.org/licenses/LICENSE-2.0 +* +* Unless required by applicable law or agreed to in writing, software +* distributed under the License is distributed on an "AS IS" BASIS, +* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +* See the License for the specific language governing permissions and +* limitations under the License. +*/ + + +package jsp2.examples.simpletag; + +import java.io.IOException; + +import javax.servlet.jsp.JspException; +import javax.servlet.jsp.tagext.SimpleTagSupport; + +/** + * SimpleTag handler that prints "Hello, world!" + */ +public class HelloWorldSimpleTag extends SimpleTagSupport { + @Override + public void doTag() throws JspException, IOException { + getJspContext().getOut().write( "Hello, world!" ); + } +} diff --git a/webapps/examples/WEB-INF/classes/jsp2/examples/simpletag/RepeatSimpleTag.java b/webapps/examples/WEB-INF/classes/jsp2/examples/simpletag/RepeatSimpleTag.java new file mode 100644 index 000000000000..d1dadcc7595d --- /dev/null +++ b/webapps/examples/WEB-INF/classes/jsp2/examples/simpletag/RepeatSimpleTag.java @@ -0,0 +1,44 @@ +/* +* Licensed to the Apache Software Foundation (ASF) under one or more +* contributor license agreements. See the NOTICE file distributed with +* this work for additional information regarding copyright ownership. +* The ASF licenses this file to You under the Apache License, Version 2.0 +* (the "License"); you may not use this file except in compliance with +* the License. You may obtain a copy of the License at +* +* http://www.apache.org/licenses/LICENSE-2.0 +* +* Unless required by applicable law or agreed to in writing, software +* distributed under the License is distributed on an "AS IS" BASIS, +* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +* See the License for the specific language governing permissions and +* limitations under the License. +*/ + + +package jsp2.examples.simpletag; + +import java.io.IOException; + +import javax.servlet.jsp.JspException; +import javax.servlet.jsp.tagext.SimpleTagSupport; + +/** + * SimpleTag handler that accepts a num attribute and + * invokes its body 'num' times. + */ +public class RepeatSimpleTag extends SimpleTagSupport { + private int num; + + @Override + public void doTag() throws JspException, IOException { + for (int i=0; i
    " + this.label + + "
    " ); + } + + public void setColor( String color ) { + this.color = color; + } + + public void setLabel( String label ) { + this.label = label; + } +} diff --git a/webapps/examples/WEB-INF/classes/listeners/ContextListener.java b/webapps/examples/WEB-INF/classes/listeners/ContextListener.java new file mode 100644 index 000000000000..cd7a73a5acdb --- /dev/null +++ b/webapps/examples/WEB-INF/classes/listeners/ContextListener.java @@ -0,0 +1,140 @@ +/* +* Licensed to the Apache Software Foundation (ASF) under one or more +* contributor license agreements. See the NOTICE file distributed with +* this work for additional information regarding copyright ownership. +* The ASF licenses this file to You under the Apache License, Version 2.0 +* (the "License"); you may not use this file except in compliance with +* the License. You may obtain a copy of the License at +* +* http://www.apache.org/licenses/LICENSE-2.0 +* +* Unless required by applicable law or agreed to in writing, software +* distributed under the License is distributed on an "AS IS" BASIS, +* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +* See the License for the specific language governing permissions and +* limitations under the License. +*/ +package listeners; + + +import javax.servlet.ServletContext; +import javax.servlet.ServletContextAttributeEvent; +import javax.servlet.ServletContextAttributeListener; +import javax.servlet.ServletContextEvent; +import javax.servlet.ServletContextListener; + + +/** + * Example listener for context-related application events, which were + * introduced in the 2.3 version of the Servlet API. This listener + * merely documents the occurrence of such events in the application log + * associated with our servlet context. + * + * @author Craig R. McClanahan + * @version $Id$ + */ + +public final class ContextListener + implements ServletContextAttributeListener, ServletContextListener { + + + // ----------------------------------------------------- Instance Variables + + + /** + * The servlet context with which we are associated. + */ + private ServletContext context = null; + + + // --------------------------------------------------------- Public Methods + + + /** + * Record the fact that a servlet context attribute was added. + * + * @param event The servlet context attribute event + */ + @Override + public void attributeAdded(ServletContextAttributeEvent event) { + + log("attributeAdded('" + event.getName() + "', '" + + event.getValue() + "')"); + + } + + + /** + * Record the fact that a servlet context attribute was removed. + * + * @param event The servlet context attribute event + */ + @Override + public void attributeRemoved(ServletContextAttributeEvent event) { + + log("attributeRemoved('" + event.getName() + "', '" + + event.getValue() + "')"); + + } + + + /** + * Record the fact that a servlet context attribute was replaced. + * + * @param event The servlet context attribute event + */ + @Override + public void attributeReplaced(ServletContextAttributeEvent event) { + + log("attributeReplaced('" + event.getName() + "', '" + + event.getValue() + "')"); + + } + + + /** + * Record the fact that this web application has been destroyed. + * + * @param event The servlet context event + */ + @Override + public void contextDestroyed(ServletContextEvent event) { + + log("contextDestroyed()"); + this.context = null; + + } + + + /** + * Record the fact that this web application has been initialized. + * + * @param event The servlet context event + */ + @Override + public void contextInitialized(ServletContextEvent event) { + + this.context = event.getServletContext(); + log("contextInitialized()"); + + } + + + // -------------------------------------------------------- Private Methods + + + /** + * Log a message to the servlet context application log. + * + * @param message Message to be logged + */ + private void log(String message) { + + if (context != null) + context.log("ContextListener: " + message); + else + System.out.println("ContextListener: " + message); + + } + +} diff --git a/webapps/examples/WEB-INF/classes/listeners/SessionListener.java b/webapps/examples/WEB-INF/classes/listeners/SessionListener.java new file mode 100644 index 000000000000..f0ed53277196 --- /dev/null +++ b/webapps/examples/WEB-INF/classes/listeners/SessionListener.java @@ -0,0 +1,162 @@ +/* + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed with + * this work for additional information regarding copyright ownership. + * The ASF licenses this file to You under the Apache License, Version 2.0 + * (the "License"); you may not use this file except in compliance with + * the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +package listeners; + +import javax.servlet.ServletContext; +import javax.servlet.ServletContextEvent; +import javax.servlet.ServletContextListener; +import javax.servlet.http.HttpSessionAttributeListener; +import javax.servlet.http.HttpSessionBindingEvent; +import javax.servlet.http.HttpSessionEvent; +import javax.servlet.http.HttpSessionListener; + +/** + * Example listener for context-related application events, which were + * introduced in the 2.3 version of the Servlet API. This listener merely + * documents the occurrence of such events in the application log associated + * with our servlet context. + * + * @author Craig R. McClanahan + * @version $Id$ + */ + +public final class SessionListener implements ServletContextListener, + HttpSessionAttributeListener, HttpSessionListener { + + // ----------------------------------------------------- Instance Variables + + /** + * The servlet context with which we are associated. + */ + private ServletContext context = null; + + // --------------------------------------------------------- Public Methods + + /** + * Record the fact that a servlet context attribute was added. + * + * @param event + * The session attribute event + */ + @Override + public void attributeAdded(HttpSessionBindingEvent event) { + + log("attributeAdded('" + event.getSession().getId() + "', '" + + event.getName() + "', '" + event.getValue() + "')"); + + } + + /** + * Record the fact that a servlet context attribute was removed. + * + * @param event + * The session attribute event + */ + @Override + public void attributeRemoved(HttpSessionBindingEvent event) { + + log("attributeRemoved('" + event.getSession().getId() + "', '" + + event.getName() + "', '" + event.getValue() + "')"); + + } + + /** + * Record the fact that a servlet context attribute was replaced. + * + * @param event + * The session attribute event + */ + @Override + public void attributeReplaced(HttpSessionBindingEvent event) { + + log("attributeReplaced('" + event.getSession().getId() + "', '" + + event.getName() + "', '" + event.getValue() + "')"); + + } + + /** + * Record the fact that this web application has been destroyed. + * + * @param event + * The servlet context event + */ + @Override + public void contextDestroyed(ServletContextEvent event) { + + log("contextDestroyed()"); + this.context = null; + + } + + /** + * Record the fact that this web application has been initialized. + * + * @param event + * The servlet context event + */ + @Override + public void contextInitialized(ServletContextEvent event) { + + this.context = event.getServletContext(); + log("contextInitialized()"); + + } + + /** + * Record the fact that a session has been created. + * + * @param event + * The session event + */ + @Override + public void sessionCreated(HttpSessionEvent event) { + + log("sessionCreated('" + event.getSession().getId() + "')"); + + } + + /** + * Record the fact that a session has been destroyed. + * + * @param event + * The session event + */ + @Override + public void sessionDestroyed(HttpSessionEvent event) { + + log("sessionDestroyed('" + event.getSession().getId() + "')"); + + } + + // -------------------------------------------------------- Private Methods + + /** + * Log a message to the servlet context application log. + * + * @param message + * Message to be logged + */ + private void log(String message) { + + if (context != null) + context.log("SessionListener: " + message); + else + System.out.println("SessionListener: " + message); + + } + +} diff --git a/webapps/examples/WEB-INF/classes/num/NumberGuessBean.java b/webapps/examples/WEB-INF/classes/num/NumberGuessBean.java new file mode 100644 index 000000000000..1d3b1afb46b4 --- /dev/null +++ b/webapps/examples/WEB-INF/classes/num/NumberGuessBean.java @@ -0,0 +1,99 @@ +/* + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed with + * this work for additional information regarding copyright ownership. + * The ASF licenses this file to You under the Apache License, Version 2.0 + * (the "License"); you may not use this file except in compliance with + * the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +/* + * Originally written by Jason Hunter, http://www.servlets.com. + */ + +package num; + +import java.io.Serializable; +import java.util.Random; + +public class NumberGuessBean implements Serializable { + + private static final long serialVersionUID = 1L; + + private int answer; + private String hint; + private int numGuesses; + private boolean success; + private Random random = new Random(); + + public NumberGuessBean() { + reset(); + } + + public int getAnswer() { + return answer; + } + + public void setAnswer(int answer) { + this.answer = answer; + } + + public String getHint() { + return "" + hint; + } + + public void setHint(String hint) { + this.hint = hint; + } + + public void setNumGuesses(int numGuesses) { + this.numGuesses = numGuesses; + } + + public int getNumGuesses() { + return numGuesses; + } + + public boolean getSuccess() { + return success; + } + + public void setSuccess(boolean success) { + this.success = success; + } + + public void setGuess(String guess) { + numGuesses++; + + int g; + try { + g = Integer.parseInt(guess); + } catch (NumberFormatException e) { + g = -1; + } + + if (g == answer) { + success = true; + } else if (g == -1) { + hint = "a number next time"; + } else if (g < answer) { + hint = "higher"; + } else if (g > answer) { + hint = "lower"; + } + } + + public void reset() { + answer = Math.abs(random.nextInt() % 100) + 1; + success = false; + numGuesses = 0; + } +} diff --git a/webapps/examples/WEB-INF/classes/servletToJsp.java b/webapps/examples/WEB-INF/classes/servletToJsp.java new file mode 100644 index 000000000000..c0ccda0297d0 --- /dev/null +++ b/webapps/examples/WEB-INF/classes/servletToJsp.java @@ -0,0 +1,39 @@ +/* +* Licensed to the Apache Software Foundation (ASF) under one or more +* contributor license agreements. See the NOTICE file distributed with +* this work for additional information regarding copyright ownership. +* The ASF licenses this file to You under the Apache License, Version 2.0 +* (the "License"); you may not use this file except in compliance with +* the License. You may obtain a copy of the License at +* +* http://www.apache.org/licenses/LICENSE-2.0 +* +* Unless required by applicable law or agreed to in writing, software +* distributed under the License is distributed on an "AS IS" BASIS, +* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +* See the License for the specific language governing permissions and +* limitations under the License. +*/ + +import javax.servlet.http.HttpServlet; +import javax.servlet.http.HttpServletRequest; +import javax.servlet.http.HttpServletResponse; + +public class servletToJsp extends HttpServlet { + + private static final long serialVersionUID = 1L; + + @Override + public void doGet (HttpServletRequest request, + HttpServletResponse response) { + + try { + // Set the attribute and Forward to hello.jsp + request.setAttribute ("servletName", "servletToJsp"); + getServletConfig().getServletContext().getRequestDispatcher( + "/jsp/jsptoserv/hello.jsp").forward(request, response); + } catch (Exception ex) { + ex.printStackTrace (); + } + } +} diff --git a/webapps/examples/WEB-INF/classes/sessions/DummyCart.java b/webapps/examples/WEB-INF/classes/sessions/DummyCart.java new file mode 100644 index 000000000000..3e5023a9d5d1 --- /dev/null +++ b/webapps/examples/WEB-INF/classes/sessions/DummyCart.java @@ -0,0 +1,65 @@ +/* +* Licensed to the Apache Software Foundation (ASF) under one or more +* contributor license agreements. See the NOTICE file distributed with +* this work for additional information regarding copyright ownership. +* The ASF licenses this file to You under the Apache License, Version 2.0 +* (the "License"); you may not use this file except in compliance with +* the License. You may obtain a copy of the License at +* +* http://www.apache.org/licenses/LICENSE-2.0 +* +* Unless required by applicable law or agreed to in writing, software +* distributed under the License is distributed on an "AS IS" BASIS, +* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +* See the License for the specific language governing permissions and +* limitations under the License. +*/ +package sessions; + +import java.util.Vector; + +public class DummyCart { + Vector v = new Vector(); + String submit = null; + String item = null; + + private void addItem(String name) { + v.addElement(name); + } + + private void removeItem(String name) { + v.removeElement(name); + } + + public void setItem(String name) { + item = name; + } + + public void setSubmit(String s) { + submit = s; + } + + public String[] getItems() { + String[] s = new String[v.size()]; + v.copyInto(s); + return s; + } + + public void processRequest() { + // null value for submit - user hit enter instead of clicking on + // "add" or "remove" + if (submit == null || submit.equals("add")) + addItem(item); + else if (submit.equals("remove")) + removeItem(item); + + // reset at the end of the request + reset(); + } + + // reset + private void reset() { + submit = null; + item = null; + } +} diff --git a/webapps/examples/WEB-INF/classes/util/HTMLFilter.java b/webapps/examples/WEB-INF/classes/util/HTMLFilter.java new file mode 100644 index 000000000000..b7a6a8eef0be --- /dev/null +++ b/webapps/examples/WEB-INF/classes/util/HTMLFilter.java @@ -0,0 +1,69 @@ +/* +* Licensed to the Apache Software Foundation (ASF) under one or more +* contributor license agreements. See the NOTICE file distributed with +* this work for additional information regarding copyright ownership. +* The ASF licenses this file to You under the Apache License, Version 2.0 +* (the "License"); you may not use this file except in compliance with +* the License. You may obtain a copy of the License at +* +* http://www.apache.org/licenses/LICENSE-2.0 +* +* Unless required by applicable law or agreed to in writing, software +* distributed under the License is distributed on an "AS IS" BASIS, +* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +* See the License for the specific language governing permissions and +* limitations under the License. +*/ +package util; + +/** + * HTML filter utility. + * + * @author Craig R. McClanahan + * @author Tim Tye + * @version $Id$ + */ + +public final class HTMLFilter { + + + /** + * Filter the specified message string for characters that are sensitive + * in HTML. This avoids potential attacks caused by including JavaScript + * codes in the request URL that is often reported in error messages. + * + * @param message The message string to be filtered + */ + public static String filter(String message) { + + if (message == null) + return (null); + + char content[] = new char[message.length()]; + message.getChars(0, message.length(), content, 0); + StringBuilder result = new StringBuilder(content.length + 50); + for (int i = 0; i < content.length; i++) { + switch (content[i]) { + case '<': + result.append("<"); + break; + case '>': + result.append(">"); + break; + case '&': + result.append("&"); + break; + case '"': + result.append("""); + break; + default: + result.append(content[i]); + } + } + return (result.toString()); + + } + + +} + diff --git a/webapps/examples/WEB-INF/classes/validators/DebugValidator.java b/webapps/examples/WEB-INF/classes/validators/DebugValidator.java new file mode 100644 index 000000000000..7a7d7c6d5d1a --- /dev/null +++ b/webapps/examples/WEB-INF/classes/validators/DebugValidator.java @@ -0,0 +1,86 @@ +/* +* Licensed to the Apache Software Foundation (ASF) under one or more +* contributor license agreements. See the NOTICE file distributed with +* this work for additional information regarding copyright ownership. +* The ASF licenses this file to You under the Apache License, Version 2.0 +* (the "License"); you may not use this file except in compliance with +* the License. You may obtain a copy of the License at +* +* http://www.apache.org/licenses/LICENSE-2.0 +* +* Unless required by applicable law or agreed to in writing, software +* distributed under the License is distributed on an "AS IS" BASIS, +* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +* See the License for the specific language governing permissions and +* limitations under the License. +*/ + + +package validators; + + +import java.io.IOException; +import java.io.InputStream; + +import javax.servlet.jsp.tagext.PageData; +import javax.servlet.jsp.tagext.TagLibraryValidator; +import javax.servlet.jsp.tagext.ValidationMessage; + + +/** + * Example tag library validator that simply dumps the XML version of each + * page to standard output (which will typically be sent to the file + * $CATALINA_HOME/logs/catalina.out). To utilize it, simply + * include a taglib directive for this tag library at the top + * of your JSP page. + * + * @author Craig McClanahan + * @version $Id$ + */ + +public class DebugValidator extends TagLibraryValidator { + + + // ----------------------------------------------------- Instance Variables + + + // --------------------------------------------------------- Public Methods + + + /** + * Validate a JSP page. This will get invoked once per directive in the + * JSP page. This method will return null if the page is + * valid; otherwise the method should return an array of + * ValidationMessage objects. An array of length zero is + * also interpreted as no errors. + * + * @param prefix The value of the prefix argument in this directive + * @param uri The value of the URI argument in this directive + * @param page The page data for this page + */ + @Override + public ValidationMessage[] validate(String prefix, String uri, + PageData page) { + + System.out.println("---------- Prefix=" + prefix + " URI=" + uri + + "----------"); + + InputStream is = page.getInputStream(); + while (true) { + try { + int ch = is.read(); + if (ch < 0) + break; + System.out.print((char) ch); + } catch (IOException e) { + break; + } + } + System.out.println(); + System.out.println("-----------------------------------------------"); + return (null); + + } + + +} diff --git a/webapps/examples/WEB-INF/jsp/applet/Clock2.java b/webapps/examples/WEB-INF/jsp/applet/Clock2.java new file mode 100644 index 000000000000..0892d379cbef --- /dev/null +++ b/webapps/examples/WEB-INF/jsp/applet/Clock2.java @@ -0,0 +1,217 @@ +/* +* Licensed to the Apache Software Foundation (ASF) under one or more +* contributor license agreements. See the NOTICE file distributed with +* this work for additional information regarding copyright ownership. +* The ASF licenses this file to You under the Apache License, Version 2.0 +* (the "License"); you may not use this file except in compliance with +* the License. You may obtain a copy of the License at +* +* http://www.apache.org/licenses/LICENSE-2.0 +* +* Unless required by applicable law or agreed to in writing, software +* distributed under the License is distributed on an "AS IS" BASIS, +* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +* See the License for the specific language governing permissions and +* limitations under the License. +*/ + +import java.applet.Applet; +import java.awt.Color; +import java.awt.Font; +import java.awt.Graphics; +import java.text.SimpleDateFormat; +import java.util.Date; +import java.util.Locale; + + +/** + * Time! + * + * @author Rachel Gollub + */ + +public class Clock2 extends Applet implements Runnable { + Thread timer; // The thread that displays clock + int lastxs, lastys, lastxm, + lastym, lastxh, lastyh; // Dimensions used to draw hands + SimpleDateFormat formatter; // Formats the date displayed + String lastdate; // String to hold date displayed + Font clockFaceFont; // Font for number display on clock + Date currentDate; // Used to get date to display + Color handColor; // Color of main hands and dial + Color numberColor; // Color of second hand and numbers + + public void init() { + int x,y; + lastxs = lastys = lastxm = lastym = lastxh = lastyh = 0; + formatter = new SimpleDateFormat ("EEE MMM dd hh:mm:ss yyyy", Locale.getDefault()); + currentDate = new Date(); + lastdate = formatter.format(currentDate); + clockFaceFont = new Font("Serif", Font.PLAIN, 14); + handColor = Color.blue; + numberColor = Color.darkGray; + + try { + setBackground(new Color(Integer.parseInt(getParameter("bgcolor"),16))); + } catch (Exception E) { } + try { + handColor = new Color(Integer.parseInt(getParameter("fgcolor1"),16)); + } catch (Exception E) { } + try { + numberColor = new Color(Integer.parseInt(getParameter("fgcolor2"),16)); + } catch (Exception E) { } + resize(300,300); // Set clock window size + } + + // Plotpoints allows calculation to only cover 45 degrees of the circle, + // and then mirror + public void plotpoints(int x0, int y0, int x, int y, Graphics g) { + g.drawLine(x0+x,y0+y,x0+x,y0+y); + g.drawLine(x0+y,y0+x,x0+y,y0+x); + g.drawLine(x0+y,y0-x,x0+y,y0-x); + g.drawLine(x0+x,y0-y,x0+x,y0-y); + g.drawLine(x0-x,y0-y,x0-x,y0-y); + g.drawLine(x0-y,y0-x,x0-y,y0-x); + g.drawLine(x0-y,y0+x,x0-y,y0+x); + g.drawLine(x0-x,y0+y,x0-x,y0+y); + } + + // Circle is just Bresenham's algorithm for a scan converted circle + public void circle(int x0, int y0, int r, Graphics g) { + int x,y; + float d; + x=0; + y=r; + d=5/4-r; + plotpoints(x0,y0,x,y,g); + + while (y>x){ + if (d<0) { + d=d+2*x+3; + x++; + } + else { + d=d+2*(x-y)+5; + x++; + y--; + } + plotpoints(x0,y0,x,y,g); + } + } + + // Paint is the main part of the program + public void paint(Graphics g) { + int xh, yh, xm, ym, xs, ys, s = 0, m = 10, h = 10, xcenter, ycenter; + String today; + + currentDate = new Date(); + SimpleDateFormat formatter = new SimpleDateFormat("s",Locale.getDefault()); + try { + s = Integer.parseInt(formatter.format(currentDate)); + } catch (NumberFormatException n) { + s = 0; + } + formatter.applyPattern("m"); + try { + m = Integer.parseInt(formatter.format(currentDate)); + } catch (NumberFormatException n) { + m = 10; + } + formatter.applyPattern("h"); + try { + h = Integer.parseInt(formatter.format(currentDate)); + } catch (NumberFormatException n) { + h = 10; + } + formatter.applyPattern("EEE MMM dd HH:mm:ss yyyy"); + today = formatter.format(currentDate); + xcenter=80; + ycenter=55; + + // a= s* pi/2 - pi/2 (to switch 0,0 from 3:00 to 12:00) + // x = r(cos a) + xcenter, y = r(sin a) + ycenter + + xs = (int)(Math.cos(s * 3.14f/30 - 3.14f/2) * 45 + xcenter); + ys = (int)(Math.sin(s * 3.14f/30 - 3.14f/2) * 45 + ycenter); + xm = (int)(Math.cos(m * 3.14f/30 - 3.14f/2) * 40 + xcenter); + ym = (int)(Math.sin(m * 3.14f/30 - 3.14f/2) * 40 + ycenter); + xh = (int)(Math.cos((h*30 + m/2) * 3.14f/180 - 3.14f/2) * 30 + xcenter); + yh = (int)(Math.sin((h*30 + m/2) * 3.14f/180 - 3.14f/2) * 30 + ycenter); + + // Draw the circle and numbers + + g.setFont(clockFaceFont); + g.setColor(handColor); + circle(xcenter,ycenter,50,g); + g.setColor(numberColor); + g.drawString("9",xcenter-45,ycenter+3); + g.drawString("3",xcenter+40,ycenter+3); + g.drawString("12",xcenter-5,ycenter-37); + g.drawString("6",xcenter-3,ycenter+45); + + // Erase if necessary, and redraw + + g.setColor(getBackground()); + if (xs != lastxs || ys != lastys) { + g.drawLine(xcenter, ycenter, lastxs, lastys); + g.drawString(lastdate, 5, 125); + } + if (xm != lastxm || ym != lastym) { + g.drawLine(xcenter, ycenter-1, lastxm, lastym); + g.drawLine(xcenter-1, ycenter, lastxm, lastym); } + if (xh != lastxh || yh != lastyh) { + g.drawLine(xcenter, ycenter-1, lastxh, lastyh); + g.drawLine(xcenter-1, ycenter, lastxh, lastyh); } + g.setColor(numberColor); + g.drawString("", 5, 125); + g.drawString(today, 5, 125); + g.drawLine(xcenter, ycenter, xs, ys); + g.setColor(handColor); + g.drawLine(xcenter, ycenter-1, xm, ym); + g.drawLine(xcenter-1, ycenter, xm, ym); + g.drawLine(xcenter, ycenter-1, xh, yh); + g.drawLine(xcenter-1, ycenter, xh, yh); + lastxs=xs; lastys=ys; + lastxm=xm; lastym=ym; + lastxh=xh; lastyh=yh; + lastdate = today; + currentDate=null; + } + + public void start() { + timer = new Thread(this); + timer.start(); + } + + public void stop() { + timer = null; + } + + public void run() { + Thread me = Thread.currentThread(); + while (timer == me) { + try { + Thread.currentThread().sleep(100); + } catch (InterruptedException e) { + } + repaint(); + } + } + + public void update(Graphics g) { + paint(g); + } + + public String getAppletInfo() { + return "Title: A Clock \nAuthor: Rachel Gollub, 1995 \nAn analog clock."; + } + + public String[][] getParameterInfo() { + String[][] info = { + {"bgcolor", "hexadecimal RGB number", "The background color. Default is the color of your browser."}, + {"fgcolor1", "hexadecimal RGB number", "The color of the hands and dial. Default is blue."}, + {"fgcolor2", "hexadecimal RGB number", "The color of the seconds hand and numbers. Default is dark gray."} + }; + return info; + } +} diff --git a/webapps/examples/WEB-INF/jsp/debug-taglib.tld b/webapps/examples/WEB-INF/jsp/debug-taglib.tld new file mode 100644 index 000000000000..7e589ebf6104 --- /dev/null +++ b/webapps/examples/WEB-INF/jsp/debug-taglib.tld @@ -0,0 +1,54 @@ + + + + + + + + 1.0 + 1.2 + debug + http://tomcat.apache.org/debug-taglib + + This tag library defines no tags. Instead, its purpose is encapsulated + in the TagLibraryValidator implementation that simply outputs the XML + version of a JSP page to standard output, whenever this tag library is + referenced in a "taglib" directive in a JSP page. + + + validators.DebugValidator + + + + + log + examples.LogTag + TAGDEPENDENT + + Perform a server side action; Log the message. + + + toBrowser + false + + + + + diff --git a/webapps/examples/WEB-INF/jsp/example-taglib.tld b/webapps/examples/WEB-INF/jsp/example-taglib.tld new file mode 100644 index 000000000000..bd316d5b4b43 --- /dev/null +++ b/webapps/examples/WEB-INF/jsp/example-taglib.tld @@ -0,0 +1,118 @@ + + + + + + + 1.0 + 1.2 + simple + http://tomcat.apache.org/example-taglib + + A simple tab library for the examples + + + + ShowSource + examples.ShowSource + Display JSP sources + + jspFile + true + true + + + + + + + foo + examples.FooTag + examples.FooTagExtraInfo + JSP + + Perform a server side action; uses 3 mandatory attributes + + + + att1 + true + + + att2 + true + + + att3 + true + + + + + + + log + examples.LogTag + TAGDEPENDENT + + Perform a server side action; Log the message. + + + toBrowser + false + + + + + + + values + examples.ValuesTag + empty + + Accept and return values of different types. This tag is used + to illustrate type coercions. + + + object + false + true + java.lang.Object + + + string + false + true + java.lang.String + + + long + false + true + long + + + double + false + true + double + + + diff --git a/webapps/examples/WEB-INF/jsp2/jsp2-example-taglib.tld b/webapps/examples/WEB-INF/jsp2/jsp2-example-taglib.tld new file mode 100644 index 000000000000..bb2234ae8ec5 --- /dev/null +++ b/webapps/examples/WEB-INF/jsp2/jsp2-example-taglib.tld @@ -0,0 +1,124 @@ + + + + + A tag library exercising SimpleTag handlers. + 1.0 + SimpleTagLibrary + http://tomcat.apache.org/jsp2-example-taglib + + Outputs Hello, World + helloWorld + jsp2.examples.simpletag.HelloWorldSimpleTag + empty + + + Repeats the body of the tag 'num' times + repeat + jsp2.examples.simpletag.RepeatSimpleTag + scriptless + + Current invocation count (1 to num) + count + + + num + true + true + + + + Populates the page context with a BookBean + findBook + jsp2.examples.simpletag.FindBookSimpleTag + empty + + var + true + true + + + + + Takes 3 fragments and invokes them in a random order + + shuffle + jsp2.examples.simpletag.ShuffleSimpleTag + empty + + fragment1 + true + true + + + fragment2 + true + true + + + fragment3 + true + true + + + + Outputs a colored tile + tile + jsp2.examples.simpletag.TileSimpleTag + empty + + color + true + + + label + true + + + + + Tag that echoes all its attributes and body content + + echoAttributes + jsp2.examples.simpletag.EchoAttributesTag + empty + true + + + Reverses the characters in the given String + reverse + jsp2.examples.el.Functions + java.lang.String reverse( java.lang.String ) + + + Counts the number of vowels (a,e,i,o,u) in the given String + countVowels + jsp2.examples.el.Functions + java.lang.String numVowels( java.lang.String ) + + + Converts the string to all caps + caps + jsp2.examples.el.Functions + java.lang.String caps( java.lang.String ) + + + diff --git a/webapps/examples/WEB-INF/lib/jstl.jar b/webapps/examples/WEB-INF/lib/jstl.jar new file mode 100644 index 000000000000..a02abecc8b88 Binary files /dev/null and b/webapps/examples/WEB-INF/lib/jstl.jar differ diff --git a/webapps/examples/WEB-INF/lib/standard.jar b/webapps/examples/WEB-INF/lib/standard.jar new file mode 100644 index 000000000000..bc528acb9490 Binary files /dev/null and b/webapps/examples/WEB-INF/lib/standard.jar differ diff --git a/webapps/examples/WEB-INF/tags/displayProducts.tag b/webapps/examples/WEB-INF/tags/displayProducts.tag new file mode 100644 index 000000000000..10ad9f75c5ff --- /dev/null +++ b/webapps/examples/WEB-INF/tags/displayProducts.tag @@ -0,0 +1,55 @@ + +<%@ taglib prefix="c" uri="http://java.sun.com/jsp/jstl/core" %> +<%@ attribute name="normalPrice" fragment="true" %> +<%@ attribute name="onSale" fragment="true" %> +<%@ variable name-given="name" %> +<%@ variable name-given="price" %> +<%@ variable name-given="origPrice" %> +<%@ variable name-given="salePrice" %> + + + + + + + + + +
    + + + + + + + + + + + + + + + + + + + + + +
    diff --git a/webapps/examples/WEB-INF/tags/helloWorld.tag b/webapps/examples/WEB-INF/tags/helloWorld.tag new file mode 100644 index 000000000000..192bf53cc466 --- /dev/null +++ b/webapps/examples/WEB-INF/tags/helloWorld.tag @@ -0,0 +1,17 @@ + +Hello, world! diff --git a/webapps/examples/WEB-INF/tags/panel.tag b/webapps/examples/WEB-INF/tags/panel.tag new file mode 100644 index 000000000000..f4f30d0244e4 --- /dev/null +++ b/webapps/examples/WEB-INF/tags/panel.tag @@ -0,0 +1,29 @@ + +<%@ attribute name="color" %> +<%@ attribute name="bgcolor" %> +<%@ attribute name="title" %> + + + + + + + +
    ${title}
    + +
    diff --git a/webapps/examples/WEB-INF/tags/xhtmlbasic.tag b/webapps/examples/WEB-INF/tags/xhtmlbasic.tag new file mode 100644 index 000000000000..170a9bcf96f8 --- /dev/null +++ b/webapps/examples/WEB-INF/tags/xhtmlbasic.tag @@ -0,0 +1,21 @@ + + + + + diff --git a/webapps/examples/WEB-INF/web.xml b/webapps/examples/WEB-INF/web.xml new file mode 100644 index 000000000000..e64b37240ccc --- /dev/null +++ b/webapps/examples/WEB-INF/web.xml @@ -0,0 +1,346 @@ + + + + + + Servlet and JSP Examples. + + Servlet and JSP Examples + + + + + Timing filter + filters.ExampleFilter + + attribute + filters.ExampleFilter + + + + + Request Dumper Filter + org.apache.catalina.filters.RequestDumperFilter + + + + + Set Character Encoding + filters.SetCharacterEncodingFilter + + encoding + EUC_JP + + + + + Compression Filter + compressionFilters.CompressionFilter + + + compressionThreshold + 10 + + + debug + 0 + + + + + + + + + + + + + + + + listeners.ContextListener + + + listeners.SessionListener + + + + + + servletToJsp + servletToJsp + + + ChatServlet + chat.ChatServlet + + + CompressionFilterTestServlet + compressionFilters.CompressionFilterTestServlet + + + HelloWorldExample + HelloWorldExample + + + RequestInfoExample + RequestInfoExample + + + RequestHeaderExample + RequestHeaderExample + + + RequestParamExample + RequestParamExample + + + CookieExample + CookieExample + + + SessionExample + SessionExample + + + + ChatServlet + /jsp/chat/chat + + + CompressionFilterTestServlet + /CompressionTest + + + HelloWorldExample + /servlets/servlet/HelloWorldExample + + + RequestInfoExample + /servlets/servlet/RequestInfoExample/* + + + RequestHeaderExample + /servlets/servlet/RequestHeaderExample + + + RequestParamExample + /servlets/servlet/RequestParamExample + + + CookieExample + /servlets/servlet/CookieExample + + + SessionExample + /servlets/servlet/SessionExample + + + servletToJsp + /servletToJsp + + + + + + http://tomcat.apache.org/debug-taglib + + + /WEB-INF/jsp/debug-taglib.tld + + + + + + http://tomcat.apache.org/example-taglib + + + /WEB-INF/jsp/example-taglib.tld + + + + + + http://tomcat.apache.org/jsp2-example-taglib + + + /WEB-INF/jsp2/jsp2-example-taglib.tld + + + + + + Special property group for JSP Configuration JSP example. + + JSPConfiguration + /jsp/jsp2/misc/config.jsp + true + ISO-8859-1 + true + /jsp/jsp2/misc/prelude.jspf + /jsp/jsp2/misc/coda.jspf + + + + + Example Security Constraint + + Protected Area + + /jsp/security/protected/* + + DELETE + GET + POST + PUT + + + + tomcat + role1 + + + + + + FORM + Example Form-Based Authentication Area + + /jsp/security/protected/login.jsp + /jsp/security/protected/error.jsp + + + + + + role1 + + + tomcat + + + + + + minExemptions + java.lang.Integer + 1 + + + foo/name1 + java.lang.String + value1 + + + foo/bar/name2 + java.lang.Boolean + true + + + name3 + java.lang.Integer + 1 + + + foo/name4 + java.lang.Integer + 10 + + + + + async0 + async.Async0 + true + + + async0 + /async/async0 + + + async1 + async.Async1 + true + + + async1 + /async/async1 + + + async2 + async.Async2 + true + + + async2 + /async/async2 + + + async3 + async.Async3 + true + + + async3 + /async/async3 + + + stock + async.AsyncStockServlet + true + + + stock + /async/stockticker + + + diff --git a/webapps/examples/index.html b/webapps/examples/index.html new file mode 100644 index 000000000000..c15c007c7163 --- /dev/null +++ b/webapps/examples/index.html @@ -0,0 +1,29 @@ + + +Apache Tomcat Examples + + + +

    +

    Apache Tomcat Examples

    +

    + + diff --git a/webapps/examples/jsp/async/async1.jsp b/webapps/examples/jsp/async/async1.jsp new file mode 100644 index 000000000000..1a0e907c0ae4 --- /dev/null +++ b/webapps/examples/jsp/async/async1.jsp @@ -0,0 +1,26 @@ + +<%@page session="false"%> +Output from async1.jsp +Type is <%=request.getDispatcherType()%> +<% +System.out.println("Inside Async 1"); + if (request.isAsyncStarted()) { + request.getAsyncContext().complete(); + } +%> +Completed async request at <%=new java.sql.Date(System.currentTimeMillis())%> \ No newline at end of file diff --git a/webapps/examples/jsp/async/async3.jsp b/webapps/examples/jsp/async/async3.jsp new file mode 100644 index 000000000000..c7caf2d7864c --- /dev/null +++ b/webapps/examples/jsp/async/async3.jsp @@ -0,0 +1,20 @@ + +<%@page session="false"%> +Output from async3.jsp +Type is <%=request.getDispatcherType()%> +Completed async 3 request at <%=new java.sql.Date(System.currentTimeMillis())%> \ No newline at end of file diff --git a/webapps/examples/jsp/async/index.jsp b/webapps/examples/jsp/async/index.jsp new file mode 100644 index 000000000000..18f320d52651 --- /dev/null +++ b/webapps/examples/jsp/async/index.jsp @@ -0,0 +1,69 @@ + +<%@page session="false"%> + +
    +Use cases:
    +
    +1. Simple dispatch 
    + - servlet does startAsync()
    + - background thread calls ctx.dispatch() 
    +   "> Async 0 
    + 
    +2. Simple dispatch
    + - servlet does startAsync()
    + - background thread calls dispatch(/path/to/jsp)
    +   "> Async 1 
    + 
    +3. Simple dispatch
    + - servlet does startAsync()
    + - background thread calls writes and calls complete()
    +   "> Async 2 
    +
    +4. Simple dispatch
    + - servlet does a startAsync()
    + - servlet calls dispatch(/path/to/jsp)
    + - servlet calls complete()
    +   "> Async 3 
    +
    +3. Timeout s1
    + - servlet does a startAsync()
    + - servlet does a setAsyncTimeout
    + - returns - waits for timeout to happen should return error page 
    + 
    +4. Timeout s2
    + - servlet does a startAsync()
    + - servlet does a setAsyncTimeout
    + - servlet does a addAsyncListener
    + - returns - waits for timeout to happen and listener invoked 
    + 
    +5. Dispatch to asyncSupported=false servlet
    + - servlet1 does a startAsync()
    + - servlet1 dispatches to dispatch(/servlet2)
    + - the container calls complete() after servlet2 is complete
    + - TODO
    + 
    +6. Chained dispatch
    + - servlet1 does a startAsync
    + - servlet1 does a dispatch to servlet2 (asyncsupported=true)
    + - servlet2 does a dispatch to servlet3 (asyncsupported=true)
    + - servlet3 does a dispatch to servlet4 (asyncsupported=false) 
    + 
    + 
    +7. Stock ticker
    +   "> StockTicker 
    +
    \ No newline at end of file diff --git a/webapps/examples/jsp/cal/cal1.jsp b/webapps/examples/jsp/cal/cal1.jsp new file mode 100644 index 000000000000..42d41976ec56 --- /dev/null +++ b/webapps/examples/jsp/cal/cal1.jsp @@ -0,0 +1,93 @@ + + + + Calendar: A JSP APPLICATION + + + + + +<%@ page language="java" import="cal.*" %> + + +<% + table.processRequest(request); + if (table.getProcessError() == false) { +%> + + +
    + + + + +
    prev + Calendar:<%= table.getDate() %> next +
    + + + + + + + + +<% + for(int i=0; i + + + + +<% + } +%> + +
    Time Appointment
    + > + <%= entr.getHour() %> + > + <% out.print(util.HTMLFilter.filter(entr.getDescription())); %> +
    +
    + + + + + + +
    <% out.print(util.HTMLFilter.filter(table.getName())); %> : + <% out.print(util.HTMLFilter.filter(table.getEmail())); %>
    +
    + +<% + } else { +%> + + You must enter your name and email address correctly. + +<% + } +%> + + + + + + diff --git a/webapps/examples/jsp/cal/cal2.jsp b/webapps/examples/jsp/cal/cal2.jsp new file mode 100644 index 000000000000..b2295de89b87 --- /dev/null +++ b/webapps/examples/jsp/cal/cal2.jsp @@ -0,0 +1,45 @@ + + + + + Calendar: A JSP APPLICATION + + + + + + +<% + String time = request.getParameter ("time"); +%> + + Please add the following event: +

    Date <%= table.getDate() %> +
    Time <%= util.HTMLFilter.filter(time) %>

    +
    +
    +
    +
    +
    +

    Description of the event

    +
    +
    + + + + diff --git a/webapps/examples/jsp/cal/calendar.html b/webapps/examples/jsp/cal/calendar.html new file mode 100644 index 000000000000..a0a3ea184134 --- /dev/null +++ b/webapps/examples/jsp/cal/calendar.html @@ -0,0 +1,43 @@ + + + + +Untitled Document + + + + +

    + +

    Source Code for Calendar Example.
    +

    cal1.jsp +

    +

    cal2.jsp +

    + +
    +

    Beans. +

    TableBean +

    +

    Entries +

    +

    Entry +

    + + + diff --git a/webapps/examples/jsp/cal/login.html b/webapps/examples/jsp/cal/login.html new file mode 100644 index 000000000000..5ed271bc6da2 --- /dev/null +++ b/webapps/examples/jsp/cal/login.html @@ -0,0 +1,47 @@ + + + + + Login page for the calendar. + + + +
    + + Please Enter the following information: + +
    +
    + + Name + +
    + Email + +
    + + +
    +
    + Note: This application does not implement the complete +functionality of a typical calendar application. It demostartes a way JSP can be +used with html tables and forms. + +
    + + diff --git a/webapps/examples/jsp/chat/index.jsp b/webapps/examples/jsp/chat/index.jsp new file mode 100644 index 000000000000..e0b37298a821 --- /dev/null +++ b/webapps/examples/jsp/chat/index.jsp @@ -0,0 +1,32 @@ +<%@page contentType="text/html; charset=UTF-8" %> +<% if (session.getAttribute("nickname") == null) { + response.sendRedirect("login.jsp"); + return; +} +%> + + + + + JSP Chat + + + + + + diff --git a/webapps/examples/jsp/chat/login.jsp b/webapps/examples/jsp/chat/login.jsp new file mode 100644 index 000000000000..551ca3426920 --- /dev/null +++ b/webapps/examples/jsp/chat/login.jsp @@ -0,0 +1,33 @@ + +<%@page contentType="text/html; charset=UTF-8" %> + + + + JSP Chat + + + + +
    + +Nickname: + +
    + + + diff --git a/webapps/examples/jsp/chat/post.jsp b/webapps/examples/jsp/chat/post.jsp new file mode 100644 index 000000000000..69dde51672f0 --- /dev/null +++ b/webapps/examples/jsp/chat/post.jsp @@ -0,0 +1,55 @@ + +<%@page contentType="text/html; charset=UTF-8" %> + + + + JSP Chat + + + + +
    + +Message: + +
    + +
    +<% + String serverName = request.getServerName(); + if ("localhost".equals(serverName)) { + serverName = "127.0.0.1"; + } else if ("127.0.0.1".equals(serverName)) { + serverName = "localhost"; + } + + String chatUrl = request.getScheme() + "://" + serverName + ":" + + request.getServerPort() + request.getContextPath() + + request.getServletPath(); + + // strip "post.jsp" from the address + chatUrl = chatUrl.substring(0, chatUrl.lastIndexOf("/") + 1); +%> +Click to open a new chat window +Note: To avoid hitting the limit on the count of simultaneous +connections to the same host, imposed by the +HTTP specification, +the second chat window should be opened using a different URL, e.g. with +an IP address instead of the host name. + + diff --git a/webapps/examples/jsp/checkbox/CheckTest.html b/webapps/examples/jsp/checkbox/CheckTest.html new file mode 100644 index 000000000000..284d9ec3bce2 --- /dev/null +++ b/webapps/examples/jsp/checkbox/CheckTest.html @@ -0,0 +1,56 @@ + + + + + +checkbox.CheckTest Bean Properties + + +

    +checkbox.CheckTest Bean Properties +

    +
    +
    +
    public class CheckTest
    extends Object
    + +

    +


    + +

    + + + + + + + + + +
    +Properties Summary
    + +String +CheckTest:fruit +
    +
    + +Multi +
    +


    + + diff --git a/webapps/examples/jsp/checkbox/check.html b/webapps/examples/jsp/checkbox/check.html new file mode 100644 index 000000000000..b6d6b3bc1b3c --- /dev/null +++ b/webapps/examples/jsp/checkbox/check.html @@ -0,0 +1,38 @@ + + + + + + +
    +
    + +Check all Favorite fruits:
    + + Apples
    + Grapes
    + Oranges
    + Melons
    + + +
    + +
    +
    + + diff --git a/webapps/examples/jsp/checkbox/checkresult.jsp b/webapps/examples/jsp/checkbox/checkresult.jsp new file mode 100644 index 000000000000..4b7fa96d7de6 --- /dev/null +++ b/webapps/examples/jsp/checkbox/checkresult.jsp @@ -0,0 +1,64 @@ + + + + + +<%! String[] fruits; %> + + + +
    +The checked fruits (got using request) are:
    +<% + fruits = request.getParameterValues("fruit"); +%> +
      +<% + if (fruits != null) { + for (int i = 0; i < fruits.length; i++) { +%> +
    • +<% + out.println (util.HTMLFilter.filter(fruits[i])); + } + } else out.println ("none selected"); +%> +
    +
    +
    + +The checked fruits (got using beans) are
    + +<% + fruits = foo.getFruit(); +%> +
      +<% + if (!fruits[0].equals("1")) { + for (int i = 0; i < fruits.length; i++) { +%> +
    • +<% + out.println (util.HTMLFilter.filter(fruits[i])); + } + } else out.println ("none selected"); +%> +
    +
    + + diff --git a/webapps/examples/jsp/checkbox/cresult.html b/webapps/examples/jsp/checkbox/cresult.html new file mode 100644 index 000000000000..b6a28d6645fc --- /dev/null +++ b/webapps/examples/jsp/checkbox/cresult.html @@ -0,0 +1,34 @@ + + + + +Untitled Document + + + + +

    + +

    Source Code for Checkbox Example +

    + +

    Property Sheet for CheckTest +

    + + + diff --git a/webapps/examples/jsp/colors/ColorGameBean.html b/webapps/examples/jsp/colors/ColorGameBean.html new file mode 100644 index 000000000000..172bc6646b26 --- /dev/null +++ b/webapps/examples/jsp/colors/ColorGameBean.html @@ -0,0 +1,116 @@ + + + + + +colors.ColorGameBean Bean Properties + + +

    +colors.ColorGameBean Bean Properties +

    +
    +
    +
    public class ColorGameBean
    extends Object
    + +

    +


    + +

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    +Properties Summary
    + +String +ColorGameBean:color2 +
    +
    + +Single +
    + +String +ColorGameBean:color1 +
    +
    + +Single +
    + +int +ColorGameBean:attempts +
    +
    + +Single +
    + +boolean +ColorGameBean:hint +
    +
    + +Single +
    + +boolean +ColorGameBean:success +
    +
    + +Single +
    + +boolean +ColorGameBean:hintTaken +
    +
    + +Single +
    +


    + + diff --git a/webapps/examples/jsp/colors/clr.html b/webapps/examples/jsp/colors/clr.html new file mode 100644 index 000000000000..e411f597d22d --- /dev/null +++ b/webapps/examples/jsp/colors/clr.html @@ -0,0 +1,34 @@ + + + + +Untitled Document + + + + +

    + +

    Source Code for Color Example +

    + +

    Property Sheet for ColorGameBean +

    + + + diff --git a/webapps/examples/jsp/colors/colors.html b/webapps/examples/jsp/colors/colors.html new file mode 100644 index 000000000000..bf9268d6bbc5 --- /dev/null +++ b/webapps/examples/jsp/colors/colors.html @@ -0,0 +1,47 @@ + + + + + + +
    +This web page is an example using JSP and BEANs. +

    +Guess my favorite two colors + +

    If you fail to guess both of them - you get yellow on red. + +

    If you guess one of them right, either your foreground or + your background will change to the color that was guessed right. + +

    Guess them both right and your browser foreground/background + will change to my two favorite colors to display this page. + +


    +
    +Color #1: +
    +Color #2: +

    + + +

    + +
    + + diff --git a/webapps/examples/jsp/colors/colrs.jsp b/webapps/examples/jsp/colors/colrs.jsp new file mode 100644 index 000000000000..f7661968adab --- /dev/null +++ b/webapps/examples/jsp/colors/colrs.jsp @@ -0,0 +1,70 @@ + + + + + + +<% + cb.processRequest(); +%> + +> +> +

    + +<% if (cb.getHint()==true) { %> + +

    Hint #1: Vampires prey at night! +

    Hint #2: Nancy without the n. + +<% } %> + +<% if (cb.getSuccess()==true) { %> + +

    CONGRATULATIONS!! + <% if (cb.getHintTaken()==true) { %> + +

    ( although I know you cheated and peeked into the hints) + + <% } %> + +<% } %> + +

    Total attempts so far: <%= cb.getAttempts() %> +

    + +

    + +

    + +Color #1: + +
    + +Color #2: + +

    + + + + +

    + +
    + + diff --git a/webapps/examples/jsp/dates/date.html b/webapps/examples/jsp/dates/date.html new file mode 100644 index 000000000000..683ab4d2a06a --- /dev/null +++ b/webapps/examples/jsp/dates/date.html @@ -0,0 +1,31 @@ + + + + +Untitled Document + + + + +

    + +

    Source Code for Date Example +

    + + + diff --git a/webapps/examples/jsp/dates/date.jsp b/webapps/examples/jsp/dates/date.jsp new file mode 100644 index 000000000000..84c2724e1e0d --- /dev/null +++ b/webapps/examples/jsp/dates/date.jsp @@ -0,0 +1,41 @@ + + + +<%@ page session="false"%> + + + + + +
      +
    • Day of month: is +
    • Year: is +
    • Month: is +
    • Time: is +
    • Date: is +
    • Day: is +
    • Day Of Year: is +
    • Week Of Year: is +
    • era: is +
    • DST Offset: is +
    • Zone Offset: is +
    +
    + + + diff --git a/webapps/examples/jsp/error/er.html b/webapps/examples/jsp/error/er.html new file mode 100644 index 000000000000..af78159dda60 --- /dev/null +++ b/webapps/examples/jsp/error/er.html @@ -0,0 +1,31 @@ + + + + +Untitled Document + + + + +

    + +

    Source Code for Error Example +

    + + + diff --git a/webapps/examples/jsp/error/err.jsp b/webapps/examples/jsp/error/err.jsp new file mode 100644 index 000000000000..dc5d98b0ebad --- /dev/null +++ b/webapps/examples/jsp/error/err.jsp @@ -0,0 +1,44 @@ + + + + + <%@ page errorPage="errorpge.jsp" %> + + <% + String name = null; + + if (request.getParameter("name") == null) { + %> + <%@ include file="error.html" %> + <% + } else { + foo.setName(request.getParameter("name")); + if (foo.getName().equalsIgnoreCase("integra")) + name = "acura"; + if (name.equalsIgnoreCase("acura")) { + %> + +

    Yes!!! Acura is my favorite car. + + <% + } + } + %> + + + diff --git a/webapps/examples/jsp/error/error.html b/webapps/examples/jsp/error/error.html new file mode 100644 index 000000000000..b1b029c90a8a --- /dev/null +++ b/webapps/examples/jsp/error/error.html @@ -0,0 +1,37 @@ + + + + + +

    This example uses errorpage directive

    +
    +

    Select my favourite car.

    +
    + + +
    +
    + + + diff --git a/webapps/examples/jsp/error/errorpge.jsp b/webapps/examples/jsp/error/errorpge.jsp new file mode 100644 index 000000000000..e52ccfc72979 --- /dev/null +++ b/webapps/examples/jsp/error/errorpge.jsp @@ -0,0 +1,25 @@ + + + + + + <%@ page isErrorPage="true" %> +

    The exception <%= exception.getMessage() %> tells me you + made a wrong choice. + + diff --git a/webapps/examples/jsp/forward/forward.jsp b/webapps/examples/jsp/forward/forward.jsp new file mode 100644 index 000000000000..b395aa78ab89 --- /dev/null +++ b/webapps/examples/jsp/forward/forward.jsp @@ -0,0 +1,34 @@ + + + +<% + double freeMem = Runtime.getRuntime().freeMemory(); + double totlMem = Runtime.getRuntime().totalMemory(); + double percent = freeMem/totlMem; + if (percent < 0.5) { +%> + + + +<% } else { %> + + + +<% } %> + + diff --git a/webapps/examples/jsp/forward/fwd.html b/webapps/examples/jsp/forward/fwd.html new file mode 100644 index 000000000000..b3b0219fc903 --- /dev/null +++ b/webapps/examples/jsp/forward/fwd.html @@ -0,0 +1,30 @@ + + + +Untitled Document + + + + +

    + +

    Source Code for Forward Example +

    + + + diff --git a/webapps/examples/jsp/forward/one.jsp b/webapps/examples/jsp/forward/one.jsp new file mode 100644 index 000000000000..39441df24e22 --- /dev/null +++ b/webapps/examples/jsp/forward/one.jsp @@ -0,0 +1,23 @@ + + + + + + +VM Memory usage < 50%. + \ No newline at end of file diff --git a/webapps/examples/jsp/forward/two.html b/webapps/examples/jsp/forward/two.html new file mode 100644 index 000000000000..31c4d96bd5f1 --- /dev/null +++ b/webapps/examples/jsp/forward/two.html @@ -0,0 +1,23 @@ + + + + + + +VM Memory usage > 50%. + \ No newline at end of file diff --git a/webapps/examples/jsp/images/code.gif b/webapps/examples/jsp/images/code.gif new file mode 100644 index 000000000000..93af2cd130aa Binary files /dev/null and b/webapps/examples/jsp/images/code.gif differ diff --git a/webapps/examples/jsp/images/execute.gif b/webapps/examples/jsp/images/execute.gif new file mode 100644 index 000000000000..f64d70fd233d Binary files /dev/null and b/webapps/examples/jsp/images/execute.gif differ diff --git a/webapps/examples/jsp/images/read.gif b/webapps/examples/jsp/images/read.gif new file mode 100644 index 000000000000..66cb4e9232ed Binary files /dev/null and b/webapps/examples/jsp/images/read.gif differ diff --git a/webapps/examples/jsp/images/return.gif b/webapps/examples/jsp/images/return.gif new file mode 100644 index 000000000000..af4f68f4a3a1 Binary files /dev/null and b/webapps/examples/jsp/images/return.gif differ diff --git a/webapps/examples/jsp/include/foo.html b/webapps/examples/jsp/include/foo.html new file mode 100644 index 000000000000..168c8c852f19 --- /dev/null +++ b/webapps/examples/jsp/include/foo.html @@ -0,0 +1,17 @@ + +To get the current time in ms diff --git a/webapps/examples/jsp/include/foo.jsp b/webapps/examples/jsp/include/foo.jsp new file mode 100644 index 000000000000..b1e3e8377019 --- /dev/null +++ b/webapps/examples/jsp/include/foo.jsp @@ -0,0 +1,21 @@ + + + + + +<%= System.currentTimeMillis() %> diff --git a/webapps/examples/jsp/include/inc.html b/webapps/examples/jsp/include/inc.html new file mode 100644 index 000000000000..fedaed0918e4 --- /dev/null +++ b/webapps/examples/jsp/include/inc.html @@ -0,0 +1,30 @@ + + + +Untitled Document + + + + +

    + +

    Source Code for Include Example +

    + + + diff --git a/webapps/examples/jsp/include/include.jsp b/webapps/examples/jsp/include/include.jsp new file mode 100644 index 000000000000..706ff7e40d1d --- /dev/null +++ b/webapps/examples/jsp/include/include.jsp @@ -0,0 +1,35 @@ + + + + + + + +<%@ page buffer="5kb" autoFlush="false" %> + +

    In place evaluation of another JSP which gives you the current time: + +<%@ include file="foo.jsp" %> + +

    by including the output of another JSP: + + + +:-) + + diff --git a/webapps/examples/jsp/index.html b/webapps/examples/jsp/index.html new file mode 100644 index 000000000000..44438900e32d --- /dev/null +++ b/webapps/examples/jsp/index.html @@ -0,0 +1,378 @@ + + + + + + + + JSP Examples + + +JSP +Samples +

    This is a collection of samples demonstrating the usage of different +parts of the Java Server Pages (JSP) specification. Both JSP 2.0 and +JSP 1.2 examples are presented below. +

    These examples will only work when these pages are being served by a +servlet engine; of course, we recommend +Tomcat. +They will not work if you are viewing these pages via a +"file://..." URL. +

    To navigate your way through the examples, the following icons will +help: +
      + + + + + + + + + + + + + + + + + + + + + +
    Execute the example
    Look at the source code for the example
    Return to this screen
    + +

    Tip: For session scoped beans to work, the cookies must be enabled. +This can be done using browser options. +
      +
    +JSP 2.0 Examples
    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    Expression Language
    Basic ArithmeticExecuteSource
    Basic ComparisonsExecuteSource
    Implicit ObjectsExecuteSource
    FunctionsExecuteSource
    Composite ExpressionsExecuteSource

    SimpleTag Handlers and JSP Fragments
    Hello World TagExecuteSource
    Repeat TagExecuteSource
    Book ExampleExecuteSource

    Tag Files
    Hello World Tag FileExecuteSource
    Panel Tag FileExecuteSource
    Display Products ExampleExecuteSource

    New JSP XML Syntax (.jspx)
    XHTML Basic ExampleExecuteSource
    SVG (Scalable Vector Graphics)ExecuteSource

    Other JSP 2.0 Features
    <jsp:attribute> and <jsp:body>ExecuteSource
    Shuffle ExampleExecuteSource
    Attributes With Dynamic NamesExecuteSource
    JSP ConfigurationExecuteSource
    + +
    +JSP 1.2 Examples
    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    Numberguess ExecuteSource
    Date ExecuteSource
    SnoopExecuteSource
    ErrorPage ExecuteSource
    Carts ExecuteSource
    Checkbox ExecuteSource
    Color ExecuteSource
    Calendar ExecuteSource
    Include ExecuteSource
    Forward ExecuteSource
    Plugin ExecuteSource
    JSP-Servlet-JSP ExecuteSource
    Custom tag exampleExecuteSource
    XML syntax exampleExecuteSource
    + +
    +Tag Plugins
    + + + + + + + + + + + + + + + + + + + + +
    If  + + Execute + + + Source +
    ForEach  + + Execute + + + Source +
    Choose  + + Execute + + + Source +
    + + + diff --git a/webapps/examples/jsp/jsp2/el/basic-arithmetic.html b/webapps/examples/jsp/jsp2/el/basic-arithmetic.html new file mode 100644 index 000000000000..8a2f0a61dbb0 --- /dev/null +++ b/webapps/examples/jsp/jsp2/el/basic-arithmetic.html @@ -0,0 +1,30 @@ + + + +View Source Code + + + + +

    + +

    Source Code for Basic Arithmetic Example +

    + + + diff --git a/webapps/examples/jsp/jsp2/el/basic-arithmetic.jsp b/webapps/examples/jsp/jsp2/el/basic-arithmetic.jsp new file mode 100644 index 000000000000..1108df03d435 --- /dev/null +++ b/webapps/examples/jsp/jsp2/el/basic-arithmetic.jsp @@ -0,0 +1,88 @@ + + + + JSP 2.0 Expression Language - Basic Arithmetic + + +

    JSP 2.0 Expression Language - Basic Arithmetic

    +
    + This example illustrates basic Expression Language arithmetic. + Addition (+), subtraction (-), multiplication (*), division (/ or div), + and modulus (% or mod) are all supported. Error conditions, like + division by zero, are handled gracefully. +
    +
    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    EL ExpressionResult
    \${1}${1}
    \${1 + 2}${1 + 2}
    \${1.2 + 2.3}${1.2 + 2.3}
    \${1.2E4 + 1.4}${1.2E4 + 1.4}
    \${-4 - 2}${-4 - 2}
    \${21 * 2}${21 * 2}
    \${3/4}${3/4}
    \${3 div 4}${3 div 4}
    \${3/0}${3/0}
    \${10%4}${10%4}
    \${10 mod 4}${10 mod 4}
    \${(1==2) ? 3 : 4}${(1==2) ? 3 : 4}
    +
    +
    + + diff --git a/webapps/examples/jsp/jsp2/el/basic-comparisons.html b/webapps/examples/jsp/jsp2/el/basic-comparisons.html new file mode 100644 index 000000000000..60fb40a3bbf9 --- /dev/null +++ b/webapps/examples/jsp/jsp2/el/basic-comparisons.html @@ -0,0 +1,30 @@ + + + +View Source Code + + + + +

    + +

    Source Code for Basic Comparisons Example +

    + + + diff --git a/webapps/examples/jsp/jsp2/el/basic-comparisons.jsp b/webapps/examples/jsp/jsp2/el/basic-comparisons.jsp new file mode 100644 index 000000000000..77679d6ebace --- /dev/null +++ b/webapps/examples/jsp/jsp2/el/basic-comparisons.jsp @@ -0,0 +1,116 @@ + + + + JSP 2.0 Expression Language - Basic Comparisons + + +

    JSP 2.0 Expression Language - Basic Comparisons

    +
    + This example illustrates basic Expression Language comparisons. + The following comparison operators are supported: +
      +
    • Less-than (< or lt)
    • +
    • Greater-than (> or gt)
    • +
    • Less-than-or-equal (<= or le)
    • +
    • Greater-than-or-equal (>= or ge)
    • +
    • Equal (== or eq)
    • +
    • Not Equal (!= or ne)
    • +
    +
    + Numeric + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    EL ExpressionResult
    \${1 < 2}${1 < 2}
    \${1 lt 2}${1 lt 2}
    \${1 > (4/2)}${1 > (4/2)}
    \${1 gt (4/2)}${1 gt (4/2)}
    \${4.0 >= 3}${4.0 >= 3}
    \${4.0 ge 3}${4.0 ge 3}
    \${4 <= 3}${4 <= 3}
    \${4 le 3}${4 le 3}
    \${100.0 == 100}${100.0 == 100}
    \${100.0 eq 100}${100.0 eq 100}
    \${(10*10) != 100}${(10*10) != 100}
    \${(10*10) ne 100}${(10*10) ne 100}
    +
    +
    + Alphabetic + + + + + + + + + + + + + + + + + + +
    EL ExpressionResult
    \${'a' < 'b'}${'a' < 'b'}
    \${'hip' > 'hit'}${'hip' > 'hit'}
    \${'4' > 3}${'4' > 3}
    +
    +
    + + diff --git a/webapps/examples/jsp/jsp2/el/composite.html b/webapps/examples/jsp/jsp2/el/composite.html new file mode 100644 index 000000000000..5900008e2dac --- /dev/null +++ b/webapps/examples/jsp/jsp2/el/composite.html @@ -0,0 +1,31 @@ + + + +View Source Code + + + + +

    + +

    Source Code for composite.jsp

    +

    Source Code for ValuesTag.java

    +

    Source Code for ValuesBean.java

    + + + diff --git a/webapps/examples/jsp/jsp2/el/composite.jsp b/webapps/examples/jsp/jsp2/el/composite.jsp new file mode 100644 index 000000000000..cfe9fd1a03e2 --- /dev/null +++ b/webapps/examples/jsp/jsp2/el/composite.jsp @@ -0,0 +1,110 @@ + +<%@ taglib prefix="my" uri="http://tomcat.apache.org/example-taglib" %> + + + + JSP 2.0 Expression Language - Composite Expressions + + +

    JSP 2.0 Expression Language - Composite Expressions

    +
    + This example illustrates EL composite expressions. Composite expressions + are formed by grouping together multiple EL expressions. Each of them is + evaluated from left to right, coerced to String, all those strings are + concatenated, and the result is coerced to the expected type. + + + +
    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    EL ExpressionTypeResult
    \${'hello'} wo\${'rld'}String${values.stringValue}
    \${'hello'} wo\${'rld'}String
    \${1+2}.\${220}Double${values.doubleValue}
    \${1+2}.\${220}Double
    000\${1}\${7}Long${values.longValue}
    000\${1}\${7}Long
    \${undefinedFoo}hello world\${undefinedBar}String${values.stringValue}
    \${undefinedFoo}hello world\${undefinedBar}String
    \${undefinedFoo}\${undefinedBar}Double${values.doubleValue}
    \${undefinedFoo}\${undefinedBar}Double
    \${undefinedFoo}\${undefinedBar}Long${values.longValue}
    \${undefinedFoo}\${undefinedBar}Long
    +
    +
    + + + diff --git a/webapps/examples/jsp/jsp2/el/functions.html b/webapps/examples/jsp/jsp2/el/functions.html new file mode 100644 index 000000000000..726dda3661cc --- /dev/null +++ b/webapps/examples/jsp/jsp2/el/functions.html @@ -0,0 +1,32 @@ + + + +View Source Code + + + + +

    + +

    Source Code for functions.jsp +

    +

    Source Code for Functions.java +

    + + + diff --git a/webapps/examples/jsp/jsp2/el/functions.jsp b/webapps/examples/jsp/jsp2/el/functions.jsp new file mode 100644 index 000000000000..557f934847b6 --- /dev/null +++ b/webapps/examples/jsp/jsp2/el/functions.jsp @@ -0,0 +1,66 @@ + +<%@ taglib prefix="fn" uri="http://java.sun.com/jsp/jstl/functions" %> +<%@ taglib prefix="my" uri="http://tomcat.apache.org/jsp2-example-taglib"%> + + + + JSP 2.0 Expression Language - Functions + + +

    JSP 2.0 Expression Language - Functions

    +
    + An upgrade from the JSTL expression language, the JSP 2.0 EL also + allows for simple function invocation. Functions are defined + by tag libraries and are implemented by a Java programmer as + static methods. + +
    + Change Parameter +
    + foo = + +
    +
    + + + + + + + + + + + + + + + + + + + + + + +
    EL ExpressionResult
    \${param["foo"]}${fn:escapeXml(param["foo"])} 
    \${my:reverse(param["foo"])}${my:reverse(fn:escapeXml(param["foo"]))} 
    \${my:reverse(my:reverse(param["foo"]))}${my:reverse(my:reverse(fn:escapeXml(param["foo"])))} 
    \${my:countVowels(param["foo"])}${my:countVowels(fn:escapeXml(param["foo"]))} 
    +
    +
    + + + diff --git a/webapps/examples/jsp/jsp2/el/implicit-objects.html b/webapps/examples/jsp/jsp2/el/implicit-objects.html new file mode 100644 index 000000000000..15268db59abc --- /dev/null +++ b/webapps/examples/jsp/jsp2/el/implicit-objects.html @@ -0,0 +1,31 @@ + + + +View Source Code + + + + +

    +

    + +

    Source Code for Implicit Objects Example +

    + + + diff --git a/webapps/examples/jsp/jsp2/el/implicit-objects.jsp b/webapps/examples/jsp/jsp2/el/implicit-objects.jsp new file mode 100644 index 000000000000..c1c1fc3b5013 --- /dev/null +++ b/webapps/examples/jsp/jsp2/el/implicit-objects.jsp @@ -0,0 +1,89 @@ + +<%@ taglib prefix="fn" uri="http://java.sun.com/jsp/jstl/functions" %> + + + + JSP 2.0 Expression Language - Implicit Objects + + +

    JSP 2.0 Expression Language - Implicit Objects

    +
    + This example illustrates some of the implicit objects available + in the Expression Lanaguage. The following implicit objects are + available (not all illustrated here): +
      +
    • pageContext - the PageContext object
    • +
    • pageScope - a Map that maps page-scoped attribute names to + their values
    • +
    • requestScope - a Map that maps request-scoped attribute names + to their values
    • +
    • sessionScope - a Map that maps session-scoped attribute names + to their values
    • +
    • applicationScope - a Map that maps application-scoped attribute + names to their values
    • +
    • param - a Map that maps parameter names to a single String + parameter value
    • +
    • paramValues - a Map that maps parameter names to a String[] of + all values for that parameter
    • +
    • header - a Map that maps header names to a single String + header value
    • +
    • headerValues - a Map that maps header names to a String[] of + all values for that header
    • +
    • initParam - a Map that maps context initialization parameter + names to their String parameter value
    • +
    • cookie - a Map that maps cookie names to a single Cookie object.
    • +
    + +
    + Change Parameter +
    + foo = + +
    +
    + + + + + + + + + + + + + + + + + + + + + + + + + + +
    EL ExpressionResult
    \${param.foo}${fn:escapeXml(param["foo"])} 
    \${param["foo"]}${fn:escapeXml(param["foo"])} 
    \${header["host"]}${fn:escapeXml(header["host"])} 
    \${header["accept"]}${fn:escapeXml(header["accept"])} 
    \${header["user-agent"]}${fn:escapeXml(header["user-agent"])} 
    +
    +
    + + diff --git a/webapps/examples/jsp/jsp2/jspattribute/jspattribute.html b/webapps/examples/jsp/jsp2/jspattribute/jspattribute.html new file mode 100644 index 000000000000..df1b6e68c6dd --- /dev/null +++ b/webapps/examples/jsp/jsp2/jspattribute/jspattribute.html @@ -0,0 +1,37 @@ + + + +View Source Code + + + + +

    +

    + +

    Source Code for jspattribute.jsp +

    + +

    Source Code for HelloWorldSimpleTag.java +

    + +

    Source Code for FooBean.java +

    + + + diff --git a/webapps/examples/jsp/jsp2/jspattribute/jspattribute.jsp b/webapps/examples/jsp/jsp2/jspattribute/jspattribute.jsp new file mode 100644 index 000000000000..1d28584b9d22 --- /dev/null +++ b/webapps/examples/jsp/jsp2/jspattribute/jspattribute.jsp @@ -0,0 +1,46 @@ + +<%@ taglib prefix="my" uri="http://tomcat.apache.org/jsp2-example-taglib"%> + + + + JSP 2.0 Examples - jsp:attribute and jsp:body + + +

    JSP 2.0 Examples - jsp:attribute and jsp:body

    +
    +

    The new <jsp:attribute> and <jsp:body> + standard actions can be used to specify the value of any standard + action or custom action attribute.

    +

    This example uses the <jsp:attribute> + standard action to use the output of a custom action invocation + (one that simply outputs "Hello, World!") to set the value of a + bean property. This would normally require an intermediary + step, such as using JSTL's <c:set> action.

    +
    + + Bean created! Setting foo.bar...
    + + + + + +
    +
    + Result: ${foo.bar} + + diff --git a/webapps/examples/jsp/jsp2/jspattribute/shuffle.html b/webapps/examples/jsp/jsp2/jspattribute/shuffle.html new file mode 100644 index 000000000000..5711860afe55 --- /dev/null +++ b/webapps/examples/jsp/jsp2/jspattribute/shuffle.html @@ -0,0 +1,37 @@ + + + +View Source Code + + + + +

    +

    + +

    Source Code for shuffle.jsp +

    + +

    Source Code for ShuffleSimpleTag.java +

    + +

    Source Code for TileSimpleTag.java +

    + + + diff --git a/webapps/examples/jsp/jsp2/jspattribute/shuffle.jsp b/webapps/examples/jsp/jsp2/jspattribute/shuffle.jsp new file mode 100644 index 000000000000..38864a31766c --- /dev/null +++ b/webapps/examples/jsp/jsp2/jspattribute/shuffle.jsp @@ -0,0 +1,90 @@ + +<%@ taglib prefix="my" uri="http://tomcat.apache.org/jsp2-example-taglib"%> + + + + JSP 2.0 Examples - Shuffle Example + + +

    JSP 2.0 Examples - Shuffle Example

    +
    +

    Try reloading the page a few times. Both the rows and the columns + are shuffled and appear different each time.

    +

    Here's how the code works. The SimpleTag handler called + <my:shuffle> accepts three attributes. Each attribute is a + JSP Fragment, meaning it is a fragment of JSP code that can be + dynamically executed by the shuffle tag handler on demand. The + shuffle tag handler executes the three fragments in a random order. + To shuffle both the rows and the columns, the shuffle tag is used + with itself as a parameter.

    +
    +
    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    +
    +
    + + diff --git a/webapps/examples/jsp/jsp2/jspx/basic.html b/webapps/examples/jsp/jsp2/jspx/basic.html new file mode 100644 index 000000000000..51552d32064e --- /dev/null +++ b/webapps/examples/jsp/jsp2/jspx/basic.html @@ -0,0 +1,31 @@ + + + +View Source Code + + + + +

    + +

    Source Code for XHTML Basic Example +

    + + + diff --git a/webapps/examples/jsp/jsp2/jspx/basic.jspx b/webapps/examples/jsp/jsp2/jspx/basic.jspx new file mode 100644 index 000000000000..2ff5cf9d9c64 --- /dev/null +++ b/webapps/examples/jsp/jsp2/jspx/basic.jspx @@ -0,0 +1,46 @@ + + + + + JSPX - XHTML Basic Example + + +

    JSPX - XHTML Basic Example

    +
    + This example illustrates how to use JSPX to produce an XHTML basic + document suitable for use with mobile phones, televisions, + PDAs, vending machines, pagers, car navigation systems, + mobile game machines, digital book readers, smart watches, etc. +

    + JSPX lets you create dynamic documents in a pure XML syntax compatible + with existing XML tools. The XML syntax in JSP 1.2 was awkward and + required &lt;jsp:root&gt; to be the root element of the document. + This is no longer the case in JSP 2.0. +

    + This particular example uses a tag file to produce the DOCTYPE and + namespace declarations to make the output of this page a valid XHTML + Basic document. +

    + Just to prove this is live, here's some dynamic content: + + + + diff --git a/webapps/examples/jsp/jsp2/jspx/svgexample.html b/webapps/examples/jsp/jsp2/jspx/svgexample.html new file mode 100644 index 000000000000..f6718fc89240 --- /dev/null +++ b/webapps/examples/jsp/jsp2/jspx/svgexample.html @@ -0,0 +1,52 @@ + + + + JSP 2.0 SVG Example + + +

    JSP 2.0 SVG Example

    +
    + This example uses JSP 2.0's new, simplified JSPX syntax to render a + Scalable Vector Graphics (SVG) document. When you view the source, + notice the lack of a <jsp:root> element! The text to be rendered + can be modified by changing the value of the name parameter. +

    + SVG has many potential uses, such as searchable images, or images + customized with the name of your site's visitor (e.g. a "Susan's Store" + tab image). JSPX is a natural fit for generating dynamic XML content + such as SVG. +

    + To execute this example, follow these steps: +

      +
    1. Download Batik, + or any other SVG viewer.
    2. +
    3. Copy the following URL: + + http://localhost:8080/examples/jsp/jsp2/jspx/textRotate.jspx?name=JSPX +
    4. +
    5. Paste the URL into Batik's Location field and press Enter
    6. +
    7. Customize by changing the name=JSPX parameter
    8. +
    +
    + The following is a screenshot of the resulting image, for those that + don't have an SVG viewer: +
    + +
    + + diff --git a/webapps/examples/jsp/jsp2/jspx/textRotate.html b/webapps/examples/jsp/jsp2/jspx/textRotate.html new file mode 100644 index 000000000000..97f9cddb6e02 --- /dev/null +++ b/webapps/examples/jsp/jsp2/jspx/textRotate.html @@ -0,0 +1,32 @@ + + + +View Source Code + + + + +

    + +

    Source Code for SVG (Scalable Vector Graphics) +Example +

    + + + diff --git a/webapps/examples/jsp/jsp2/jspx/textRotate.jpg b/webapps/examples/jsp/jsp2/jspx/textRotate.jpg new file mode 100644 index 000000000000..9e987367bc83 Binary files /dev/null and b/webapps/examples/jsp/jsp2/jspx/textRotate.jpg differ diff --git a/webapps/examples/jsp/jsp2/jspx/textRotate.jspx b/webapps/examples/jsp/jsp2/jspx/textRotate.jspx new file mode 100644 index 000000000000..320ca1f7d8a3 --- /dev/null +++ b/webapps/examples/jsp/jsp2/jspx/textRotate.jspx @@ -0,0 +1,52 @@ + + + + + JSP 2.0 JSPX + + + + + JSP 2.0 XML Syntax (.jspx) Demo + + Try changing the name parameter! + + + + <g opacity="0.95" transform="scale(1.05) rotate(15)"> + + ${name} + + + </g> + + ${name} + + + diff --git a/webapps/examples/jsp/jsp2/misc/coda.jspf b/webapps/examples/jsp/jsp2/misc/coda.jspf new file mode 100644 index 000000000000..d767de506b8d --- /dev/null +++ b/webapps/examples/jsp/jsp2/misc/coda.jspf @@ -0,0 +1,21 @@ + +
    +
    +This banner included with <include-coda> +
    +
    diff --git a/webapps/examples/jsp/jsp2/misc/config.html b/webapps/examples/jsp/jsp2/misc/config.html new file mode 100644 index 000000000000..707d68faf1c7 --- /dev/null +++ b/webapps/examples/jsp/jsp2/misc/config.html @@ -0,0 +1,35 @@ + + + +View Source Code + + + + +

    +

    + +

    Source Code for config.jsp +

    +

    Source Code for prelude.jspf +

    +

    Source Code for coda.jspf +

    + + + diff --git a/webapps/examples/jsp/jsp2/misc/config.jsp b/webapps/examples/jsp/jsp2/misc/config.jsp new file mode 100644 index 000000000000..68e374d0ba1c --- /dev/null +++ b/webapps/examples/jsp/jsp2/misc/config.jsp @@ -0,0 +1,32 @@ + +<%@ taglib prefix="my" uri="http://tomcat.apache.org/jsp2-example-taglib"%> +

    JSP 2.0 Examples - JSP Configuration

    +
    +

    Using a <jsp-property-group> element in the web.xml + deployment descriptor, this JSP page has been configured in the + following ways:

    +
      +
    • Uses <include-prelude> to include the top banner.
    • +
    • Uses <include-coda> to include the bottom banner.
    • +
    • Uses <scripting-invalid> true to disable + <% scripting %> elements
    • +
    • Uses <el-ignored> true to disable ${EL} elements
    • +
    • Uses <page-encoding> ISO-8859-1 to set the page encoding (though this is the default anyway)
    • +
    + There are various other configuration options that can be used. + diff --git a/webapps/examples/jsp/jsp2/misc/dynamicattrs.html b/webapps/examples/jsp/jsp2/misc/dynamicattrs.html new file mode 100644 index 000000000000..4fa1bf14e6f8 --- /dev/null +++ b/webapps/examples/jsp/jsp2/misc/dynamicattrs.html @@ -0,0 +1,33 @@ + + + +View Source Code + + + + +

    +

    + +

    Source Code for dynamicattrs.jsp +

    +

    Source Code for EchoAttributesTag.java +

    + + + diff --git a/webapps/examples/jsp/jsp2/misc/dynamicattrs.jsp b/webapps/examples/jsp/jsp2/misc/dynamicattrs.jsp new file mode 100644 index 000000000000..fff5d2968858 --- /dev/null +++ b/webapps/examples/jsp/jsp2/misc/dynamicattrs.jsp @@ -0,0 +1,44 @@ + +<%@ taglib prefix="my" uri="http://tomcat.apache.org/jsp2-example-taglib"%> + + + JSP 2.0 Examples - Dynamic Attributes + + +

    JSP 2.0 Examples - Dynamic Attributes

    +
    +

    This JSP page invokes a custom tag that accepts a dynamic set + of attributes. The tag echoes the name and value of all attributes + passed to it.

    +
    +

    Invocation 1 (six attributes)

    +
      + +
    +

    Invocation 2 (zero attributes)

    +
      + +
    +

    Invocation 3 (three attributes)

    +
      + +
    + + diff --git a/webapps/examples/jsp/jsp2/misc/prelude.jspf b/webapps/examples/jsp/jsp2/misc/prelude.jspf new file mode 100644 index 000000000000..05f7c845a108 --- /dev/null +++ b/webapps/examples/jsp/jsp2/misc/prelude.jspf @@ -0,0 +1,21 @@ + +
    +
    +This banner included with <include-prelude> +
    +
    diff --git a/webapps/examples/jsp/jsp2/simpletag/book.html b/webapps/examples/jsp/jsp2/simpletag/book.html new file mode 100644 index 000000000000..2841acf17f8b --- /dev/null +++ b/webapps/examples/jsp/jsp2/simpletag/book.html @@ -0,0 +1,37 @@ + + + +View Source Code + + + + +

    +

    + +

    Source Code for the Book Example JSP +

    +

    Source Code for the FindBook SimpleTag Handler +

    +

    Source Code for BookBean +

    +

    Source Code for the EL Functions +

    + + + diff --git a/webapps/examples/jsp/jsp2/simpletag/book.jsp b/webapps/examples/jsp/jsp2/simpletag/book.jsp new file mode 100644 index 000000000000..117ea4a9f9f7 --- /dev/null +++ b/webapps/examples/jsp/jsp2/simpletag/book.jsp @@ -0,0 +1,55 @@ + +<%@ taglib prefix="my" uri="/WEB-INF/jsp2/jsp2-example-taglib.tld" %> + + + JSP 2.0 Examples - Book SimpleTag Handler + + +

    JSP 2.0 Examples - Book SimpleTag Handler

    +
    +

    Illustrates a semi-realistic use of SimpleTag and the Expression + Language. First, a <my:findBook> tag is invoked to populate + the page context with a BookBean. Then, the books fields are printed + in all caps.

    +
    + Result:
    + + + + + + + + + + + + + + + + + + + + + + +
    FieldValueCapitalized
    Title${book.title}${my:caps(book.title)}
    Author${book.author}${my:caps(book.author)}
    ISBN${book.isbn}${my:caps(book.isbn)}
    + + diff --git a/webapps/examples/jsp/jsp2/simpletag/hello.html b/webapps/examples/jsp/jsp2/simpletag/hello.html new file mode 100644 index 000000000000..20cadf877c32 --- /dev/null +++ b/webapps/examples/jsp/jsp2/simpletag/hello.html @@ -0,0 +1,33 @@ + + + +View Source Code + + + + +

    +

    + +

    Source Code for the Hello World Tag Example JSP +

    +

    Source Code for the Hello World SimpleTag Handler +

    + + + diff --git a/webapps/examples/jsp/jsp2/simpletag/hello.jsp b/webapps/examples/jsp/jsp2/simpletag/hello.jsp new file mode 100644 index 000000000000..09213613475e --- /dev/null +++ b/webapps/examples/jsp/jsp2/simpletag/hello.jsp @@ -0,0 +1,31 @@ + +<%@ taglib prefix="mytag" uri="/WEB-INF/jsp2/jsp2-example-taglib.tld" %> + + + JSP 2.0 Examples - Hello World SimpleTag Handler + + +

    JSP 2.0 Examples - Hello World SimpleTag Handler

    +
    +

    This tag handler simply echos "Hello, World!" It's an example of + a very basic SimpleTag handler with no body.

    +
    + Result: + + + diff --git a/webapps/examples/jsp/jsp2/simpletag/repeat.html b/webapps/examples/jsp/jsp2/simpletag/repeat.html new file mode 100644 index 000000000000..a56bfcd2e700 --- /dev/null +++ b/webapps/examples/jsp/jsp2/simpletag/repeat.html @@ -0,0 +1,33 @@ + + + +View Source Code + + + + +

    +

    + +

    Source Code for the Repeat Tag Example JSP +

    +

    Source Code for the Repeat SimpleTag Handler +

    + + + diff --git a/webapps/examples/jsp/jsp2/simpletag/repeat.jsp b/webapps/examples/jsp/jsp2/simpletag/repeat.jsp new file mode 100644 index 000000000000..dedbf6e943b1 --- /dev/null +++ b/webapps/examples/jsp/jsp2/simpletag/repeat.jsp @@ -0,0 +1,39 @@ + +<%@ taglib prefix="mytag" uri="/WEB-INF/jsp2/jsp2-example-taglib.tld" %> + + + JSP 2.0 Examples - Repeat SimpleTag Handler + + +

    JSP 2.0 Examples - Repeat SimpleTag Handler

    +
    +

    This tag handler accepts a "num" parameter and repeats the body of the + tag "num" times. It's a simple example, but the implementation of + such a tag in JSP 2.0 is substantially simpler than the equivalent + JSP 1.2-style classic tag handler.

    +

    The body of the tag is encapsulated in a "JSP Fragment" and passed + to the tag handler, which then executes it five times, inside a + for loop. The tag handler passes in the current invocation in a + scoped variable called count, which can be accessed using the EL.

    +
    + Result:
    + + Invocation ${count} of 5
    +
    + + diff --git a/webapps/examples/jsp/jsp2/tagfiles/hello.html b/webapps/examples/jsp/jsp2/tagfiles/hello.html new file mode 100644 index 000000000000..f29a37969b2e --- /dev/null +++ b/webapps/examples/jsp/jsp2/tagfiles/hello.html @@ -0,0 +1,33 @@ + + + +View Source Code + + + + +

    +

    + +

    Source Code for hello.jsp +

    +

    Source Code for helloWorld.tag +

    + + + diff --git a/webapps/examples/jsp/jsp2/tagfiles/hello.jsp b/webapps/examples/jsp/jsp2/tagfiles/hello.jsp new file mode 100644 index 000000000000..93a01557223e --- /dev/null +++ b/webapps/examples/jsp/jsp2/tagfiles/hello.jsp @@ -0,0 +1,35 @@ + +<%@ taglib prefix="tags" tagdir="/WEB-INF/tags" %> + + + JSP 2.0 Examples - Hello World Using a Tag File + + +

    JSP 2.0 Examples - Hello World Using a Tag File

    +
    +

    This JSP page invokes a custom tag that simply echos "Hello, World!" + The custom tag is generated from a tag file in the /WEB-INF/tags + directory.

    +

    Notice that we did not need to write a TLD for this tag. We just + created /WEB-INF/tags/helloWorld.tag, imported it using the taglib + directive, and used it!

    +
    + Result: + + + diff --git a/webapps/examples/jsp/jsp2/tagfiles/panel.html b/webapps/examples/jsp/jsp2/tagfiles/panel.html new file mode 100644 index 000000000000..1f03b9cab7b2 --- /dev/null +++ b/webapps/examples/jsp/jsp2/tagfiles/panel.html @@ -0,0 +1,33 @@ + + + +View Source Code + + + + +

    +

    + +

    Source Code for panel.jsp +

    +

    Source Code for panel.tag +

    + + + diff --git a/webapps/examples/jsp/jsp2/tagfiles/panel.jsp b/webapps/examples/jsp/jsp2/tagfiles/panel.jsp new file mode 100644 index 000000000000..17ac07434b91 --- /dev/null +++ b/webapps/examples/jsp/jsp2/tagfiles/panel.jsp @@ -0,0 +1,58 @@ + +<%@ taglib prefix="tags" tagdir="/WEB-INF/tags" %> + + + JSP 2.0 Examples - Panels using Tag Files + + +

    JSP 2.0 Examples - Panels using Tag Files

    +
    +

    This JSP page invokes a custom tag that draws a + panel around the contents of the tag body. Normally, such a tag + implementation would require a Java class with many println() statements, + outputting HTML. Instead, we can use a .tag file as a template, + and we don't need to write a single line of Java or even a TLD!

    +
    + + + + + + +
    + + First panel.
    +
    +
    + + Second panel.
    + Second panel.
    + Second panel.
    + Second panel.
    +
    +
    + + Third panel.
    + + A panel in a panel. + + Third panel.
    +
    +
    + + diff --git a/webapps/examples/jsp/jsp2/tagfiles/products.html b/webapps/examples/jsp/jsp2/tagfiles/products.html new file mode 100644 index 000000000000..72ae49ff2c63 --- /dev/null +++ b/webapps/examples/jsp/jsp2/tagfiles/products.html @@ -0,0 +1,33 @@ + + + +View Source Code + + + + +

    +

    + +

    Source Code for products.jsp +

    +

    Source Code for displayProducts.tag +

    + + + diff --git a/webapps/examples/jsp/jsp2/tagfiles/products.jsp b/webapps/examples/jsp/jsp2/tagfiles/products.jsp new file mode 100644 index 000000000000..0092fa291605 --- /dev/null +++ b/webapps/examples/jsp/jsp2/tagfiles/products.jsp @@ -0,0 +1,54 @@ + +<%@ taglib prefix="tags" tagdir="/WEB-INF/tags" %> + + + JSP 2.0 Examples - Display Products Tag File + + +

    JSP 2.0 Examples - Display Products Tag File

    +
    +

    This JSP page invokes a tag file that displays a listing of + products. The custom tag accepts two fragments that enable + customization of appearance. One for when the product is on sale + and one for normal price.

    +

    The tag is invoked twice, using different styles

    +
    +

    Products

    + + + Item: ${name}
    + Price: ${price} +
    + + Item: ${name}
    + Was: ${origPrice}
    + Now: ${salePrice} +
    +
    +
    +

    Products (Same tag, alternate style)

    + + + ${name} @ ${price} ea. + + + ${name} @ ${salePrice} ea. (was: ${origPrice}) + + + + diff --git a/webapps/examples/jsp/jsptoserv/hello.jsp b/webapps/examples/jsp/jsptoserv/hello.jsp new file mode 100644 index 000000000000..ea810508e7ec --- /dev/null +++ b/webapps/examples/jsp/jsptoserv/hello.jsp @@ -0,0 +1,26 @@ + + + + +

    +I have been invoked by +<% out.print (request.getAttribute("servletName").toString()); %> +Servlet. +

    + + \ No newline at end of file diff --git a/webapps/examples/jsp/jsptoserv/jsptoservlet.jsp b/webapps/examples/jsp/jsptoserv/jsptoservlet.jsp new file mode 100644 index 000000000000..5a7e57f84f49 --- /dev/null +++ b/webapps/examples/jsp/jsptoserv/jsptoservlet.jsp @@ -0,0 +1,23 @@ + + + + + + + + \ No newline at end of file diff --git a/webapps/examples/jsp/jsptoserv/jts.html b/webapps/examples/jsp/jsptoserv/jts.html new file mode 100644 index 000000000000..060e8e7f173d --- /dev/null +++ b/webapps/examples/jsp/jsptoserv/jts.html @@ -0,0 +1,34 @@ + + + + +Untitled Document + + + + +

    + +

    Source Code for JSP calling servlet +

    + +

    Source Code for Servlet calling JSP +

    + + + diff --git a/webapps/examples/jsp/num/numguess.html b/webapps/examples/jsp/num/numguess.html new file mode 100644 index 000000000000..1c5a4844aa17 --- /dev/null +++ b/webapps/examples/jsp/num/numguess.html @@ -0,0 +1,34 @@ + + + +Untitled Document + + + + +

    + +

    Source Code for Numguess Example +

    + + + diff --git a/webapps/examples/jsp/num/numguess.jsp b/webapps/examples/jsp/num/numguess.jsp new file mode 100644 index 000000000000..2461bf7de103 --- /dev/null +++ b/webapps/examples/jsp/num/numguess.jsp @@ -0,0 +1,69 @@ + + +<%@ page import = "num.NumberGuessBean" %> + + + + + +Number Guess + + + +<% if (numguess.getSuccess()) { %> + + Congratulations! You got it. + And after just <%= numguess.getNumGuesses() %> tries.

    + + <% numguess.reset(); %> + + Care to try again? + +<% } else if (numguess.getNumGuesses() == 0) { %> + + Welcome to the Number Guess game.

    + + I'm thinking of a number between 1 and 100.

    + +

    + What's your guess? + +
    + +<% } else { %> + + Good guess, but nope. Try <%= numguess.getHint() %>. + + You have made <%= numguess.getNumGuesses() %> guesses.

    + + I'm thinking of a number between 1 and 100.

    + +

    + What's your guess? + +
    + +<% } %> + +
    + + diff --git a/webapps/examples/jsp/plugin/applet/Clock2.java b/webapps/examples/jsp/plugin/applet/Clock2.java new file mode 100644 index 000000000000..f96cc60c4c4f --- /dev/null +++ b/webapps/examples/jsp/plugin/applet/Clock2.java @@ -0,0 +1,216 @@ +/* +* Licensed to the Apache Software Foundation (ASF) under one or more +* contributor license agreements. See the NOTICE file distributed with +* this work for additional information regarding copyright ownership. +* The ASF licenses this file to You under the Apache License, Version 2.0 +* (the "License"); you may not use this file except in compliance with +* the License. You may obtain a copy of the License at +* +* http://www.apache.org/licenses/LICENSE-2.0 +* +* Unless required by applicable law or agreed to in writing, software +* distributed under the License is distributed on an "AS IS" BASIS, +* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +* See the License for the specific language governing permissions and +* limitations under the License. +*/ + +import java.applet.Applet; +import java.awt.Color; +import java.awt.Font; +import java.awt.Graphics; +import java.text.SimpleDateFormat; +import java.util.Date; +import java.util.Locale; + +/** + * Time! + * + * @author Rachel Gollub + */ + +public class Clock2 extends Applet implements Runnable { + Thread timer; // The thread that displays clock + int lastxs, lastys, lastxm, + lastym, lastxh, lastyh; // Dimensions used to draw hands + SimpleDateFormat formatter; // Formats the date displayed + String lastdate; // String to hold date displayed + Font clockFaceFont; // Font for number display on clock + Date currentDate; // Used to get date to display + Color handColor; // Color of main hands and dial + Color numberColor; // Color of second hand and numbers + + public void init() { + int x,y; + lastxs = lastys = lastxm = lastym = lastxh = lastyh = 0; + formatter = new SimpleDateFormat ("EEE MMM dd hh:mm:ss yyyy", Locale.getDefault()); + currentDate = new Date(); + lastdate = formatter.format(currentDate); + clockFaceFont = new Font("Serif", Font.PLAIN, 14); + handColor = Color.blue; + numberColor = Color.darkGray; + + try { + setBackground(new Color(Integer.parseInt(getParameter("bgcolor"),16))); + } catch (Exception E) { } + try { + handColor = new Color(Integer.parseInt(getParameter("fgcolor1"),16)); + } catch (Exception E) { } + try { + numberColor = new Color(Integer.parseInt(getParameter("fgcolor2"),16)); + } catch (Exception E) { } + resize(300,300); // Set clock window size + } + + // Plotpoints allows calculation to only cover 45 degrees of the circle, + // and then mirror + public void plotpoints(int x0, int y0, int x, int y, Graphics g) { + g.drawLine(x0+x,y0+y,x0+x,y0+y); + g.drawLine(x0+y,y0+x,x0+y,y0+x); + g.drawLine(x0+y,y0-x,x0+y,y0-x); + g.drawLine(x0+x,y0-y,x0+x,y0-y); + g.drawLine(x0-x,y0-y,x0-x,y0-y); + g.drawLine(x0-y,y0-x,x0-y,y0-x); + g.drawLine(x0-y,y0+x,x0-y,y0+x); + g.drawLine(x0-x,y0+y,x0-x,y0+y); + } + + // Circle is just Bresenham's algorithm for a scan converted circle + public void circle(int x0, int y0, int r, Graphics g) { + int x,y; + float d; + x=0; + y=r; + d=5/4-r; + plotpoints(x0,y0,x,y,g); + + while (y>x){ + if (d<0) { + d=d+2*x+3; + x++; + } + else { + d=d+2*(x-y)+5; + x++; + y--; + } + plotpoints(x0,y0,x,y,g); + } + } + + // Paint is the main part of the program + public void paint(Graphics g) { + int xh, yh, xm, ym, xs, ys, s = 0, m = 10, h = 10, xcenter, ycenter; + String today; + + currentDate = new Date(); + SimpleDateFormat formatter = new SimpleDateFormat("s",Locale.getDefault()); + try { + s = Integer.parseInt(formatter.format(currentDate)); + } catch (NumberFormatException n) { + s = 0; + } + formatter.applyPattern("m"); + try { + m = Integer.parseInt(formatter.format(currentDate)); + } catch (NumberFormatException n) { + m = 10; + } + formatter.applyPattern("h"); + try { + h = Integer.parseInt(formatter.format(currentDate)); + } catch (NumberFormatException n) { + h = 10; + } + formatter.applyPattern("EEE MMM dd HH:mm:ss yyyy"); + today = formatter.format(currentDate); + xcenter=80; + ycenter=55; + + // a= s* pi/2 - pi/2 (to switch 0,0 from 3:00 to 12:00) + // x = r(cos a) + xcenter, y = r(sin a) + ycenter + + xs = (int)(Math.cos(s * 3.14f/30 - 3.14f/2) * 45 + xcenter); + ys = (int)(Math.sin(s * 3.14f/30 - 3.14f/2) * 45 + ycenter); + xm = (int)(Math.cos(m * 3.14f/30 - 3.14f/2) * 40 + xcenter); + ym = (int)(Math.sin(m * 3.14f/30 - 3.14f/2) * 40 + ycenter); + xh = (int)(Math.cos((h*30 + m/2) * 3.14f/180 - 3.14f/2) * 30 + xcenter); + yh = (int)(Math.sin((h*30 + m/2) * 3.14f/180 - 3.14f/2) * 30 + ycenter); + + // Draw the circle and numbers + + g.setFont(clockFaceFont); + g.setColor(handColor); + circle(xcenter,ycenter,50,g); + g.setColor(numberColor); + g.drawString("9",xcenter-45,ycenter+3); + g.drawString("3",xcenter+40,ycenter+3); + g.drawString("12",xcenter-5,ycenter-37); + g.drawString("6",xcenter-3,ycenter+45); + + // Erase if necessary, and redraw + + g.setColor(getBackground()); + if (xs != lastxs || ys != lastys) { + g.drawLine(xcenter, ycenter, lastxs, lastys); + g.drawString(lastdate, 5, 125); + } + if (xm != lastxm || ym != lastym) { + g.drawLine(xcenter, ycenter-1, lastxm, lastym); + g.drawLine(xcenter-1, ycenter, lastxm, lastym); } + if (xh != lastxh || yh != lastyh) { + g.drawLine(xcenter, ycenter-1, lastxh, lastyh); + g.drawLine(xcenter-1, ycenter, lastxh, lastyh); } + g.setColor(numberColor); + g.drawString("", 5, 125); + g.drawString(today, 5, 125); + g.drawLine(xcenter, ycenter, xs, ys); + g.setColor(handColor); + g.drawLine(xcenter, ycenter-1, xm, ym); + g.drawLine(xcenter-1, ycenter, xm, ym); + g.drawLine(xcenter, ycenter-1, xh, yh); + g.drawLine(xcenter-1, ycenter, xh, yh); + lastxs=xs; lastys=ys; + lastxm=xm; lastym=ym; + lastxh=xh; lastyh=yh; + lastdate = today; + currentDate=null; + } + + public void start() { + timer = new Thread(this); + timer.start(); + } + + public void stop() { + timer = null; + } + + public void run() { + Thread me = Thread.currentThread(); + while (timer == me) { + try { + Thread.currentThread().sleep(100); + } catch (InterruptedException e) { + } + repaint(); + } + } + + public void update(Graphics g) { + paint(g); + } + + public String getAppletInfo() { + return "Title: A Clock \nAuthor: Rachel Gollub, 1995 \nAn analog clock."; + } + + public String[][] getParameterInfo() { + String[][] info = { + {"bgcolor", "hexadecimal RGB number", "The background color. Default is the color of your browser."}, + {"fgcolor1", "hexadecimal RGB number", "The color of the hands and dial. Default is blue."}, + {"fgcolor2", "hexadecimal RGB number", "The color of the seconds hand and numbers. Default is dark gray."} + }; + return info; + } +} diff --git a/webapps/examples/jsp/plugin/plugin.html b/webapps/examples/jsp/plugin/plugin.html new file mode 100644 index 000000000000..27bc51b131ff --- /dev/null +++ b/webapps/examples/jsp/plugin/plugin.html @@ -0,0 +1,30 @@ + + + +Untitled Document + + + + +

    + +

    Source Code for Plugin Example +

    + + + diff --git a/webapps/examples/jsp/plugin/plugin.jsp b/webapps/examples/jsp/plugin/plugin.jsp new file mode 100644 index 000000000000..548a110e2468 --- /dev/null +++ b/webapps/examples/jsp/plugin/plugin.jsp @@ -0,0 +1,34 @@ + + + Plugin example + +

    Current time is :

    + + + Plugin tag OBJECT or EMBED not supported by browser. + + +

    +

    + +The above applet is loaded using the Java Plugin from a jsp page using the +plugin tag. + +

    + + diff --git a/webapps/examples/jsp/security/protected/error.jsp b/webapps/examples/jsp/security/protected/error.jsp new file mode 100644 index 000000000000..5fc22eff8e62 --- /dev/null +++ b/webapps/examples/jsp/security/protected/error.jsp @@ -0,0 +1,25 @@ + + + +Error Page For Examples + + +Invalid username and/or password, please try +again. + + diff --git a/webapps/examples/jsp/security/protected/index.jsp b/webapps/examples/jsp/security/protected/index.jsp new file mode 100644 index 000000000000..d2e84be22611 --- /dev/null +++ b/webapps/examples/jsp/security/protected/index.jsp @@ -0,0 +1,81 @@ + +<% + if (request.getParameter("logoff") != null) { + session.invalidate(); + response.sendRedirect("index.jsp"); + return; + } +%> + + +Protected Page for Examples + + + +You are logged in as remote user +<%= util.HTMLFilter.filter(request.getRemoteUser()) %> +in session <%= session.getId() %>

    + +<% + if (request.getUserPrincipal() != null) { +%> + Your user principal name is + <%= util.HTMLFilter.filter(request.getUserPrincipal().getName()) %> +

    +<% + } else { +%> + No user principal could be identified.

    +<% + } +%> + +<% + String role = request.getParameter("role"); + if (role == null) + role = ""; + if (role.length() > 0) { + if (request.isUserInRole(role)) { +%> + You have been granted role + <%= util.HTMLFilter.filter(role) %>

    +<% + } else { +%> + You have not been granted role + <%= util.HTMLFilter.filter(role) %>

    +<% + } + } +%> + +To check whether your username has been granted a particular role, +enter it here: +
    + +
    +

    + +If you have configured this app for form-based authentication, you can log +off by clicking +here. +This should cause you to be returned to the logon page after the redirect +that is performed. + + + diff --git a/webapps/examples/jsp/security/protected/login.jsp b/webapps/examples/jsp/security/protected/login.jsp new file mode 100644 index 000000000000..1b381b2d706c --- /dev/null +++ b/webapps/examples/jsp/security/protected/login.jsp @@ -0,0 +1,38 @@ + + + +Login Page for Examples + +
    + + + + + + + + + + + + + +
    Username:
    Password:
    +
    + + diff --git a/webapps/examples/jsp/sessions/DummyCart.html b/webapps/examples/jsp/sessions/DummyCart.html new file mode 100644 index 000000000000..d953fa920976 --- /dev/null +++ b/webapps/examples/jsp/sessions/DummyCart.html @@ -0,0 +1,56 @@ + + + + + +sessions.DummyCart Bean Properties + + +

    +sessions.DummyCart Bean Properties +

    +
    +
    +
    public class DummyCart
    extends Object
    + +

    +


    + +

    + + + + + + + + + +
    +Properties Summary
    + +String +DummyCart:items +
    +
    + +Multi +
    +


    + + diff --git a/webapps/examples/jsp/sessions/carts.html b/webapps/examples/jsp/sessions/carts.html new file mode 100644 index 000000000000..3fce29103e43 --- /dev/null +++ b/webapps/examples/jsp/sessions/carts.html @@ -0,0 +1,53 @@ + + + + + carts + + + + + +
    +
    +Please enter item to add or remove: +
    +Add Item: + + + + +

    + + + +
    + +
    + + diff --git a/webapps/examples/jsp/sessions/carts.jsp b/webapps/examples/jsp/sessions/carts.jsp new file mode 100644 index 000000000000..3a3f6fcd4b9a --- /dev/null +++ b/webapps/examples/jsp/sessions/carts.jsp @@ -0,0 +1,44 @@ + + + + + + +<% + cart.processRequest(); +%> + + + +
    You have the following items in your cart: +
      +<% + String[] items = cart.getItems(); + for (int i=0; i +
    1. <% out.print(util.HTMLFilter.filter(items[i])); %> +<% + } +%> +
    + +
    + +
    +<%@ include file ="carts.html" %> + diff --git a/webapps/examples/jsp/sessions/crt.html b/webapps/examples/jsp/sessions/crt.html new file mode 100644 index 000000000000..11e6edafe0e9 --- /dev/null +++ b/webapps/examples/jsp/sessions/crt.html @@ -0,0 +1,34 @@ + + + + +Untitled Document + + + + +

    + +

    Source Code for Cart Example +

    + +

    Property Sheet for DummyCart +

    + + + diff --git a/webapps/examples/jsp/simpletag/foo.html b/webapps/examples/jsp/simpletag/foo.html new file mode 100644 index 000000000000..e20f840b7b97 --- /dev/null +++ b/webapps/examples/jsp/simpletag/foo.html @@ -0,0 +1,30 @@ + + + +Untitled Document + + + + +

    + +

    Source Code for the Simple Tag Example +

    + + + diff --git a/webapps/examples/jsp/simpletag/foo.jsp b/webapps/examples/jsp/simpletag/foo.jsp new file mode 100644 index 000000000000..d86fe0208300 --- /dev/null +++ b/webapps/examples/jsp/simpletag/foo.jsp @@ -0,0 +1,38 @@ + + + +<%@ taglib uri="http://tomcat.apache.org/example-taglib" prefix="eg"%> + +Radio stations that rock: + +
      + +
    • <%= member %>
    • +
      +
    + + +Did you see me on the stderr window? + + + +Did you see me on the browser window as well? + + + + diff --git a/webapps/examples/jsp/snp/snoop.html b/webapps/examples/jsp/snp/snoop.html new file mode 100644 index 000000000000..e48355b4351d --- /dev/null +++ b/webapps/examples/jsp/snp/snoop.html @@ -0,0 +1,31 @@ + + + + +Untitled Document + + + + +

    + +

    Source Code for Request Parameters Example +

    + + + diff --git a/webapps/examples/jsp/snp/snoop.jsp b/webapps/examples/jsp/snp/snoop.jsp new file mode 100644 index 000000000000..c8561dec6918 --- /dev/null +++ b/webapps/examples/jsp/snp/snoop.jsp @@ -0,0 +1,57 @@ + + + + +

    Request Information

    + +JSP Request Method: <%= util.HTMLFilter.filter(request.getMethod()) %> +
    +Request URI: <%= util.HTMLFilter.filter(request.getRequestURI()) %> +
    +Request Protocol: <%= util.HTMLFilter.filter(request.getProtocol()) %> +
    +Servlet path: <%= util.HTMLFilter.filter(request.getServletPath()) %> +
    +Path info: <%= util.HTMLFilter.filter(request.getPathInfo()) %> +
    +Query string: <%= util.HTMLFilter.filter(request.getQueryString()) %> +
    +Content length: <%= request.getContentLength() %> +
    +Content type: <%= util.HTMLFilter.filter(request.getContentType()) %> +
    +Server name: <%= util.HTMLFilter.filter(request.getServerName()) %> +
    +Server port: <%= request.getServerPort() %> +
    +Remote user: <%= util.HTMLFilter.filter(request.getRemoteUser()) %> +
    +Remote address: <%= util.HTMLFilter.filter(request.getRemoteAddr()) %> +
    +Remote host: <%= util.HTMLFilter.filter(request.getRemoteHost()) %> +
    +Authorization scheme: <%= util.HTMLFilter.filter(request.getAuthType()) %> +
    +Locale: <%= request.getLocale() %> +
    +The browser you are using is +<%= util.HTMLFilter.filter(request.getHeader("User-Agent")) %> +
    +
    + + diff --git a/webapps/examples/jsp/source.jsp b/webapps/examples/jsp/source.jsp new file mode 100644 index 000000000000..db094cf39a24 --- /dev/null +++ b/webapps/examples/jsp/source.jsp @@ -0,0 +1,20 @@ + +<%@ taglib uri="http://tomcat.apache.org/example-taglib" + prefix="eg" %> + + diff --git a/webapps/examples/jsp/tagplugin/choose.html b/webapps/examples/jsp/tagplugin/choose.html new file mode 100644 index 000000000000..afe90b2f42ef --- /dev/null +++ b/webapps/examples/jsp/tagplugin/choose.html @@ -0,0 +1,36 @@ + + + +View Source Code + + + +

    + + + + + +

    + +

    + Source Code for choose.jsp +

    + + + diff --git a/webapps/examples/jsp/tagplugin/choose.jsp b/webapps/examples/jsp/tagplugin/choose.jsp new file mode 100644 index 000000000000..62aa75ee5483 --- /dev/null +++ b/webapps/examples/jsp/tagplugin/choose.jsp @@ -0,0 +1,58 @@ + + + + Tag Examples - choose + + +

    Tag Plugin Examples - <c:choose>

    + +
    +
    + Plugin Introductory Notes +
    +
    Brief Instructions for Writing Plugins +

    +
    + + +
    + + <%@ taglib uri="http://java.sun.com/jsp/jstl/core" prefix="c" %> + + + # ${index}: + + + One!
    +
    + + Four!
    +
    + + Three!
    +
    + + Huh?
    +
    +
    +
    + + diff --git a/webapps/examples/jsp/tagplugin/foreach.html b/webapps/examples/jsp/tagplugin/foreach.html new file mode 100644 index 000000000000..3d2e6082daa0 --- /dev/null +++ b/webapps/examples/jsp/tagplugin/foreach.html @@ -0,0 +1,36 @@ + + + +View Source Code + + + +

    + + + + + +

    + +

    + Source Code for foreach.jsp +

    + + + diff --git a/webapps/examples/jsp/tagplugin/foreach.jsp b/webapps/examples/jsp/tagplugin/foreach.jsp new file mode 100644 index 000000000000..acf38ee7faa4 --- /dev/null +++ b/webapps/examples/jsp/tagplugin/foreach.jsp @@ -0,0 +1,57 @@ + + + + Tag Plugin Examples: forEach + + +

    Tag Plugin Examples - <c:forEach>

    + +
    +
    + Plugin Introductory Notes +
    +
    Brief Instructions for Writing Plugins +

    +
    + + +
    + + <%@ taglib uri="http://java.sun.com/jsp/jstl/core" prefix="c" %> + <%@ page import="java.util.Vector" %> + +

    Iterating over a range

    + + ${item} + + + <% Vector v = new Vector(); + v.add("One"); v.add("Two"); v.add("Three"); v.add("Four"); + + pageContext.setAttribute("vector", v); + %> + +

    Iterating over a Vector

    + + + ${item} + + + diff --git a/webapps/examples/jsp/tagplugin/howto.html b/webapps/examples/jsp/tagplugin/howto.html new file mode 100644 index 000000000000..bc40e8695c22 --- /dev/null +++ b/webapps/examples/jsp/tagplugin/howto.html @@ -0,0 +1,45 @@ + + + + Tag Plugin Implementation + + +

    How to write tag plugins

    +

    + To write a plugin, you'll need to download the source for Tomcat 5. + There are two steps: +

      +
    1. + Implement the plugin class.

      + This class, which implements + org.apache.jasper.compiler.tagplugin.TagPlugin + instructs Jasper what Java codes to generate in place of the tag + handler calls. + See Javadoc for org.apache.jasper.compiler.tagplugin.TagPlugin + for details. +

    2. + +
    3. + Create the plugin descriptor file WEB-INF/tagPlugins.xml

      + This file + specifies the plugin classes and their corresponding tag handler + classes. +

    4. +
    + + diff --git a/webapps/examples/jsp/tagplugin/if.html b/webapps/examples/jsp/tagplugin/if.html new file mode 100644 index 000000000000..b04ac592b9bc --- /dev/null +++ b/webapps/examples/jsp/tagplugin/if.html @@ -0,0 +1,36 @@ + + + +View Source Code + + + +

    + + + + + +

    + +

    + Source Code for if.jsp +

    + + + diff --git a/webapps/examples/jsp/tagplugin/if.jsp b/webapps/examples/jsp/tagplugin/if.jsp new file mode 100644 index 000000000000..dd21c80cca71 --- /dev/null +++ b/webapps/examples/jsp/tagplugin/if.jsp @@ -0,0 +1,45 @@ + + + + Tag Plugin Examples: if + + +

    Tag Plugin Examples - <c:if>

    + +
    +
    + Plugin Introductory Notes +
    + Brief Instructions for Writing Plugins +

    +
    + + +
    + <%@ taglib uri="http://java.sun.com/jsp/jstl/core" prefix="c" %> + +

    Set the test result to a variable

    + + The result of testing for (1==1) is: ${theTruth} + +

    Conditionally execute the body

    + + It's true that (2>0)! + + + diff --git a/webapps/examples/jsp/tagplugin/notes.html b/webapps/examples/jsp/tagplugin/notes.html new file mode 100644 index 000000000000..bbd22771912e --- /dev/null +++ b/webapps/examples/jsp/tagplugin/notes.html @@ -0,0 +1,41 @@ + + + + Tag Plugin Introduction + + +

    Tag Plugins: Introductory Notes

    +

    + Tomcat 5 provides a framework for implementing tag plugins. The + plugins instruct Jasper, at translation time, to replace tag handler + calls with Java scriptlets. + The framework allows tag library authors to implement plugins for + their tags. +

    +

    + Tomcat 5 is released with plugins for several JSTL tags. Note + that these plugins work with JSTL 1.1 as well as JSTL 1.0, though + the examples uses JSTL 1.1 and JSP 2.0. + These plugins are not complete (for instance, some item types not + handled in <c:if>). + They do serve as examples to show plugins in action (just + examine the generated Java files), and how they can be implemented. +

    + + + diff --git a/webapps/examples/jsp/xml/xml.html b/webapps/examples/jsp/xml/xml.html new file mode 100644 index 000000000000..00121424e98b --- /dev/null +++ b/webapps/examples/jsp/xml/xml.html @@ -0,0 +1,31 @@ + + + + +Untitled Document + + + + +

    + +

    Source Code for XML syntax Example +

    + + + diff --git a/webapps/examples/jsp/xml/xml.jsp b/webapps/examples/jsp/xml/xml.jsp new file mode 100644 index 000000000000..e84ae5604ef2 --- /dev/null +++ b/webapps/examples/jsp/xml/xml.jsp @@ -0,0 +1,70 @@ + + + + + + + + + String getDateTimeStr(Locale l) { + DateFormat df = SimpleDateFormat.getDateTimeInstance(DateFormat.MEDIUM, DateFormat.MEDIUM, l); + return df.format(new Date()); + } + + + + + Example JSP in XML format + + + +This is the output of a simple JSP using XML format. +
    + +
    Use a jsp:scriptlet to loop from 1 to 10:
    + +// Note we need to declare CDATA because we don't escape the less than symbol + + + + +
    +]]> + +
    + Use a jsp:expression to write the date and time in the browser's locale: + getDateTimeStr(request.getLocale()) +
    + + + + <p>This sentence is enclosed in a jsp:text element.</p> + + + + +
    diff --git a/webapps/examples/servlets/cookies.html b/webapps/examples/servlets/cookies.html new file mode 100644 index 000000000000..55950209804f --- /dev/null +++ b/webapps/examples/servlets/cookies.html @@ -0,0 +1,61 @@ + + + +Untitled Document + + + + +

    +

    Source Code for Cookie Example
    +

    + +
    import java.io.*;
    +import javax.servlet.*;
    +import javax.servlet.http.*;
    +
    +public class CookieExample extends HttpServlet {
    +
    +    public void doGet(HttpServletRequest request, HttpServletResponse response)
    +    throws IOException, ServletException
    +    {
    +        response.setContentType("text/html");
    +        PrintWriter out = response.getWriter();
    +        
    +        // print out cookies
    +
    +        Cookie[] cookies = request.getCookies();
    +        for (int i = 0; i < cookies.length; i++) {
    +            Cookie c = cookies[i];
    +            String name = c.getName();
    +            String value = c.getValue();
    +            out.println(name + " = " + value);
    +        }
    +
    +        // set a cookie
    +
    +        String name = request.getParameter("cookieName");
    +        if (name != null && name.length() > 0) {
    +            String value = request.getParameter("cookieValue");
    +            Cookie c = new Cookie(name, value);
    +            response.addCookie(c);
    +        }
    +    }
    +}
    + + diff --git a/webapps/examples/servlets/helloworld.html b/webapps/examples/servlets/helloworld.html new file mode 100644 index 000000000000..c2234467b9f1 --- /dev/null +++ b/webapps/examples/servlets/helloworld.html @@ -0,0 +1,50 @@ + + + +Untitled Document + + + + +

    +

    Source Code for HelloWorld Example
    +

    + +
    import java.io.*;
    +import javax.servlet.*;
    +import javax.servlet.http.*;
    +
    +public class HelloWorld extends HttpServlet {
    +
    +    public void doGet(HttpServletRequest request, HttpServletResponse response)
    +    throws IOException, ServletException
    +    {
    +        response.setContentType("text/html");
    +        PrintWriter out = response.getWriter();
    +        out.println("<html>");
    +        out.println("<head>");
    +        out.println("<title>Hello World!</title>");
    +        out.println("</head>");
    +        out.println("<body>");
    +        out.println("<h1>Hello World!</h1>");
    +        out.println("</body>");
    +        out.println("</html>");
    +    }
    +}
    + + diff --git a/webapps/examples/servlets/images/code.gif b/webapps/examples/servlets/images/code.gif new file mode 100644 index 000000000000..93af2cd130aa Binary files /dev/null and b/webapps/examples/servlets/images/code.gif differ diff --git a/webapps/examples/servlets/images/execute.gif b/webapps/examples/servlets/images/execute.gif new file mode 100644 index 000000000000..f64d70fd233d Binary files /dev/null and b/webapps/examples/servlets/images/execute.gif differ diff --git a/webapps/examples/servlets/images/return.gif b/webapps/examples/servlets/images/return.gif new file mode 100644 index 000000000000..af4f68f4a3a1 Binary files /dev/null and b/webapps/examples/servlets/images/return.gif differ diff --git a/webapps/examples/servlets/index.html b/webapps/examples/servlets/index.html new file mode 100644 index 000000000000..ee3155a21495 --- /dev/null +++ b/webapps/examples/servlets/index.html @@ -0,0 +1,121 @@ + + + + + + + + Servlet Examples + + +Servlet +Examples with Code +

    This is a collection of examples which demonstrate some of the more +frequently used parts of the Servlet API. Familiarity with the Java(tm) +Programming Language is assumed. +

    These examples will only work when viewed via an http URL. They will +not work if you are viewing these pages via a "file://..." URL. Please +refer to the README file provide with this Tomcat release regarding +how to configure and start the provided web server. +

    Wherever you see a form, enter some data and see how the servlet reacts. +When playing with the Cookie and Session Examples, jump back to the Headers +Example to see exactly what your browser is sending the server. +

    To navigate your way through the examples, the following icons will +help: +
      + + + + + + + + + + + + + + + + + + +
    Execute the example
    Look at the source code for the example
    Return to this screen
    + +

    Tip: To see the cookie interactions with your browser, try turning on +the "notify when setting a cookie" option in your browser preferences. +This will let you see when a session is created and give some feedback +when looking at the cookie demo. +
      + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    Hello WorldExecuteSource
    Request InfoExecuteSource
    Request HeadersExecuteSource
    Request ParametersExecuteSource
    CookiesExecuteSource
    SessionsExecuteSource
    + +

    Note: The source code for these examples does not contain all of the +source code that is actually in the example, only the important sections +of code. Code not important to understand the example has been removed +for clarity. + + diff --git a/webapps/examples/servlets/reqheaders.html b/webapps/examples/servlets/reqheaders.html new file mode 100644 index 000000000000..adda30cefa94 --- /dev/null +++ b/webapps/examples/servlets/reqheaders.html @@ -0,0 +1,49 @@ + + + +Untitled Document + + + + +

    +

    Source Code for RequestHeader Example
    +

    + +
    import java.io.*;
    +import java.util.*;
    +import javax.servlet.*;
    +import javax.servlet.http.*;
    +
    +public class RequestHeaderExample extends HttpServlet {
    +
    +    public void doGet(HttpServletRequest request, HttpServletResponse response)
    +    throws IOException, ServletException
    +    {
    +        response.setContentType("text/html");
    +        PrintWriter out = response.getWriter();
    +        Enumeration e = request.getHeaderNames();
    +        while (e.hasMoreElements()) {
    +            String name = (String)e.nextElement();
    +            String value = request.getHeader(name);
    +            out.println(name + " = " + value);
    +        }
    +    }
    +}
    + + diff --git a/webapps/examples/servlets/reqinfo.html b/webapps/examples/servlets/reqinfo.html new file mode 100644 index 000000000000..72ec49a316bf --- /dev/null +++ b/webapps/examples/servlets/reqinfo.html @@ -0,0 +1,68 @@ + + + +Untitled Document + + + + +

    +

    Source Code for Request Info Example
    +

    + +
    import java.io.*;
    +import javax.servlet.*;
    +import javax.servlet.http.*;
    +
    +public class RequestInfo extends HttpServlet {
    +
    +    public void doGet(HttpServletRequest request, HttpServletResponse response)
    +    throws IOException, ServletException
    +    {
    +        response.setContentType("text/html");
    +        PrintWriter out = response.getWriter();
    +        out.println("<html>");
    +        out.println("<body>");
    +        out.println("<head>");
    +        out.println("<title>Request Information Example</title>");
    +        out.println("</head>");
    +        out.println("<body>");
    +        out.println("<h3>Request Information Example</h3>");
    +        out.println("Method: " + request.getMethod());
    +        out.println("Request URI: " + request.getRequestURI());
    +        out.println("Protocol: " + request.getProtocol());
    +        out.println("PathInfo: " + request.getPathInfo());
    +        out.println("Remote Address: " + request.getRemoteAddr());
    +        out.println("</body>");
    +        out.println("</html>");
    +    }
    +
    +    /**
    +     * We are going to perform the same operations for POST requests
    +     * as for GET methods, so this method just sends the request to
    +     * the doGet method.
    +     */
    +
    +    public void doPost(HttpServletRequest request, HttpServletResponse response)
    +    throws IOException, ServletException
    +    {
    +        doGet(request, response);
    +    }
    +}
    + + diff --git a/webapps/examples/servlets/reqparams.html b/webapps/examples/servlets/reqparams.html new file mode 100644 index 000000000000..1dcdf0d136e9 --- /dev/null +++ b/webapps/examples/servlets/reqparams.html @@ -0,0 +1,78 @@ + + + +Untitled Document + + + + +

    +

    Source Code for Request Parameter Example
    +

    + +
    import java.io.*;
    +import java.util.*;
    +import javax.servlet.*;
    +import javax.servlet.http.*;
    +
    +public class RequestParamExample extends HttpServlet {
    +
    +    public void doGet(HttpServletRequest request, HttpServletResponse response)
    +    throws IOException, ServletException
    +    {
    +        response.setContentType("text/html");
    +        PrintWriter out = response.getWriter();
    +        out.println("<html>");
    +        out.println("<head>");
    +        out.println("<title>Request Parameters Example</title>");
    +        out.println("</head>");
    +        out.println("<body>");
    +        out.println("<h3>Request Parameters Example</h3>");
    +        out.println("Parameters in this request:<br>");
    +        if (firstName != null || lastName != null) {
    +            out.println("First Name:");
    +            out.println(" = " + HTMLFilter.filter(firstName) + "<br>");
    +            out.println("Last Name:");
    +            out.println(" = " + HTMLFilter.filter(lastName));
    +        } else {
    +            out.println("No Parameters, Please enter some");
    +        }
    +        out.println("<P>");
    +        out.print("<form action=\"");
    +        out.print("RequestParamExample\" ");
    +        out.println("method=POST>");
    +        out.println("First Name:");
    +        out.println("<input type=text size=20 name=firstname>");
    +        out.println("<br>");
    +        out.println("Last Name:");
    +        out.println("<input type=text size=20 name=lastname>");
    +        out.println("<br>");
    +        out.println("<input type=submit>");
    +        out.println("</form>");
    +        out.println("</body>");
    +        out.println("</html>");
    +    }
    +
    +    public void doPost(HttpServletRequest request, HttpServletResponse res)
    +    throws IOException, ServletException
    +    {
    +        doGet(request, response);
    +    }
    +}
    + + diff --git a/webapps/examples/servlets/sessions.html b/webapps/examples/servlets/sessions.html new file mode 100644 index 000000000000..c42d4142722a --- /dev/null +++ b/webapps/examples/servlets/sessions.html @@ -0,0 +1,70 @@ + + + +Untitled Document + + + + +

    +

    Source Code for Session Example
    +

    + +
    import java.io.*;
    +import java.util.*;
    +import javax.servlet.*;
    +import javax.servlet.http.*;
    +
    +public class SessionExample extends HttpServlet {
    +
    +    public void doGet(HttpServletRequest request, HttpServletResponse response)
    +    throws IOException, ServletException
    +    {
    +        response.setContentType("text/html");
    +        PrintWriter out = response.getWriter();
    +        
    +        HttpSession session = request.getSession(true);
    +
    +        // print session info
    +
    +        Date created = new Date(session.getCreationTime());
    +        Date accessed = new Date(session.getLastAccessedTime());
    +        out.println("ID " + session.getId());
    +        out.println("Created: " + created);
    +        out.println("Last Accessed: " + accessed);
    +
    +        // set session info if needed
    +
    +        String dataName = request.getParameter("dataName");
    +        if (dataName != null && dataName.length() > 0) {
    +            String dataValue = request.getParameter("dataValue");
    +            session.setAttribute(dataName, dataValue);
    +        }
    +
    +        // print session contents
    +
    +        Enumeration e = session.getAttributeNames();
    +        while (e.hasMoreElements()) {
    +            String name = (String)e.nextElement();
    +            String value = session.getAttribute(name).toString();
    +            out.println(name + " = " + value);
    +        }
    +    }
    +}
    + + diff --git a/webapps/host-manager/401.jsp b/webapps/host-manager/401.jsp new file mode 100644 index 000000000000..b2d9deb96ad8 --- /dev/null +++ b/webapps/host-manager/401.jsp @@ -0,0 +1,62 @@ +<%-- + Licensed to the Apache Software Foundation (ASF) under one or more + contributor license agreements. See the NOTICE file distributed with + this work for additional information regarding copyright ownership. + The ASF licenses this file to You under the Apache License, Version 2.0 + (the "License"); you may not use this file except in compliance with + the License. You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + + Unless required by applicable law or agreed to in writing, software + distributed under the License is distributed on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + See the License for the specific language governing permissions and + limitations under the License. +--%> +<% + response.setHeader("WWW-Authenticate", "Basic realm=\"Tomcat Host Manager Application\""); +%> + + + + 401 Unauthorized + + + +

    401 Unauthorized

    +

    + You are not authorized to view this page. If you have not changed + any configuration files, please examine the file + conf/tomcat-users.xml in your installation. That + file must contain the credentials to let you use this webapp. +

    +

    + For example, to add the admin-gui role to a user named + tomcat with a password of s3cret, add the following to the + config file listed above. +

    +
    +<role rolename="admin-gui"/>
    +<user username="tomcat" password="s3cret" roles="admin-gui"/>
    +
    +

    + Note that for Tomcat 7 onwards, the roles required to use the host manager + application were changed from the single admin role to the + following two roles. You will need to assign the role(s) required for + the functionality you wish to access. +

    +
      +
    • admin - allows access to the HTML GUI
    • +
    • admin-script - allows access to the text interface
    • +
    + + + diff --git a/webapps/host-manager/403.jsp b/webapps/host-manager/403.jsp new file mode 100644 index 000000000000..8f5b0d34f36e --- /dev/null +++ b/webapps/host-manager/403.jsp @@ -0,0 +1,76 @@ +<%-- + Licensed to the Apache Software Foundation (ASF) under one or more + contributor license agreements. See the NOTICE file distributed with + this work for additional information regarding copyright ownership. + The ASF licenses this file to You under the Apache License, Version 2.0 + (the "License"); you may not use this file except in compliance with + the License. You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + + Unless required by applicable law or agreed to in writing, software + distributed under the License is distributed on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + See the License for the specific language governing permissions and + limitations under the License. +--%> +<% + response.setHeader("WWW-Authenticate", "Basic realm=\"Tomcat Host Manager Application\""); +%> + + + + 403 Access Denied + + + +

    403 Access Denied

    +

    + You are not authorized to view this page. +

    +

    + If you have already configured the Host Manager application to allow access + and you have used your browsers back button, used a saved book-mark or + similar then you may have triggered the cross-site request forgery (CSRF) + protection that has been enabled for the HTML interface of the Host Manager + application. You will need to reset this protection by returning to the + main Host Manager page. + Once you return to this page, you will be able to continue using the Host + Manager appliction's HTML interface normally. If you continue to see this + access denied message, check that you have the necessary permissions to + access this application. +

    +

    If you have not changed + any configuration files, please examine the file + conf/tomcat-users.xml in your installation. That + file must contain the credentials to let you use this webapp. +

    +

    + For example, to add the admin-gui role to a user named + tomcat with a password of s3cret, add the following to the + config file listed above. +

    +
    +<role rolename="admin-gui"/>
    +<user username="tomcat" password="s3cret" roles="admin-gui"/>
    +
    +

    + Note that for Tomcat 7 onwards, the roles required to use the host manager + application were changed from the single admin role to the + following two roles. You will need to assign the role(s) required for + the functionality you wish to access. +

    +
      +
    • admin-gui - allows access to the HTML GUI
    • +
    • admin-script - allows access to the text interface
    • +
    + + + diff --git a/webapps/host-manager/404.jsp b/webapps/host-manager/404.jsp new file mode 100644 index 000000000000..f2b74ba4a0e5 --- /dev/null +++ b/webapps/host-manager/404.jsp @@ -0,0 +1,61 @@ +<%-- + Licensed to the Apache Software Foundation (ASF) under one or more + contributor license agreements. See the NOTICE file distributed with + this work for additional information regarding copyright ownership. + The ASF licenses this file to You under the Apache License, Version 2.0 + (the "License"); you may not use this file except in compliance with + the License. You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + + Unless required by applicable law or agreed to in writing, software + distributed under the License is distributed on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + See the License for the specific language governing permissions and + limitations under the License. +--%> +<%@ page import="org.apache.catalina.util.RequestUtil" %> + + + + 404 Not found + + + +

    404 Not found

    +

    + The page you tried to access + (<%=RequestUtil.filter((String) request.getAttribute( + "javax.servlet.error.request_uri"))%>) + does not exist. +

    +

    + The Host Manager application has been re-structured for Tomcat 7 onwards and some + of URLs have changed. All URLs used to access the Manager application should + now start with one of the following options: +

    +
      +
    • <%=request.getContextPath()%>/html for the HTML GUI
    • +
    • <%=request.getContextPath()%>/text for the text interface
    • +
    +

    + Note that the URL for the text interface has changed from + "<%=request.getContextPath()%>" to + "<%=request.getContextPath()%>/text". +

    +

    + You probably need to adjust the URL you are using to access the Host Manager + application. However, there is always a chance you have found a bug in the + Host Manager application. If you are sure you have found a bug, and that the + bug has not already been reported, please report it to the Apache Tomcat + team. +

    + + diff --git a/webapps/host-manager/META-INF/context.xml b/webapps/host-manager/META-INF/context.xml new file mode 100644 index 000000000000..b23cf481468e --- /dev/null +++ b/webapps/host-manager/META-INF/context.xml @@ -0,0 +1,18 @@ + + + diff --git a/webapps/host-manager/WEB-INF/web.xml b/webapps/host-manager/WEB-INF/web.xml new file mode 100644 index 000000000000..3a928c0f6ad9 --- /dev/null +++ b/webapps/host-manager/WEB-INF/web.xml @@ -0,0 +1,130 @@ + + + + + + Tomcat Host Manager Application + + A scriptable host management web application for the Tomcat Web Server; + Manager lets you view, create and remove virtual hosts. + + + + HostManager + org.apache.catalina.manager.host.HostManagerServlet + + debug + 2 + + + + HTMLHostManager + org.apache.catalina.manager.host.HTMLHostManagerServlet + + debug + 2 + + + + + CSRF + org.apache.catalina.filters.CsrfPreventionFilter + + entryPoints + /html,/html/,/html/list,/index.jsp + + + + + CSRF + HTMLHostManager + + + + + HostManager + /text/* + + + HTMLHostManager + /html/* + + + + + + HostManager commands + /text/* + + + + admin-script + + + + + HTMLHostManager commands + /html/* + + + + admin-gui + + + + + + BASIC + Tomcat Host Manager Application + + + + + + The role that is required to log in to the Host Manager Application HTML + interface + + admin-gui + + + + The role that is required to log in to the Host Manager Application text + interface + + admin-script + + + + 401 + /401.jsp + + + 403 + /403.jsp + + + 404 + /404.jsp + + + diff --git a/webapps/host-manager/images/add.gif b/webapps/host-manager/images/add.gif new file mode 100644 index 000000000000..0774d074e5e4 Binary files /dev/null and b/webapps/host-manager/images/add.gif differ diff --git a/webapps/host-manager/images/asf-logo.gif b/webapps/host-manager/images/asf-logo.gif new file mode 100644 index 000000000000..22eb9d7358ef Binary files /dev/null and b/webapps/host-manager/images/asf-logo.gif differ diff --git a/webapps/host-manager/images/code.gif b/webapps/host-manager/images/code.gif new file mode 100644 index 000000000000..d27307b5c094 Binary files /dev/null and b/webapps/host-manager/images/code.gif differ diff --git a/webapps/host-manager/images/design.gif b/webapps/host-manager/images/design.gif new file mode 100644 index 000000000000..f5db0a9fc783 Binary files /dev/null and b/webapps/host-manager/images/design.gif differ diff --git a/webapps/host-manager/images/docs.gif b/webapps/host-manager/images/docs.gif new file mode 100644 index 000000000000..d64a4a18c405 Binary files /dev/null and b/webapps/host-manager/images/docs.gif differ diff --git a/webapps/host-manager/images/fix.gif b/webapps/host-manager/images/fix.gif new file mode 100644 index 000000000000..d59ad642ba46 Binary files /dev/null and b/webapps/host-manager/images/fix.gif differ diff --git a/webapps/host-manager/images/tomcat.gif b/webapps/host-manager/images/tomcat.gif new file mode 100644 index 000000000000..61756736b823 Binary files /dev/null and b/webapps/host-manager/images/tomcat.gif differ diff --git a/webapps/host-manager/images/update.gif b/webapps/host-manager/images/update.gif new file mode 100644 index 000000000000..31e22abbc7a2 Binary files /dev/null and b/webapps/host-manager/images/update.gif differ diff --git a/webapps/host-manager/images/void.gif b/webapps/host-manager/images/void.gif new file mode 100644 index 000000000000..e565824aafaf Binary files /dev/null and b/webapps/host-manager/images/void.gif differ diff --git a/webapps/host-manager/index.jsp b/webapps/host-manager/index.jsp new file mode 100644 index 000000000000..d4816e5a2228 --- /dev/null +++ b/webapps/host-manager/index.jsp @@ -0,0 +1,18 @@ +<%-- + Licensed to the Apache Software Foundation (ASF) under one or more + contributor license agreements. See the NOTICE file distributed with + this work for additional information regarding copyright ownership. + The ASF licenses this file to You under the Apache License, Version 2.0 + (the "License"); you may not use this file except in compliance with + the License. You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + + Unless required by applicable law or agreed to in writing, software + distributed under the License is distributed on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + See the License for the specific language governing permissions and + limitations under the License. +--%> +<% response.sendRedirect(response.encodeRedirectURL(request.getContextPath() + + "/html")); %> \ No newline at end of file diff --git a/webapps/host-manager/manager.xml b/webapps/host-manager/manager.xml new file mode 100644 index 000000000000..ac5387fb90cb --- /dev/null +++ b/webapps/host-manager/manager.xml @@ -0,0 +1,30 @@ + + + + + + + + diff --git a/webapps/manager/401.jsp b/webapps/manager/401.jsp new file mode 100644 index 000000000000..8fb2cfd570dc --- /dev/null +++ b/webapps/manager/401.jsp @@ -0,0 +1,71 @@ +<%-- + Licensed to the Apache Software Foundation (ASF) under one or more + contributor license agreements. See the NOTICE file distributed with + this work for additional information regarding copyright ownership. + The ASF licenses this file to You under the Apache License, Version 2.0 + (the "License"); you may not use this file except in compliance with + the License. You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + + Unless required by applicable law or agreed to in writing, software + distributed under the License is distributed on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + See the License for the specific language governing permissions and + limitations under the License. +--%> +<% + response.setHeader("WWW-Authenticate", "Basic realm=\"Tomcat Manager Application\""); +%> + + + + 401 Unauthorized + + + +

    401 Unauthorized

    +

    + You are not authorized to view this page. If you have not changed + any configuration files, please examine the file + conf/tomcat-users.xml in your installation. That + file must contain the credentials to let you use this webapp. +

    +

    + For example, to add the manager-gui role to a user named + tomcat with a password of s3cret, add the following to the + config file listed above. +

    +
    +<role rolename="manager-gui"/>
    +<user username="tomcat" password="s3cret" roles="manager-gui"/>
    +
    +

    + Note that for Tomcat 7 onwards, the roles required to use the manager + application were changed from the single manager role to the + following four roles. You will need to assign the role(s) required for + the functionality you wish to access. +

    +
      +
    • manager-gui - allows access to the HTML GUI and the status + pages
    • +
    • manager-script - allows access to the text interface and the + status pages
    • +
    • manager-jmx - allows access to the JMX proxy and the status + pages
    • +
    • manager-status - allows access to the status pages only
    • +
    +

    + For more information - please see the + Manager App HOW-TO. +

    + + + diff --git a/webapps/manager/403.jsp b/webapps/manager/403.jsp new file mode 100644 index 000000000000..23f9d724f12a --- /dev/null +++ b/webapps/manager/403.jsp @@ -0,0 +1,86 @@ +<%-- + Licensed to the Apache Software Foundation (ASF) under one or more + contributor license agreements. See the NOTICE file distributed with + this work for additional information regarding copyright ownership. + The ASF licenses this file to You under the Apache License, Version 2.0 + (the "License"); you may not use this file except in compliance with + the License. You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + + Unless required by applicable law or agreed to in writing, software + distributed under the License is distributed on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + See the License for the specific language governing permissions and + limitations under the License. +--%> +<% + response.setHeader("WWW-Authenticate", "Basic realm=\"Tomcat Manager Application\""); +%> + + + + 403 Access Denied + + + +

    403 Access Denied

    +

    + You are not authorized to view this page. +

    +

    + If you have already configured the Manager application to allow access and + you have used your browsers back button, used a saved book-mark or similar + then you may have triggered the cross-site request forgery (CSRF) protection + that has been enabled for the HTML interface of the Manager application. You + will need to reset this protection by returning to the + main Manager page. Once you + return to this page, you will be able to continue using the Manager + appliction's HTML interface normally. If you continue to see this access + denied message, check that you have the necessary permissions to access this + application. +

    +

    + If you have not changed + any configuration files, please examine the file + conf/tomcat-users.xml in your installation. That + file must contain the credentials to let you use this webapp. +

    +

    + For example, to add the manager-gui role to a user named + tomcat with a password of s3cret, add the following to the + config file listed above. +

    +
    +<role rolename="manager-gui"/>
    +<user username="tomcat" password="s3cret" roles="manager-gui"/>
    +
    +

    + Note that for Tomcat 7 onwards, the roles required to use the manager + application were changed from the single manager role to the + following four roles. You will need to assign the role(s) required for + the functionality you wish to access. +

    +
      +
    • manager-gui - allows access to the HTML GUI and the status + pages
    • +
    • manager-script - allows access to the text interface and the + status pages
    • +
    • manager-jmx - allows access to the JMX proxy and the status + pages
    • +
    • manager-status - allows access to the status pages only
    • +
    +

    + For more information - please see the + Manager App HOW-TO. +

    + + + diff --git a/webapps/manager/404.jsp b/webapps/manager/404.jsp new file mode 100644 index 000000000000..86d4f351960d --- /dev/null +++ b/webapps/manager/404.jsp @@ -0,0 +1,62 @@ +<%-- + Licensed to the Apache Software Foundation (ASF) under one or more + contributor license agreements. See the NOTICE file distributed with + this work for additional information regarding copyright ownership. + The ASF licenses this file to You under the Apache License, Version 2.0 + (the "License"); you may not use this file except in compliance with + the License. You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + + Unless required by applicable law or agreed to in writing, software + distributed under the License is distributed on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + See the License for the specific language governing permissions and + limitations under the License. +--%> +<%@ page import="org.apache.catalina.util.RequestUtil" %> + + + + 404 Not found + + + +

    404 Not found

    +

    + The page you tried to access + (<%=RequestUtil.filter((String) request.getAttribute( + "javax.servlet.error.request_uri"))%>) + does not exist. +

    +

    + The Manager application has been re-structured for Tomcat 7 onwards and some + of URLs have changed. All URLs used to access the Manager application should + now start with one of the following options: +

    +
      +
    • <%=request.getContextPath()%>/html for the HTML GUI
    • +
    • <%=request.getContextPath()%>/text for the text interface
    • +
    • <%=request.getContextPath()%>/jmxproxy for the JMX proxy
    • +
    • <%=request.getContextPath()%>/status for the status pages
    • +
    +

    + Note that the URL for the text interface has changed from + "<%=request.getContextPath()%>" to + "<%=request.getContextPath()%>/text". +

    +

    + You probably need to adjust the URL you are using to access the Manager + application. However, there is always a chance you have found a bug in the + Manager application. If you are sure you have found a bug, and that the bug + has not already been reported, please report it to the Apache Tomcat team. +

    + + diff --git a/webapps/manager/META-INF/context.xml b/webapps/manager/META-INF/context.xml new file mode 100644 index 000000000000..b23cf481468e --- /dev/null +++ b/webapps/manager/META-INF/context.xml @@ -0,0 +1,18 @@ + + + diff --git a/webapps/manager/WEB-INF/jsp/sessionDetail.jsp b/webapps/manager/WEB-INF/jsp/sessionDetail.jsp new file mode 100644 index 000000000000..65db26b470fe --- /dev/null +++ b/webapps/manager/WEB-INF/jsp/sessionDetail.jsp @@ -0,0 +1,179 @@ + +<%-- + Licensed to the Apache Software Foundation (ASF) under one or more + contributor license agreements. See the NOTICE file distributed with + this work for additional information regarding copyright ownership. + The ASF licenses this file to You under the Apache License, Version 2.0 + (the "License"); you may not use this file except in compliance with + the License. You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + + Unless required by applicable law or agreed to in writing, software + distributed under the License is distributed on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + See the License for the specific language governing permissions and + limitations under the License. +--%> +<%@page session="false" contentType="text/html; charset=ISO-8859-1" %> +<%@page import="java.util.Enumeration" %> +<%@page import="javax.servlet.http.HttpSession" %> +<%@page import="org.apache.catalina.Session" %> +<%@page import="org.apache.catalina.manager.JspHelper" %> + +<%--!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.1//EN" + "http://www.w3.org/TR/xhtml11/DTD/xhtml11.dtd"--%> + + +<% String path = (String) request.getAttribute("path"); + Session currentSession = (Session)request.getAttribute("currentSession"); + HttpSession currentHttpSession = currentSession.getSession(); + String currentSessionId = currentSession.getId(); + String submitUrl = response.encodeURL(((HttpServletRequest) + pageContext.getRequest()).getRequestURL().toString()); +%> + + + + + + + + + + Sessions Administration: details for <%= currentSessionId %> + + +

    Details for Session <%= JspHelper.escapeXml(currentSessionId) %>

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    Session Id<%= currentSessionId %>
    Guessed Locale<%= JspHelper.guessDisplayLocaleFromSession(currentSession) %>
    Guessed User<%= JspHelper.guessDisplayUserFromSession(currentSession) %>
    Creation Time<%= JspHelper.getDisplayCreationTimeForSession(currentSession) %>
    Last Accessed Time<%= JspHelper.getDisplayLastAccessedTimeForSession(currentSession) %>
    Session Max Inactive Interval<%= JspHelper.secondsToTimeString(currentSession.getMaxInactiveInterval()) %>
    Used Time<%= JspHelper.getDisplayUsedTimeForSession(currentSession) %>
    Inactive Time<%= JspHelper.getDisplayInactiveTimeForSession(currentSession) %>
    TTL<%= JspHelper.getDisplayTTLForSession(currentSession) %>
    + +
    +
    + + + + +
    +
    + +
    <%= JspHelper.escapeXml(request.getAttribute("error")) %>
    +
    <%= JspHelper.escapeXml(request.getAttribute("message")) %>
    + + +<% int nAttributes = 0; + Enumeration attributeNamesEnumeration = currentHttpSession.getAttributeNames(); + while (attributeNamesEnumeration.hasMoreElements()) { + attributeNamesEnumeration.nextElement(); + ++nAttributes; + } +%> + + + + + + + + + <%--tfoot> + + + + + +<% attributeNamesEnumeration = currentHttpSession.getAttributeNames(); + while (attributeNamesEnumeration.hasMoreElements()) { + String attributeName = (String) attributeNamesEnumeration.nextElement(); +%> + + + + + +<% } // end while %> + +
    <%= JspHelper.formatNumber(nAttributes) %> attributes
    Remove AttributeAttribute nameAttribute value
    + TODO: set Max Inactive Interval on sessions +
    +
    +
    + + + + + <% + if ("Primary".equals(request.getAttribute("sessionType"))) { + %> + + <% + } else { + out.print("Primary sessions only"); + } + %> +
    +
    +
    <%= JspHelper.escapeXml(attributeName) %><% Object attributeValue = currentHttpSession.getAttribute(attributeName); %>"><%= JspHelper.escapeXml(attributeValue) %>
    + +
    +

    + + +

    +
    + +<%--div style="display: none;"> +

    + Valid HTML 4.01! + Valid XHTML 1.0! + Valid XHTML 1.1! +

    + + + + diff --git a/webapps/manager/WEB-INF/jsp/sessionsList.jsp b/webapps/manager/WEB-INF/jsp/sessionsList.jsp new file mode 100644 index 000000000000..fcf40bddd504 --- /dev/null +++ b/webapps/manager/WEB-INF/jsp/sessionsList.jsp @@ -0,0 +1,168 @@ + +<%-- + Licensed to the Apache Software Foundation (ASF) under one or more + contributor license agreements. See the NOTICE file distributed with + this work for additional information regarding copyright ownership. + The ASF licenses this file to You under the Apache License, Version 2.0 + (the "License"); you may not use this file except in compliance with + the License. You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + + Unless required by applicable law or agreed to in writing, software + distributed under the License is distributed on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + See the License for the specific language governing permissions and + limitations under the License. +--%> +<%@page session="false" contentType="text/html; charset=ISO-8859-1" %> +<%@page import="java.util.Collection" %> +<%@page import="java.util.Iterator" %> +<%@page import="org.apache.catalina.manager.JspHelper" %> +<%@page import="org.apache.catalina.Session" %> +<%@page import="org.apache.catalina.ha.session.DeltaSession" %> + + + +<%@page import="org.apache.catalina.manager.DummyProxySession"%> +<% String path = (String) request.getAttribute("path"); + String submitUrl = response.encodeURL(((HttpServletRequest) + pageContext.getRequest()).getRequestURI() + "?path=" + path); + Collection activeSessions = (Collection) request.getAttribute("activeSessions"); +%> + + + + + + + + + + Sessions Administration for <%= path %> + + +

    Sessions Administration for <%= path %>

    + +

    Tips:

    +
      +
    • Click on a column to sort.
    • +
    • To view a session details and/or remove a session attributes, click on its id.
    • +
    + +
    <%= JspHelper.escapeXml(request.getAttribute("error")) %>
    +
    <%= JspHelper.escapeXml(request.getAttribute("message")) %>
    + +
    +
    Active HttpSessions informations + + "/> + <% String order = (String) request.getAttribute("order"); + if (order == null || "".equals(order)) { + order = "ASC"; + } + %> + + + <%= JspHelper.formatNumber(activeSessions.size()) %> active Sessions
    + + + + + + + + + + + + + + + <% if (activeSessions.size() > 10) { %> + <%-- is the same as --%> + + + + + + + + + + + + + <% } // end if %> + +<% Iterator iter = activeSessions.iterator(); + while (iter.hasNext()) { + Session currentSession = (Session) iter.next(); + String currentSessionId = currentSession.getId(); + String type; + if (currentSession instanceof DeltaSession) { + if (((DeltaSession) currentSession).isPrimarySession()) { + type = "Primary"; + } else { + type = "Backup"; + } + } else if (currentSession instanceof DummyProxySession) { + type = "Proxy"; + } else { + type = "Primary"; + } +%> + + + + + + + + + + + +<% } // end while %> + +
    Session IdTypeGuessed LocaleGuessed User nameCreation TimeLast Accessed TimeUsed TimeInactive TimeTTL
    Session IdTypeGuessed LocaleGuessed User nameCreation TimeLast Accessed TimeUsed TimeInactive TimeTTL
    + <% + if ("Proxy".equals(type)) { + out.print(currentSessionId); + } else { + %> + <%= JspHelper.escapeXml(currentSessionId) %> + <% + } + %> + <%= type %><%= JspHelper.guessDisplayLocaleFromSession(currentSession) %><%= JspHelper.guessDisplayUserFromSession(currentSession) %><%= JspHelper.getDisplayCreationTimeForSession(currentSession) %><%= JspHelper.getDisplayLastAccessedTimeForSession(currentSession) %><%= JspHelper.getDisplayUsedTimeForSession(currentSession) %><%= JspHelper.getDisplayInactiveTimeForSession(currentSession) %><%= JspHelper.getDisplayTTLForSession(currentSession) %>
    +

    + +

    +
    +
    + +
    +

    + +

    +
    + +<%--div style="display: none;"> +

    + Valid HTML 4.01! + Valid XHTML 1.0! + Valid XHTML 1.1! +

    + + + + diff --git a/webapps/manager/WEB-INF/web.xml b/webapps/manager/WEB-INF/web.xml new file mode 100644 index 000000000000..e23e226d5da1 --- /dev/null +++ b/webapps/manager/WEB-INF/web.xml @@ -0,0 +1,209 @@ + + + + + + Tomcat Manager Application + + A scriptable management web application for the Tomcat Web Server; + Manager lets you view, load/unload/etc particular web applications. + + + + Manager + org.apache.catalina.manager.ManagerServlet + + debug + 2 + + + + HTMLManager + org.apache.catalina.manager.HTMLManagerServlet + + debug + 2 + + + + + 52428800 + 52428800 + 0 + + + + Status + org.apache.catalina.manager.StatusManagerServlet + + debug + 0 + + + + + JMXProxy + org.apache.catalina.manager.JMXProxyServlet + + + + + Manager + /text/* + + + Status + /status/* + + + JMXProxy + /jmxproxy/* + + + HTMLManager + /html/* + + + + CSRF + org.apache.catalina.filters.CsrfPreventionFilter + + entryPoints + /html,/html/,/html/list,/index.jsp + + + + + CSRF + HTMLManager + jsp + + + + + + Link to the UserDatabase instance from which we request lists of + defined role names. Typically, this will be connected to the global + user database with a ResourceLink element in server.xml or the context + configuration file for the Manager web application. + + users + + org.apache.catalina.UserDatabase + + + + + + + + HTML Manager interface (for humans) + /html/* + + + manager-gui + + + + + Text Manager interface (for scripts) + /text/* + + + manager-script + + + + + JMX Proxy interface + /jmxproxy/* + + + manager-jmx + + + + + Status interface + /status/* + + + manager-gui + manager-script + manager-jmx + manager-status + + + + + + BASIC + Tomcat Manager Application + + + + + + The role that is required to access the HTML Manager pages + + manager-gui + + + + The role that is required to access the text Manager pages + + manager-script + + + + The role that is required to access the HTML JMX Proxy + + manager-jmx + + + + The role that is required to access to the Manager Status pages + + manager-status + + + + 401 + /401.jsp + + + 403 + /403.jsp + + + 404 + /404.jsp + + + diff --git a/webapps/manager/images/add.gif b/webapps/manager/images/add.gif new file mode 100644 index 000000000000..0774d074e5e4 Binary files /dev/null and b/webapps/manager/images/add.gif differ diff --git a/webapps/manager/images/asf-logo.gif b/webapps/manager/images/asf-logo.gif new file mode 100644 index 000000000000..22eb9d7358ef Binary files /dev/null and b/webapps/manager/images/asf-logo.gif differ diff --git a/webapps/manager/images/code.gif b/webapps/manager/images/code.gif new file mode 100644 index 000000000000..d27307b5c094 Binary files /dev/null and b/webapps/manager/images/code.gif differ diff --git a/webapps/manager/images/design.gif b/webapps/manager/images/design.gif new file mode 100644 index 000000000000..f5db0a9fc783 Binary files /dev/null and b/webapps/manager/images/design.gif differ diff --git a/webapps/manager/images/docs.gif b/webapps/manager/images/docs.gif new file mode 100644 index 000000000000..d64a4a18c405 Binary files /dev/null and b/webapps/manager/images/docs.gif differ diff --git a/webapps/manager/images/fix.gif b/webapps/manager/images/fix.gif new file mode 100644 index 000000000000..d59ad642ba46 Binary files /dev/null and b/webapps/manager/images/fix.gif differ diff --git a/webapps/manager/images/tomcat.gif b/webapps/manager/images/tomcat.gif new file mode 100644 index 000000000000..61756736b823 Binary files /dev/null and b/webapps/manager/images/tomcat.gif differ diff --git a/webapps/manager/images/update.gif b/webapps/manager/images/update.gif new file mode 100644 index 000000000000..31e22abbc7a2 Binary files /dev/null and b/webapps/manager/images/update.gif differ diff --git a/webapps/manager/images/void.gif b/webapps/manager/images/void.gif new file mode 100644 index 000000000000..e565824aafaf Binary files /dev/null and b/webapps/manager/images/void.gif differ diff --git a/webapps/manager/index.jsp b/webapps/manager/index.jsp new file mode 100644 index 000000000000..d4816e5a2228 --- /dev/null +++ b/webapps/manager/index.jsp @@ -0,0 +1,18 @@ +<%-- + Licensed to the Apache Software Foundation (ASF) under one or more + contributor license agreements. See the NOTICE file distributed with + this work for additional information regarding copyright ownership. + The ASF licenses this file to You under the Apache License, Version 2.0 + (the "License"); you may not use this file except in compliance with + the License. You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + + Unless required by applicable law or agreed to in writing, software + distributed under the License is distributed on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + See the License for the specific language governing permissions and + limitations under the License. +--%> +<% response.sendRedirect(response.encodeRedirectURL(request.getContextPath() + + "/html")); %> \ No newline at end of file diff --git a/webapps/manager/status.xsd b/webapps/manager/status.xsd new file mode 100644 index 000000000000..6c8c14389500 --- /dev/null +++ b/webapps/manager/status.xsd @@ -0,0 +1,78 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/webapps/manager/xform.xsl b/webapps/manager/xform.xsl new file mode 100644 index 000000000000..a09445b1e401 --- /dev/null +++ b/webapps/manager/xform.xsl @@ -0,0 +1,111 @@ + + + + + + + + + + + + Tomcat Status + + + +
    Tomcat Status
    + + + + + +
    + + + + + + + + + + + + +
    JVM:free: total: max:

    +
    + + + Connector --
    + + + + +
    + + + + + + + + + +
    threadInfo maxThreads: minSpareThreads: currentThreadCount: currentThreadsBusy:

    +
    + + + + + + + + + + + +
    requestInfo maxTime: processingTime: requestCount: errorCount: bytesReceived: bytesSent:

    +
    + + + + + + +
    StageTimeB SentB RecvClientVHostRequest

    +
    + + + + + + + + + + ? + + + +