<?xml version="1.0"?>

<!--
 * ========================================================================
 * 
 * Copyright 2001-2004 The Apache Software Foundation.
 *
 * Licensed 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.
 * 
 * ========================================================================
-->

<document id="howto_classpath">

  <properties>
    <title>Setting the Cactus CLASSPATH</title>
  </properties>

  <body>

    <section title="Setting up Cactus Classpaths">

      <p>
        You must understand that your Cactus tests are started by a JUnit
        Test Runner (in the client JVM) and that the Cactus TestCase that you
        have extended will connect to the Cactus Redirector (in the server
        JVM), where your <code>testXXX()</code> methods will be executed. See
        <link href="site:how_it_works">How it works</link> to understand the
        mechanism.
      </p>

      <p>
        Please also check the <link href="site:howto_runner">TestRunner
        Howto</link> tutorial which explains all the different ways to
        start a JUnit Test Runner.
      </p>

      <note>
        <strong>It is very important that you understand what files you need
        to put in the client and server classpaths, as 99% of Cactus
        errors come from an incorrect classpath !</strong>
      </note>

      <figure src="images/classpath.jpg" alt="Classpaths"/>

      <section title="Client side classpath">

        <p>
          The Cactus tests are started by running a JUnit Test Runner (For
          explanations on how JUnit works see the
          <link href="http://junit.sourceforge.net">JUnit web site</link>).
          As pictured in figure 1, you need to have the following jars and
          classes in your client side classpath:
        </p>
        <ul>
          <li>
            <strong><code>junit.jar</code></strong>: obviously this is needed
            for the JUnit Test Runner and because the Cactus
            <code>XXXTestCase</code> classes extend the JUnit
            <code>org.junit.framework.TestCase</code> class.
          </li>
          <li>
            <strong><code>cactus.jar</code></strong>: well, this is the
            Cactus jar containing all Cactus classes,
          </li>
          <li>
            <strong>your test classes</strong>: these are
            your test classes that extend the Cactus <code>XXXTestCase</code>
            classes,
          </li>
          <li>
            <strong><code>servlet.jar or j2ee.jar</code></strong>: these are
            the Servlet API / J2EE API interfaces. This
            is needed on the client side classpath because your test cases
            extend one or several of <code>XXXTestCase</code> which use class
            variables that are Servlet / J2EE objects
            (<code>HttpSevletRequest</code>, <code>PageContext</code>, ...).
            You can get this jar either from your servlet engine or from the
            <link href="http://java.sun.com">Sun Web Site</link> (
            <link href="http://java.sun.com/products/servlet/download.html">
            Servlet download page</link> or
            <link href="http://java.sun.com/j2ee/download.html">J2EE download
            page</link>).
          </li>
          <li>
            <strong><code>httpclient.jar</code></strong>: needed for
            Cactus Cookie handling.
          </li>
          <li>
            <strong><code>commons-logging.jar</code></strong>: Cactus uses
            the Jakarta Commons Logging facade framework to provide seamless
            Cactus logging using any existing Logging framework (Log4j,
            LogKit, JDK 1.4 Logging, etc). It is also needed for Commons
            HttpClient.
          </li>
          <li>
            <strong><code>logging framework jar</code>(optional)</strong>: The
            logging framework to use (Log4j jar, LogKit jar, etc). It is
            optional as it is only needed for internal Cactus logging and in
            addition, the Commons Logging framework provides a simple logger
            that logs on the console.
          </li>
          <li>
            <strong><code>httpunit.jar</code></strong>, <strong>
            <code>Tidy.jar</code></strong> and <strong>
            <code>xerces.jar</code> (optional)</strong>: only needed if you
            wish to use
            <link href="http://httpunit.sourceforge.net">HttpUnit</link>
            in your <code>endXXX()</code> methods (see the
            <link href="site:howto_httpunit">HttpUnit Howto</link> tutorial).
            The 3 jars mentioned above are part of the HttpUnit distribution.
          </li>
          <li>
            <strong><code>aspectjrt.jar</code></strong>:
            <link href="ext:aspectj">AspectJ</link> runtime jar.
          </li>
        </ul>

        <note>
          If you have the habit of using class variables for the classes
          to test (as opposed to declaring them within the
          <code>testXXX()</code> method), you'll also need to put your classes
          under test in the client side classpath.
        </note>

        <p>
          In addition to the above mentioned jars and classes, you may have
          to put the <strong><code>cactus.properties</code></strong>
          configuration file in your classpath (Only if you are using it to
          configure Cactus of course). Details are described in the
          <link href="site:howto_config">Config Howto</link> tutorial).
        </p>

        <note>
          If you are using Log4J as the logging framework, you will also
          need to put a <code>log4j.properties</code> Log4j configuration
          file in your client side classpath (See the
          <link href="site:howto_config">Config Howto</link> tutorial).
        </note>

      </section>

      <section title="Server side classpath">

        <p>
          The server side part is a webapp. It can be packaged as a .war file
          or as expanded war. It should have the following structure, which
          will ensure that the classpath is correct:
        </p>

        <ul>
          <li>
            <strong><code>WEB-INF/lib/cactus.jar</code></strong>: the
            Cactus main jar,
          </li>
          <li>
            <strong><code>WEB-INF/lib/junit.jar</code></strong>: this is
            needed because the Cactus <code>XXXTestCase</code> extends
            the JUnit <code>org.junit.framework.TestCase</code> class.
          </li>
          <li>
            <strong><code>WEB-INF/lib/aspectjrt.jar</code></strong>:
            <link href="ext:aspectj">AspectJ</link> runtime jar.
          </li>
          <li>
            <strong><code>WEB-INF/lib/commons-logging.jar</code></strong>:
            Cactus uses the Jakarta Commons Logging facade framework to provide
            seamless Cactus logging using any existing Logging framework (Log4j,
            LogKit, JDK 1.4 Logging, etc). It is also needed for Commons
            HttpClient.
          </li>
          <li>
            <strong><code>WEB-INF/lib/logging framework jar</code>
            (optional)</strong>: The logging framework to use (Log4j jar,
            LogKit jar, etc). It is optional as it is only needed for internal
            Cactus logging and in addition, the Commons Logging framework
            provides a simple logger that logs on the console.
          </li>
          <li>
            <strong><code>WEB-INF/classes/&lt;your test classes&gt;</code>
            </strong>: obviously as their <code>testXXX()</code> methods will
            get executed in the container.
          </li>
          <li>
            <strong><code>WEB-INF/classes/&lt;your classes under test&gt;</code>
            </strong>: will be called by your test classes.
          </li>
        </ul>

       <note>
          If you have several webapps that use cactus you can put all Cactus
          jars in a place loaded by your container System classloader (provided
          your container correctly sets the Context classloader). The location
          is container-dependent; for example for Tomcat 4.x, you can put the
          jars in <code>TOMCAT_HOME/common/lib</code>.
        </note>

        <note>
          If you are using Log4J as the logging framework, you will also
          need to put a <code>log4j.properties</code> Log4j configuration
          file in your server side classpath (usually in
          <code>WEB-INF/classes</code>).
        </note>

      </section>

    </section>

  </body>
</document>
