You are viewing a plain text version of this content. The canonical link for it is here.
Posted to cvs@avalon.apache.org by le...@apache.org on 2002/04/04 04:34:16 UTC

cvs commit: jakarta-avalon-excalibur/logger/src/xdocs index.xml

leif        02/04/03 18:34:16

  Added:       logger   .cvsignore BUILDING.txt README.txt
                        ant.properties.sample build.bat build.sh build.xml
                        project.properties
               logger/src/conf MANIFEST.MF
               logger/src/java/org/apache/avalon/excalibur/logger
                        DefaultLogKitManager.java
                        DefaultLogTargetFactoryManager.java
                        DefaultLogTargetManager.java
                        Log4JLoggerManager.java LogKitLoggerManager.java
                        LogKitManageable.java LogKitManager.java
                        LogTargetFactory.java
                        LogTargetFactoryManageable.java
                        LogTargetFactoryManager.java LogTargetManager.java
                        LoggerManager.java package.html
               logger/src/java/org/apache/avalon/excalibur/logger/factory
                        AbstractTargetFactory.java
                        AsyncLogTargetFactory.java
                        DatagramTargetFactory.java FileTargetFactory.java
                        FormatterFactory.java JDBCTargetFactory.java
                        JMSTargetFactory.java
                        PriorityFilterTargetFactory.java
                        ServletTargetFactory.java SocketTargetFactory.java
                        StreamTargetFactory.java
               logger/src/test/org/apache/avalon/excalibur/logger/test
                        LogKitManagementTest.java
                        LogKitManagementTest.xtest
                        LogKitManagementTestCase.java
                        LogKitManagementTestCase.xtest TestComponent.java
                        TestComponentImpl.java
               logger/src/xdocs index.xml
  Log:
  Move the logger package into its own subproject.
  
  Revision  Changes    Path
  1.1                  jakarta-avalon-excalibur/logger/.cvsignore
  
  Index: .cvsignore
  ===================================================================
  ant.properties
  build
  checkstyle.cache
  distributions
  dist
  excalibur-*
  *.el
  *.ipr
  
  
  
  1.1                  jakarta-avalon-excalibur/logger/BUILDING.txt
  
  Index: BUILDING.txt
  ===================================================================
  
                 Building The Component
                 ======================
  
  Building from CVS
  -----------------
  
  Assuming:
   - You have a JDK installed, $JAVA_HOME set and 'java -version' works
   - Your directory structure follows standard CVS layout:
  
  jakarta-avalon/                   # jakarta-avalon CVS module, containing Ant
  jakarta-avalon-excalibur/              # contains build.sh, build.bat
  jakarta-avalon-excalibur/<component>   # you are here
  
  Then to build, you need only customize ant.properties (see step 6 below) and
  type './build.sh' (Unix) or 'build' (DOS). The '-projecthelp' option will
  list the available targets.
  
  
  Building from source distribution
  ---------------------------------
  
  In order to build a binary distribution version of the component from a 
  source  distribution,  you must have  a Java Development Kit (JDK)  for 
  version  1.1 (or  later)  downloaded  and  installed  (version  1.3.1 
  recommended), and do the following:
  
  (0) Download and Install a Java Development Kit
  
  * Download a Java Development Kit (JDK) release (version 1.1 or later) 
    from:
  
      http://java.sun.com/j2se/
  
  * Install the JDK according to the instructions included with the release.
  
  * Set an environment variable JAVA_HOME to the pathname of the directory
    into which you installed the JDK release.
  
  
  (1) Download and Install the Ant Binary Distribution
  
  * Download a binary distribution of Ant 1.4.1 from:
  
      http://jakarta.apache.org/builds/jakarta-ant/release/v1.4.1/bin/
  
    On a Windows platform, you will need:
      jakarta-ant-1.4.1-bin.zip
      jakarta-ant-1.4.1-optional.jar
  
    On a Unix platform, you will need:
      jakarta-ant-1.4.1-bin.tar.gz
      jakarta-ant-1.4.1-optional.jar
  
  * Unpack the binary distribution into a convenient location so that the
    Ant release resides in its own directory (conventionally named
    "jakarta-ant-1.4.1").  For the purposes of the remainder of this document,
    the symbolic name "${ant.home}" is used to refer to the full pathname of
    the release directory.
  
  * Copy the file "jakarta-ant-1.4.1-optional.jar", downloaded above, into
    the directory "${ant.home}/lib".  This makes available several Ant
    extension commands that are commonly required when building Jakarta
    based projects.
  
  * 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.
  
  (2) Download and Install the JUnit Testing Package (OPTIONAL)
  
  NOTE: This is only required if you wish to run the unit tests for 
  this component
  
  * Download the JUnit unit test package (version 3.7 or later) from:
  
      http://www.junit.org/
  
  * Unpack the package into a convenient location so that it resides in its
    own subdirectory.
  
  * Copy the file "junit.jar", downloaded above, into the directory 
    "${ant.home}/lib".  This makes available the unit testing tasks that are 
    commonly required when building Jakarta based projects.
  
  (3) Download and Install Checkstyle, 2.1 or later (OPTIONAL)
  
  NOTE: This is only required if you wish to generate reports regarding code style.
  
  * Download the Checkstyle package (version 2.1 or later) from:
  
      http://checkstyle.sourceforge.net/
  
  * Unpack the package into a convenient location so that it resides in its
    own subdirectory.
  
  (4) Download and Install the Xalan, XSLT engine (OPTIONAL)
  
  NOTE: This is only required if you wish to generate reports for the dependency 
  analysis, checkstyle and unit testing results.
  
  * Download the Xalan package (version 2.3.1 or later) from:
  
      http://xml.apache.org/xalan-j/
  
  * Unpack the package into a convenient location so that it resides in its
    own subdirectory.
  
  * Copy the files "xalan.jar", and "xml-apis.jar", downloaded above, into 
    the directory "${ant.home}/lib".  This makes available the XSLT reporting
    capabilities.
  
  (5) Customize Build Properties For This Subproject
  
  Most Jakarta subprojects allow you to customize Ant properties (with default
  values defined in the "build.xml" file.  This is done by creating a text file
  named "ant.properties" in the source distribution directory (for property
  definitions local to this subproject) and/or your user home directory (for
  property definitions shared across subprojects).  You can use the included
  "ant.properties.sample" file as a starting point for this.
  
  External dependencies are satisfied by configuring appropriate values in your 
  ant.properties file.  The easiest way to satisfy these dependencies is to copy 
  the "ant.properties.sample" file (in the top-level directory) to "ant.properties", 
  and then edit it to suit your environment.  On Unix, this would be done as:
  
    cd @dist.name@
    cp ant.properties.sample ant.properties
    emacs ant.properties
  
  NOTE:  Be *sure* that you do not check "ant.properties" in to the CVS
  repository.  This file is local to your own development environment, and
  each developer will have their own version.
  
  (6) Build A Binary Distribution
  
  Open a command line shell, and issue the following commands:
  
    cd @dist.name@
    ant -projecthelp
  
  If everything is installed correctly, you should see a list of the Ant
  "targets" that represent different commands you might wish to build.  By
  convention, the "jar" target creates the jar of the component. To execute 
  it, type the following commands:
  
    cd @dist.name@
    ant jar
  
  This will create a jar in the @dist.name@/build/lib directory that contains 
  the component.
  
  
  
  1.1                  jakarta-avalon-excalibur/logger/README.txt
  
  Index: README.txt
  ===================================================================
                  Avalons Excalibur Logger
                  --------------------------
  
  Logger Utilities.
  
  Getting Started:
  ----------------
  
  If you downloaded a source release of the component then you 
  will need to build the component. Directions for building the 
  component are located in BUILDING.txt
  
  If you downloaded a binary release, or a release with both binary 
  and source then it is recomended you look over the documentation
  in docs/index.html - and then look into the examples/ directory
  for examples of the component in action.
  
  
  
  
  1.1                  jakarta-avalon-excalibur/logger/ant.properties.sample
  
  Index: ant.properties.sample
  ===================================================================
  # -----------------------------------------------------------------------------
  # Component ant.properties.sample
  #
  # This is an example "ant.properties" file, used to customize the building of
  # the component for your local environment.  It defines the location of all
  # external modules that this component depend on.  Copy this file to
  # "ant.properties" in the source directory, and customize it as needed.
  #
  # The ant.properties values in this directory apply only to this component, and
  # override the defaults in ../ant.properties.
  #
  # $Id: ant.properties.sample,v 1.1 2002/04/04 02:34:13 leif Exp $
  # -----------------------------------------------------------------------------
  
  # --------------------------------------------------
  #      COMPONENT-SPECIFIC REQUIRED LIBRARIES
  # --------------------------------------------------
  
  
  # ----- Compile Control Flags -----
  build.debug=on
  build.optimize=off
  build.deprecation=off
  
  # ----- Base Directory in which all the packages are stored -----
  base.path=/opt
  
  # --------------------------------------------------
  #                REQUIRED LIBRARIES
  # --------------------------------------------------
  
  # ----- Logkit -----
  logkit.home=../../jakarta-avalon-logkit/build/lib
  logkit.jar=${logkit.home}/logkit.jar
  
  # ----- Avalon Framework -----
  avalon-framework.home=../../jakarta-avalon/build/lib
  avalon-framework.jar=${avalon-framework.home}/avalon-framework.jar
  
  # ----- JUnit Unit Test Suite, version 3.7 or later -----
  junit.home=${base.path}/junit3.7
  junit.lib=${junit.home}
  junit.jar=${junit.lib}/junit.jar
  
  
  
  # --------------------------------------------------
  #                OPTIONAL LIBRARIES
  # --------------------------------------------------
  
  # ----- Checkstyle, version 2.1 or later -----
  
  # Uncomment the 'do.checkstyle' flag property to enable checkstyle
  # do.checkstyle=
  checkstyle.home=${base.path}/checkstyle-2.1
  checkstyle.lib=${checkstyle.home}
  checkstyle.jar=${checkstyle.lib}/checkstyle-all-2.1.jar
  
  
  
  1.1                  jakarta-avalon-excalibur/logger/build.bat
  
  Index: build.bat
  ===================================================================
  @echo off
  
  set BASE=..
  call %BASE%\build.bat %1 %2 %3 %4 %5 %6 %7 %8
  
  
  
  1.1                  jakarta-avalon-excalibur/logger/build.sh
  
  Index: build.sh
  ===================================================================
  #!/bin/sh
  
  BASE=`dirname $0`  # Directory containing this script. Not the same as $PWD.
  
  $BASE/../build.sh -f $BASE/build.xml $@
  
  
  
  1.1                  jakarta-avalon-excalibur/logger/build.xml
  
  Index: build.xml
  ===================================================================
  <?xml version="1.0"?>
  
  <project name="Excalibur Logger" default="main" basedir=".">
  
      <!-- load per-project properties -->
      <property file="project.properties"/>
  
      <!--
        Give user a chance to override without editing this file
        (and without typing -D each time he compiles it)
      -->
      <property file="ant.properties"/>
      <property file="../ant.properties"/>
      <property file="${user.home}/.ant.properties"/>
  
      <!-- Settings used to configure compile environment -->
      <property name="build.debug" value="on"/>
      <property name="build.optimize" value="off"/>
      <property name="build.deprecation" value="off"/>
      <property name="build.compress" value="false"/>
      <property name="junit.failonerror" value="false"/>
  
      <!-- location of intermediate products -->
      <property name="build.dir" value="build"/>
      <property name="build.lib" value="${build.dir}/lib"/>
      <property name="build.conf" value="${build.dir}/conf"/>
      <property name="build.classes" value="${build.dir}/classes"/>
      <property name="build.tests" value="${build.dir}/tests"/>
      <property name="build.reports" value="${build.dir}/reports"/>
  
      <!-- Set the properties for source directories -->
      <property name="src.dir" value="src"/>
      <property name="java.dir" value="${src.dir}/java"/>
      <property name="conf.dir" value="${src.dir}/conf"/>
      <property name="test.dir" value="${src.dir}/test"/>
  
      <!-- Set the properties for distribution directories -->
      <property name="dist.dir" value="dist"/>
      <property name="dist.javadocs" value="${dist.dir}/docs/api"/>
  
      <!-- name of .zip/.tar.gz/.bz2 files and their top-level directory -->
      <property name="dist.name" value="${name}-${version}"/>
  
      <!-- name of jar file -->
      <property name="jar.name" value="${name}-${version}.jar"/>
  
      <!-- property indicating directory where all distribution archives are placed -->
      <property name="dist.base" value="distributions"/>
  
      <!-- Classpath for product -->
      <path id="project.class.path">
          <pathelement path="${java.class.path}"/>
          <pathelement location="${build.classes}"/>
          <pathelement location="${logkit.jar}"/>
          <pathelement location="${avalon-framework.jar}"/>
          <pathelement location="${junit.jar}"/>
          <pathelement location="${checkstyle.jar}"/>
      </path>
  
      <target name="main" depends="jar" description="Build the project"/>
      <target name="rebuild" depends="clean,main" description="Rebuild the project"/>
  
      <!-- Checks the environment for existing resources -->
      <target name="check-environment">
          <available property="log4j.present" classname="org.apache.log4j.Category">
              <classpath refid="project.class.path"/>
          </available>
          <available property="servlet.present" classname="javax.servlet.Servlet">
              <classpath refid="project.class.path"/>
          </available>
          <available property="jms.present" classname="javax.jms.Queue">
              <classpath refid="project.class.path"/>
          </available>
          <available property="datasource.present" classname="javax.sql.DataSource">
              <classpath refid="project.class.path"/>
          </available>
      </target>
      
      <!-- Compiles the source code -->
      <target name="compile" depends="check-environment" description="Compiles the source code">
  
          <mkdir dir="${build.classes}"/>
  
          <!-- Compile all classes including the tests. -->
          <javac srcdir="${java.dir}"
              destdir="${build.classes}"
              debug="${build.debug}"
              optimize="${build.optimize}"
              deprecation="${build.deprecation}"
              target="1.2">
              <classpath refid="project.class.path" />
              <src path="${test.dir}"/>
              <include name="**/*.java"/>
              <exclude name="**/Log4J*"
                       unless="log4j.present"/>
              <exclude name="org/apache/avalon/excalibur/logger/factory/ServletTargetFactory.java"
                       unless="servlet.present"/>
              <exclude name="org/apache/avalon/excalibur/logger/factory/JMSTargetFactory.java"
                       unless="jms.present"/>
              <exclude name="org/apache/avalon/excalibur/logger/factory/JDBCTargetFactory.java"
                       unless="datasource.present"/>
                  
              <!-- Exclude the tests for now because they depend on the testcase project, -->
              <!--  which in turn depends on logger.  These tests need to be rewritten to -->
              <!--  remove the dependencies. -->
              <exclude name="**/test/**"/>
          </javac>
  
          <!-- copy resources to same location as .class files -->
          <copy todir="${build.classes}">
              <fileset dir="${java.dir}">
                  <exclude name="**/*.java"/>
              </fileset>
          </copy>
  
          <copy todir="${build.classes}">
              <fileset dir="${test.dir}">
                  <exclude name="**/*.java"/>
              </fileset>
          </copy>
  
      </target>
  
      <!-- Copies and filters the manifest and license. Used by jar and dist -->
      <target name="prepare-conf">
          <mkdir dir="${build.conf}"/>
          <copy todir="${build.conf}" flatten="true">
              <fileset dir="../" includes="LICENSE.txt"/>
              <fileset dir="${conf.dir}" includes="MANIFEST.MF"/> 
              <filterset>
                  <filtersfile file="project.properties"/>
              </filterset>
          </copy>
  
      </target>
  
      <!-- Creates all the .jar file -->
      <target name="jar" depends="compile, prepare-conf" description="Generates the jar files">
  
          <mkdir dir="${build.lib}"/>
  
          <jar jarfile="${build.lib}/${jar.name}"
              basedir="${build.classes}"
              compress="${build.compress}"
              manifest="${build.conf}/MANIFEST.MF">
              <exclude name="**/test/**"/>
              <zipfileset dir="${build.conf}" prefix="META-INF/">
                  <include name="LICENSE.txt"/>
              </zipfileset>
          </jar>
      </target>
  
      <!-- Creates all the Javadocs -->
      <target name="javadocs" depends="compile" description="Generates the javadocs">
  
          <mkdir dir="${dist.javadocs}"/>
          <javadoc packagenames="org.apache.*"
              sourcepath="${java.dir}"
              destdir="${dist.javadocs}">
              <classpath refid="project.class.path" />
              <doclet name="com.sun.tools.doclets.standard.Standard">
                  <param name="-author"/>
                  <param name="-version"/>
                  <param name="-doctitle" value="${Name}"/>
                  <param name="-windowtitle" value="${Name} API"/>
                  <param name="-link" value="http://java.sun.com/j2se/1.4/docs/api/"/>
                  <param name="-link" value="http://java.sun.com/j2ee/sdk_1.3/techdocs/api/"/>
                  <param name="-link" value="http://jakarta.apache.org/avalon/api/"/>
                  <param name="-bottom"
                      value="&quot;Copyright &#169; ${year} Apache Jakarta Project. All Rights Reserved.&quot;"/>
              </doclet>
          </javadoc>
      </target>
  
      <target name="test" depends="compile" description="Perform the unit tests">
  
          <echo message="Performing Unit Tests" />
  
          <mkdir dir="${build.tests}"/>
  
          <junit fork="true"
              haltonfailure="${junit.failonerror}"
              printsummary="yes"
              dir="${build.tests}">
              <classpath refid="project.class.path"/>
  
              <formatter type="xml"/>    <!-- xml reports for junitreport -->
              <formatter type="plain"/>  <!-- text reports for humans     -->
  
              <batchtest todir="${build.tests}">
                  <fileset dir="${build.classes}">
                      <include name="**/test/*TestCase.class"/>
                      <exclude name="**/Abstract*"/>
                  </fileset>
              </batchtest>
          </junit>
  
      </target>
  
      <target name="test-reports" depends="test" description="Generate Reports for the unit tests">
  
          <mkdir dir="${build.reports}/junit"/>
  
          <junitreport todir="${build.reports}/junit">
              <fileset dir="${build.tests}">
                  <include name="TEST-*.xml"/>
              </fileset>
              <report format="frames" todir="${build.reports}/junit"/>
          </junitreport>
  
          <!-- Clean up the xml reports used by the junitreport task -->
          <!--
          <delete>
              <fileset dir="${build.tests}" includes="TEST-*.xml"/>
              <fileset dir="${build.tests}" includes="TESTS-*.xml"/>
          </delete>
          -->
  
      </target>
  
      <target name="checkstyle" if="do.checkstyle" description="Checkstyle">
  
          <!-- this invocation of checkstyle requires that checkstyle be downloaded and setup -->
          <!-- thats why you are required to define do.checkstyle property to generate the report -->
          <taskdef name="checkstyle"
              classname="com.puppycrawl.tools.checkstyle.CheckStyleTask">
              <classpath refid="project.class.path"/>
          </taskdef>
          <checkstyle
              lcurlyType="nl"
              lcurlyMethod="nl"
              lcurlyOther="nl"
              rcurly="ignore"
              allowProtected="false"
              allowPackage="false"
              allowNoAuthor="false"
              maxLineLen="100"
              maxMethodLen="100"
              maxConstructorLen="100"
              memberPattern="^m_[a-z][a-zA-Z0-9]*$"
              staticPattern="^c_[a-z][a-zA-Z0-9]*$"
              constPattern="(^c_[a-z][a-zA-Z0-9]*$)|([A-Z_]*$)"
              ignoreImportLen="true"
              allowTabs="false"
              javadocScope="protected"
              ignoreWhitespace="true"
              cacheFile="checkstyle.cache"
              failOnViolation="false"
              ignoreCastWhitespace="true">
              <fileset dir="${java.dir}">
                  <include name="**/*.java"/>
              </fileset>
              <formatter type="plain"/>
              <formatter type="xml" toFile="build/checkstyle-results.xml"/>
          </checkstyle>
      </target>
  
      <target name="checkstyle-report"
          depends="checkstyle"
          if="do.checkstyle"
          description="Generate Checkstyle Report">
  
          <mkdir dir="${build.reports}/checkstyle"/>
          <property name="checkstyle.pathhack" location="."/>
          <style style="../tools/etc/checkstyle-frames.xsl" in="build/checkstyle-results.xml"
              out="${build.reports}/checkstyle/delete-me.html">
              <param name="pathhack" expression="${checkstyle.pathhack}"/>
          </style>
  
      </target>
  
      <!-- Creates the distribution -->
      <target name="dist"
          depends="prepare-conf, jar, test-reports, checkstyle-report, javadocs"
          description="Generates a distribution (jar + javadocs + unit tests + checkstyle reports)">
  
          <mkdir dir="${dist.dir}"/>
          <copy file="${build.lib}/${jar.name}" todir="${dist.dir}"/>
          <copy file="${build.conf}/LICENSE.txt" todir="${dist.dir}"/>
          <copy file="../KEYS" todir="${dist.dir}"/>
          <copy file="README.txt" todir="${dist.dir}"/>
  
          <mkdir dir="${dist.base}"/>
  
          <zip zipfile="${dist.base}/${dist.name}-bin.zip" compress="true">
              <zipfileset dir="${dist.dir}" prefix="${dist.name}"/>
          </zip>
  
          <!--
            Not supported by released ant but when it is we should enable this across
            all of the products
          <tar longfile="gnu" tarfile="${dist.base}/${dist.name}-bin.tar">
            <tarfileset dir="${dist.dir}"
                        prefix="${dist.name}"
                        username="avalon"
                        group="avalon"/>
          </tar>
  
          <gzip zipfile="${dist.base}/${dist.name}-bin.tar.gz"
                src="${dist.name}-bin.tar"/>
          <bzip2 zipfile="${dist.base}/${dist.name}-bin.tar.gz"
                 src="${dist.name}-bin.tar"/>
  
          <delete file="${dist.base}/${dist.name}-bin.tar"/>
  
          <checksum fileext=".md5">
            <fileset dir="${dist.base}" />
          </checksum>
          -->
          <delete dir="${dist.dir}" />
  
      </target>
  
      <!-- Creates a minimal distribution -->
      <target name="dist.lite"
          depends="jar, test, javadocs"
          description="Generates a minimal distribution (jar + javadocs)">
  
          <mkdir dir="${dist.dir}"/>
          <copy file="${build.lib}/${jar.name}" todir="${dist.dir}"/>
          <copy file="../LICENSE.txt" todir="${dist.dir}"/>
          <copy file="../KEYS" todir="${dist.dir}"/>
          <copy file="README.txt" todir="${dist.dir}"/>
  
      </target>
  
      <!-- Cleans up build and distribution directories -->
      <target name="clean" description="Cleans up the project">
          <delete file="checkstyle.cache"/>
          <delete dir="${build.dir}" />
          <delete dir="${dist.dir}" />
          <delete dir="test" /> <!-- unit testing output directory -->
          <delete>
              <fileset dir="." includes="**/*~" defaultexcludes="no"/>
          </delete>
      </target>
  
      <target name="real-clean" depends="clean" description="Cleans up the project, including distributions">
          <delete dir="${dist.base}" />
      </target>
  
  </project>
  
  
  
  1.1                  jakarta-avalon-excalibur/logger/project.properties
  
  Index: project.properties
  ===================================================================
  name=excalibur-logger
  Name=Excalibur Logger
  version=1.0
  year=2000-2002
  
  
  
  1.1                  jakarta-avalon-excalibur/logger/src/conf/MANIFEST.MF
  
  Index: MANIFEST.MF
  ===================================================================
  Extension-Name: @name@
  Specification-Vendor: Apache Software Foundation
  Specification-Version: 1.0
  Implementation-Vendor: Apache Software Foundation
  Implementation-Version: @version@
  
  
  
  
  1.1                  jakarta-avalon-excalibur/logger/src/java/org/apache/avalon/excalibur/logger/DefaultLogKitManager.java
  
  Index: DefaultLogKitManager.java
  ===================================================================
  /*
   * Copyright (C) The Apache Software Foundation. All rights reserved.
   *
   * This software is published under the terms of the Apache Software License
   * version 1.1, a copy of which has been included  with this distribution in
   * the LICENSE.txt file.
   */
  package org.apache.avalon.excalibur.logger;
  
  import java.util.HashMap;
  import java.util.Map;
  import org.apache.avalon.framework.configuration.Configurable;
  import org.apache.avalon.framework.configuration.Configuration;
  import org.apache.avalon.framework.configuration.ConfigurationException;
  import org.apache.avalon.framework.context.Context;
  import org.apache.avalon.framework.context.ContextException;
  import org.apache.avalon.framework.context.Contextualizable;
  import org.apache.avalon.framework.logger.AbstractLogEnabled;
  import org.apache.avalon.framework.logger.LogEnabled;
  import org.apache.avalon.framework.logger.LogKitLogger;
  import org.apache.avalon.framework.logger.Loggable;
  import org.apache.log.Hierarchy;
  import org.apache.log.LogTarget;
  import org.apache.log.Logger;
  import org.apache.log.Priority;
  
  /**
   * Default LogManager implementation.  It populates the LogManager
   * from a configuration file.
   *
   * @deprecated we should use the new LogKitLoggerManager interface that directly
   *             supports the new framework Logger interface.
   *
   * @author <a href="mailto:giacomo@apache.org">Giacomo Pati</a>
   * @version CVS $Revision: 1.1 $ $Date: 2002/04/04 02:34:14 $
   * @since 4.0
   */
  public class DefaultLogKitManager
      extends AbstractLogEnabled
      implements LogKitManager, Loggable, Contextualizable, Configurable
  {
      /** Map for name to logger mapping */
      final private Map m_loggers = new HashMap();
  
      /** The context object */
      private Context m_context;
  
      /** The hierarchy private to LogKitManager */
      private Hierarchy m_hierarchy;
  
      /** The root logger to configure */
      private String m_prefix;
  
      /**
       * Creates a new <code>DefaultLogKitManager</code>. It will use a new <code>Hierarchy</code>.
       */
      public DefaultLogKitManager()
      {
          this( new Hierarchy() );
      }
  
      /**
       * Creates a new <code>DefaultLogKitManager</code> with an existing <code>Hierarchy</code>.
       */
      public DefaultLogKitManager( final Hierarchy hierarchy )
      {
          this( null, hierarchy );
      }
  
      /**
       * Creates a new <code>DefaultLogKitManager</code> using
       * specified logger name as root logger.
       */
      public DefaultLogKitManager( final String prefix )
      {
          this( prefix, new Hierarchy() );
      }
  
      /**
       * Creates a new <code>DefaultLogKitManager</code> with an existing <code>Hierarchy</code> using
       * specified logger name as root logger.
       */
      public DefaultLogKitManager( final String prefix, final Hierarchy hierarchy )
      {
          m_prefix = prefix;
          m_hierarchy = hierarchy;
      }
  
      public void setLogger( final Logger logger )
      {
          enableLogging( new LogKitLogger( logger ) );
      }
  
      /**
       * Retrieves a Logger from a category name. Usually
       * the category name refers to a configuration attribute name.  If
       * this LogKitManager does not have the match the default Logger will
       * be returned and a warning is issued.
       *
       * @param categoryName  The category name of a configured Logger.
       * @return the Logger.
       */
      public final Logger getLogger( final String categoryName )
      {
          final Logger logger = (Logger)m_loggers.get( categoryName );
  
          if( null != logger )
          {
              if( getLogger().isDebugEnabled() )
              {
                  getLogger().debug( "Logger for category " + categoryName + " returned" );
              }
              return logger;
          }
  
          if( getLogger().isDebugEnabled() )
          {
              getLogger().debug( "Logger for category " + categoryName
                                 + " not defined in configuration. New Logger created and returned" );
          }
  
          return m_hierarchy.getLoggerFor( categoryName );
      }
  
      /**
       * Retrieve Hierarchy for Loggers configured by the system.
       *
       * @return the Hierarchy
       */
      public Hierarchy getHierarchy()
      {
          return m_hierarchy;
      }
  
      /**
       * Reads a context object.
       *
       * @param context The context object.
       * @throws ContextException if the context is malformed
       */
      public final void contextualize( final Context context )
          throws ContextException
      {
          m_context = context;
      }
  
      /**
       * Reads a configuration object and creates the category mapping.
       *
       * @param configuration  The configuration object.
       * @throws ConfigurationException if the configuration is malformed
       */
      public final void configure( final Configuration configuration )
          throws ConfigurationException
      {
          final Configuration factories = configuration.getChild( "factories" );
          final LogTargetFactoryManager targetFactoryManager = setupTargetFactoryManager( factories );
  
          final Configuration targets = configuration.getChild( "targets" );
          final LogTargetManager targetManager = setupTargetManager( targets, targetFactoryManager );
  
          final Configuration categories = configuration.getChild( "categories" );
          final Configuration[] category = categories.getChildren( "category" );
          setupLoggers( targetManager, m_prefix, category );
      }
  
      /**
       * Setup a LogTargetFactoryManager
       *
       * @param configuration  The configuration object.
       * @throws ConfigurationException if the configuration is malformed
       */
      private final LogTargetFactoryManager setupTargetFactoryManager( final Configuration configuration )
          throws ConfigurationException
      {
          final DefaultLogTargetFactoryManager targetFactoryManager = new DefaultLogTargetFactoryManager();
          if( targetFactoryManager instanceof LogEnabled )
          {
              targetFactoryManager.enableLogging( getLogger() );
          }
  
          if( targetFactoryManager instanceof Contextualizable )
          {
              try
              {
                  targetFactoryManager.contextualize( m_context );
              }
              catch( final ContextException ce )
              {
                  throw new ConfigurationException( "cannot contextualize default factory manager", ce );
              }
          }
  
          targetFactoryManager.configure( configuration );
  
          return targetFactoryManager;
      }
  
      /**
       * Setup a LogTargetManager
       *
       * @param configuration  The configuration object.
       * @throws ConfigurationException if the configuration is malformed
       */
      private final LogTargetManager setupTargetManager( final Configuration configuration,
                                                         final LogTargetFactoryManager targetFactoryManager )
          throws ConfigurationException
      {
          final DefaultLogTargetManager targetManager = new DefaultLogTargetManager();
  
          if( targetManager instanceof LogEnabled )
          {
              targetManager.enableLogging( getLogger() );
          }
  
          if( targetManager instanceof Contextualizable )
          {
              try
              {
                  targetManager.contextualize( m_context );
              }
              catch( final ContextException ce )
              {
                  throw new ConfigurationException( "cannot contextualize factory manager", ce );
              }
          }
  
          if( targetManager instanceof LogTargetFactoryManageable )
          {
              targetManager.setLogTargetFactoryManager( targetFactoryManager );
          }
  
          if( targetManager instanceof Configurable )
          {
              targetManager.configure( configuration );
          }
  
          return targetManager;
      }
  
      /**
       * Setup Loggers
       *
       * @param categories The array object of configurations for categories.
       * @throws ConfigurationException if the configuration is malformed
       */
      private final void setupLoggers( final LogTargetManager targetManager,
                                       final String parentCategory,
                                       final Configuration[] categories )
          throws ConfigurationException
      {
          for( int i = 0; i < categories.length; i++ )
          {
              final String category = categories[ i ].getAttribute( "name" );
              final String loglevel = categories[ i ].getAttribute( "log-level" ).toUpperCase();
  
              final Configuration[] targets = categories[ i ].getChildren( "log-target" );
              final LogTarget[] logTargets = new LogTarget[ targets.length ];
              for( int j = 0; j < targets.length; j++ )
              {
                  final String id = targets[ j ].getAttribute( "id-ref" );
                  logTargets[ j ] = targetManager.getLogTarget( id );
              }
  
              if( "".equals( category ) && logTargets.length > 0 )
              {
                  m_hierarchy.setDefaultPriority( Priority.getPriorityForName( loglevel ) );
                  m_hierarchy.setDefaultLogTargets( logTargets );
              }
  
              final String fullCategory;
              if( null == parentCategory )
              {
                  fullCategory = category;
              }
              else
              {
                  fullCategory = parentCategory + Logger.CATEGORY_SEPARATOR + category;
              }
  
              final Logger logger = m_hierarchy.getLoggerFor( fullCategory );
              m_loggers.put( fullCategory, logger );
              if( getLogger().isDebugEnabled() )
              {
                  getLogger().debug( "added logger for category " + fullCategory );
              }
              logger.setPriority( Priority.getPriorityForName( loglevel ) );
              logger.setLogTargets( logTargets );
  
              final Configuration[] subCategories = categories[ i ].getChildren( "category" );
              if( null != subCategories )
              {
                  setupLoggers( targetManager, fullCategory, subCategories );
              }
          }
      }
  }
  
  
  
  1.1                  jakarta-avalon-excalibur/logger/src/java/org/apache/avalon/excalibur/logger/DefaultLogTargetFactoryManager.java
  
  Index: DefaultLogTargetFactoryManager.java
  ===================================================================
  /*
   * Copyright (C) The Apache Software Foundation. All rights reserved.
   *
   * This software is published under the terms of the Apache Software License
   * version 1.1, a copy of which has been included  with this distribution in
   * the LICENSE.txt file.
   */
  package org.apache.avalon.excalibur.logger;
  
  import java.util.HashMap;
  import java.util.Map;
  import org.apache.avalon.framework.configuration.Configurable;
  import org.apache.avalon.framework.configuration.Configuration;
  import org.apache.avalon.framework.configuration.ConfigurationException;
  import org.apache.avalon.framework.context.Context;
  import org.apache.avalon.framework.context.ContextException;
  import org.apache.avalon.framework.context.Contextualizable;
  import org.apache.avalon.framework.logger.AbstractLogEnabled;
  import org.apache.avalon.framework.logger.LogEnabled;
  
  /**
   * Default LogTargetFactoryManager implementation.  It populates the LogTargetFactoryManager
   * from a configuration file.
   *
   * @author <a href="mailto:giacomo@apache.org">Giacomo Pati</a>
   * @version CVS $Revision: 1.1 $ $Date: 2002/04/04 02:34:14 $
   * @since 4.0
   */
  public class DefaultLogTargetFactoryManager
      extends AbstractLogEnabled
      implements LogTargetFactoryManager, Contextualizable, Configurable
  {
      /** Map for name to logger mapping */
      private final Map m_factories = new HashMap();
  
      /** The context object */
      private Context m_context;
  
      /**
       * Retrieves a LogTargetFactory from a name. Usually
       * the factory name refers to a element name. If
       * this LogTargetFactoryManager does not have the match a null
       * will be returned.
       *
       * @param factoryName The name of a configured LogTargetFactory.
       * @return the LogTargetFactory or null if none is found.
       */
      public final LogTargetFactory getLogTargetFactory( final String factoryName )
      {
          final LogTargetFactory factory = (LogTargetFactory)m_factories.get( factoryName );
          return factory;
      }
  
      /**
       * Reads a context object.
       *
       * @param context The context object.
       * @throws ContextException if the context is malformed
       */
      public final void contextualize( final Context context )
          throws ContextException
      {
          m_context = context;
      }
  
      /**
       * Reads a configuration object and creates the category mapping.
       *
       * @param configuration  The configuration object.
       * @throws ConfigurationException if the configuration is malformed
       */
      public final void configure( final Configuration configuration )
          throws ConfigurationException
      {
          final Configuration[] confs = configuration.getChildren( "factory" );
          for( int i = 0; i < confs.length; i++ )
          {
              final String factoryClass = confs[ i ].getAttribute( "class" );
              final String factoryType = confs[ i ].getAttribute( "type" );
  
              //FIXME(GP): Is this the right way to load a class or
              //           should the ContextClassLoader be used?
              final LogTargetFactory logTargetFactory;
              try
              {
                  Class clazz = null;
  
                  //First lets try the context ClassLoader
                  final ClassLoader classLoader = Thread.currentThread().getContextClassLoader();
                  if( null != classLoader )
                  {
                      try
                      {
                          clazz = classLoader.loadClass( factoryClass );
                      }
                      catch( final ClassNotFoundException cnfe )
                      {
                      }
                  }
  
                  //Okay now lets try classLoader this class was loaded from
                  if( null == clazz )
                  {
                      clazz = getClass().getClassLoader().loadClass( factoryClass );
                  }
  
                  logTargetFactory = (LogTargetFactory)clazz.newInstance();
              }
              catch( final ClassNotFoundException cnfe )
              {
                  throw new ConfigurationException( "cannot find LogTargetFactory class " + factoryClass, cnfe );
              }
              catch( final InstantiationException ie )
              {
                  throw new ConfigurationException( "cannot instantiate LogTargetFactory class " + factoryClass, ie );
              }
              catch( final IllegalAccessException iae )
              {
                  throw new ConfigurationException( "cannot access LogTargetFactory class " + factoryClass, iae );
              }
  
              if( logTargetFactory instanceof LogEnabled )
              {
                  ( (LogEnabled)logTargetFactory ).enableLogging( getLogger() );
              }
  
              if( logTargetFactory instanceof Contextualizable )
              {
                  try
                  {
                      ( (Contextualizable)logTargetFactory ).contextualize( m_context );
                  }
                  catch( final ContextException ce )
                  {
                      throw new ConfigurationException( "cannot contextualize LogTargetFactory " + factoryClass, ce );
                  }
              }
  
              if( logTargetFactory instanceof Configurable )
              {
                  ( (Configurable)logTargetFactory ).configure( confs[ i ] );
              }
  
              if( logTargetFactory instanceof LogTargetFactoryManageable )
              {
                  ( (LogTargetFactoryManageable)logTargetFactory ).setLogTargetFactoryManager( this );
              }
  
              if( getLogger().isDebugEnabled() )
              {
                  getLogger().debug( "added new LogTargetFactory of type " + factoryType );
              }
              m_factories.put( factoryType, logTargetFactory );
          }
      }
  }
  
  
  
  1.1                  jakarta-avalon-excalibur/logger/src/java/org/apache/avalon/excalibur/logger/DefaultLogTargetManager.java
  
  Index: DefaultLogTargetManager.java
  ===================================================================
  /*
   * Copyright (C) The Apache Software Foundation. All rights reserved.
   *
   * This software is published under the terms of the Apache Software License
   * version 1.1, a copy of which has been included  with this distribution in
   * the LICENSE.txt file.
   */
  package org.apache.avalon.excalibur.logger;
  
  import java.util.HashMap;
  import java.util.Map;
  import org.apache.avalon.framework.configuration.Configurable;
  import org.apache.avalon.framework.configuration.Configuration;
  import org.apache.avalon.framework.configuration.ConfigurationException;
  import org.apache.avalon.framework.context.Context;
  import org.apache.avalon.framework.context.ContextException;
  import org.apache.avalon.framework.context.Contextualizable;
  import org.apache.avalon.framework.logger.AbstractLogEnabled;
  import org.apache.log.LogTarget;
  
  /**
   * Default LogTargetManager implementation.  It populates the LogTargetManager
   * from a configuration file.
   *
   * @author <a href="mailto:giacomo@apache.org">Giacomo Pati</a>
   * @version CVS $Revision: 1.1 $ $Date: 2002/04/04 02:34:14 $
   * @since 4.0
   */
  public class DefaultLogTargetManager
      extends AbstractLogEnabled
      implements LogTargetManager, LogTargetFactoryManageable, Contextualizable, Configurable
  {
      /** Map for ID to LogTarget mapping */
      final private Map m_targets = new HashMap();
  
      /** The context object */
      private Context m_context;
  
      /** The LogTargetFactoryManager object */
      private LogTargetFactoryManager m_factoryManager;
  
      /**
       * Retrieves a LogTarget for an ID. If this LogTargetManager
       * does not have the match a null will be returned.
       *
       * @param id The LogTarget ID
       * @return the LogTarget or null if none is found.
       */
      public final LogTarget getLogTarget( final String id )
      {
          final LogTarget logTarget = (LogTarget)m_targets.get( id );
          return logTarget;
      }
  
      /**
       * Reads a context object.
       *
       * @param context The context object.
       * @throws ContextException if the context is malformed
       */
      public final void contextualize( final Context context )
          throws ContextException
      {
          m_context = context;
      }
  
      /**
       * Gets the LogTargetFactoryManager.
       */
      public final void setLogTargetFactoryManager( final LogTargetFactoryManager logTargetFactoryManager )
      {
          m_factoryManager = logTargetFactoryManager;
      }
  
      /**
       * Reads a configuration object and creates the log targets.
       *
       * @param configuration  The configuration object.
       * @throws ConfigurationException if the configuration is malformed
       */
      public final void configure( final Configuration configuration )
          throws ConfigurationException
      {
          if( null == m_factoryManager )
          {
              throw new ConfigurationException( "LogTargetFactory not received" );
          }
  
          final Configuration[] confs = configuration.getChildren();
          for( int i = 0; i < confs.length; i++ )
          {
              final String targetName = confs[ i ].getName();
              final LogTargetFactory logTargetFactory = m_factoryManager.getLogTargetFactory( targetName );
              final LogTarget logTarget = logTargetFactory.createTarget( confs[ i ] );
              final String targetId = confs[ i ].getAttribute( "id" );
              if( getLogger().isDebugEnabled() )
              {
                  getLogger().debug( "added new LogTarget of id " + targetId );
              }
              m_targets.put( targetId, logTarget );
          }
      }
  }
  
  
  
  1.1                  jakarta-avalon-excalibur/logger/src/java/org/apache/avalon/excalibur/logger/Log4JLoggerManager.java
  
  Index: Log4JLoggerManager.java
  ===================================================================
  /*
   * Copyright (C) The Apache Software Foundation. All rights reserved.
   *
   * This software is published under the terms of the Apache Software License
   * version 1.1, a copy of which has been included  with this distribution in
   * the LICENSE.txt file.
   */
  package org.apache.avalon.excalibur.logger;
  
  import java.util.HashMap;
  import java.util.Map;
  import org.apache.avalon.framework.logger.Log4JLogger;
  import org.apache.avalon.framework.logger.Logger;
  import org.apache.log4j.Category;
  import org.apache.log4j.Hierarchy;
  
  /**
   * Log4JLoggerManager implementation.  This is the interface used to get instances of
   * a Logger for your system.  This manager does not set up the categories--it
   * leaves that as an excercise for Log4J's construction.
   *
   * @author <a href="mailto:bloritsch@apache.org">Berin Loritsch</a>
   * @version CVS $Revision: 1.1 $ $Date: 2002/04/04 02:34:14 $
   * @since 4.1
   */
  public class Log4JLoggerManager
      implements LoggerManager
  {
      /** Map for name to logger mapping */
      final private Map m_loggers = new HashMap();
  
      /** The root logger to configure */
      private String m_prefix;
  
      /** The hierarchy private to LogKitManager */
      private Hierarchy m_hierarchy;
  
      /** The default logger used for this system */
      final private Logger m_defaultLogger;
  
      /**
       * Creates a new <code>DefaultLogKitManager</code>. It will use a new <code>Hierarchy</code>.
       */
      public Log4JLoggerManager()
      {
          this( Category.getDefaultHierarchy() );
      }
  
      /**
       * Creates a new <code>DefaultLogKitManager</code> with an existing <code>Hierarchy</code>.
       */
      public Log4JLoggerManager( final Hierarchy hierarchy )
      {
          this( null, hierarchy );
      }
  
      /**
       * Creates a new <code>DefaultLogKitManager</code> using
       * specified logger name as root logger.
       */
      public Log4JLoggerManager( final String prefix )
      {
          this( prefix, Category.getDefaultHierarchy() );
      }
  
      /**
       * Creates a new <code>DefaultLogKitManager</code> with an existing <code>Hierarchy</code> using
       * specified logger name as root logger.
       */
      public Log4JLoggerManager( final String prefix, final Hierarchy hierarchy )
      {
          this( prefix, hierarchy,
                new Log4JLogger( hierarchy.getInstance( "" ) ) );
      }
  
      /**
       * Creates a new <code>DefaultLogKitManager</code> with an existing <code>Hierarchy</code> using
       * specified logger name as root logger.
       */
      public Log4JLoggerManager( final String prefix, final Hierarchy hierarchy, final Logger defaultLogger )
      {
          m_prefix = prefix;
          m_hierarchy = hierarchy;
          m_defaultLogger = defaultLogger;
      }
  
      /**
       * Retrieves a Logger from a category name. Usually
       * the category name refers to a configuration attribute name.  If
       * this LogKitManager does not have the match the default Logger will
       * be returned and a warning is issued.
       *
       * @param categoryName  The category name of a configured Logger.
       * @return the Logger.
       */
      public final Logger getLoggerForCategory( final String categoryName )
      {
          Logger logger = (Logger)m_loggers.get( categoryName );
  
          if( null != logger )
          {
              if( m_defaultLogger.isDebugEnabled() )
              {
                  m_defaultLogger.debug( "Logger for category " + categoryName + " returned" );
              }
              return logger;
          }
  
          if( m_defaultLogger.isDebugEnabled() )
          {
              m_defaultLogger.debug( "Logger for category " + categoryName
                                     + " not defined in configuration. New Logger created and returned" );
          }
  
          logger = new Log4JLogger( m_hierarchy.getInstance( categoryName ) );
          m_loggers.put( categoryName, logger );
          return logger;
      }
  
      public final Logger getDefaultLogger()
      {
          return m_defaultLogger;
      }
  }
  
  
  
  1.1                  jakarta-avalon-excalibur/logger/src/java/org/apache/avalon/excalibur/logger/LogKitLoggerManager.java
  
  Index: LogKitLoggerManager.java
  ===================================================================
  /*
   * Copyright (C) The Apache Software Foundation. All rights reserved.
   *
   * This software is published under the terms of the Apache Software License
   * version 1.1, a copy of which has been included  with this distribution in
   * the LICENSE.txt file.
   */
  package org.apache.avalon.excalibur.logger;
  
  import java.util.HashMap;
  import java.util.Map;
  import org.apache.avalon.framework.configuration.Configurable;
  import org.apache.avalon.framework.configuration.Configuration;
  import org.apache.avalon.framework.configuration.ConfigurationException;
  import org.apache.avalon.framework.context.Context;
  import org.apache.avalon.framework.context.ContextException;
  import org.apache.avalon.framework.context.Contextualizable;
  import org.apache.avalon.framework.logger.LogEnabled;
  import org.apache.avalon.framework.logger.LogKitLogger;
  import org.apache.avalon.framework.logger.Logger;
  import org.apache.log.Hierarchy;
  import org.apache.log.LogTarget;
  import org.apache.log.Priority;
  
  /**
   * LogKitLoggerManager implementation.  It populates the LoggerManager
   * from a configuration file.
   *
   * @author <a href="mailto:giacomo@apache.org">Giacomo Pati</a>
   * @author <a href="mailto:bloritsch@apache.org">Berin Loritsch</a>
   * @version CVS $Revision: 1.1 $ $Date: 2002/04/04 02:34:14 $
   * @since 4.0
   */
  public class LogKitLoggerManager
      implements LoggerManager, Contextualizable, Configurable
  {
      /** Map for name to logger mapping */
      final private Map m_loggers = new HashMap();
  
      /** The context object */
      private Context m_context;
  
      /** The hierarchy private to LogKitManager */
      private Hierarchy m_hierarchy;
  
      /** The root logger to configure */
      private String m_prefix;
  
      /** The default logger used for this system */
      final private Logger m_defaultLogger;
  
      /**
       * Creates a new <code>DefaultLogKitManager</code>. It will use a new <code>Hierarchy</code>.
       */
      public LogKitLoggerManager()
      {
          this( new Hierarchy() );
      }
  
      /**
       * Creates a new <code>DefaultLogKitManager</code> with an existing <code>Hierarchy</code>.
       */
      public LogKitLoggerManager( final Hierarchy hierarchy )
      {
          this( null, hierarchy );
      }
  
      /**
       * Creates a new <code>DefaultLogKitManager</code> using
       * specified logger name as root logger.
       */
      public LogKitLoggerManager( final String prefix )
      {
          this( prefix, new Hierarchy() );
      }
  
      /**
       * Creates a new <code>DefaultLogKitManager</code> with an existing <code>Hierarchy</code> using
       * specified logger name as root logger.
       */
      public LogKitLoggerManager( final String prefix, final Hierarchy hierarchy )
      {
          this( prefix, hierarchy,
                new LogKitLogger( hierarchy.getLoggerFor( "" ) ) );
      }
  
      /**
       * Creates a new <code>DefaultLogKitManager</code> with an existing <code>Hierarchy</code> using
       * specified logger name as root logger.
       */
      public LogKitLoggerManager( final String prefix, final Hierarchy hierarchy, final Logger defaultLogger )
      {
          m_prefix = prefix;
          m_hierarchy = hierarchy;
          m_defaultLogger = defaultLogger;
      }
  
      /**
       * Retrieves a Logger from a category name. Usually
       * the category name refers to a configuration attribute name.  If
       * this LogKitManager does not have the match the default Logger will
       * be returned and a warning is issued.
       *
       * @param categoryName  The category name of a configured Logger.
       * @return the Logger.
       */
      public final Logger getLoggerForCategory( final String categoryName )
      {
          final Logger logger = (Logger)m_loggers.get( categoryName );
  
          if( null != logger )
          {
              if( m_defaultLogger.isDebugEnabled() )
              {
                  m_defaultLogger.debug( "Logger for category " + categoryName + " returned" );
              }
              return logger;
          }
  
          if( m_defaultLogger.isDebugEnabled() )
          {
              m_defaultLogger.debug( "Logger for category " + categoryName
                                     + " not defined in configuration. New Logger created and returned" );
          }
  
          return new LogKitLogger( m_hierarchy.getLoggerFor( categoryName ) );
      }
  
      public final Logger getDefaultLogger()
      {
          return m_defaultLogger;
      }
  
      /**
       * Reads a context object.
       *
       * @param context The context object.
       * @throws ContextException if the context is malformed
       */
      public final void contextualize( final Context context )
          throws ContextException
      {
          m_context = context;
      }
  
      /**
       * Reads a configuration object and creates the category mapping.
       *
       * @param configuration  The configuration object.
       * @throws ConfigurationException if the configuration is malformed
       */
      public final void configure( final Configuration configuration )
          throws ConfigurationException
      {
          final Configuration factories = configuration.getChild( "factories" );
          final LogTargetFactoryManager targetFactoryManager = setupTargetFactoryManager( factories );
  
          final Configuration targets = configuration.getChild( "targets" );
          final LogTargetManager targetManager = setupTargetManager( targets, targetFactoryManager );
  
          final Configuration categories = configuration.getChild( "categories" );
          final Configuration[] category = categories.getChildren( "category" );
          setupLoggers( targetManager, m_prefix, category );
      }
  
      /**
       * Setup a LogTargetFactoryManager
       *
       * @param configuration  The configuration object.
       * @throws ConfigurationException if the configuration is malformed
       */
      private final LogTargetFactoryManager setupTargetFactoryManager( final Configuration configuration )
          throws ConfigurationException
      {
          final DefaultLogTargetFactoryManager targetFactoryManager = new DefaultLogTargetFactoryManager();
          if( targetFactoryManager instanceof LogEnabled )
          {
              targetFactoryManager.enableLogging( m_defaultLogger );
          }
  
          if( targetFactoryManager instanceof Contextualizable )
          {
              try
              {
                  targetFactoryManager.contextualize( m_context );
              }
              catch( final ContextException ce )
              {
                  throw new ConfigurationException( "cannot contextualize default factory manager", ce );
              }
          }
  
          targetFactoryManager.configure( configuration );
  
          return targetFactoryManager;
      }
  
      /**
       * Setup a LogTargetManager
       *
       * @param configuration  The configuration object.
       * @throws ConfigurationException if the configuration is malformed
       */
      private final LogTargetManager setupTargetManager( final Configuration configuration,
                                                         final LogTargetFactoryManager targetFactoryManager )
          throws ConfigurationException
      {
          final DefaultLogTargetManager targetManager = new DefaultLogTargetManager();
  
          if( targetManager instanceof LogEnabled )
          {
              targetManager.enableLogging( m_defaultLogger );
          }
  
          if( targetManager instanceof Contextualizable )
          {
              try
              {
                  targetManager.contextualize( m_context );
              }
              catch( final ContextException ce )
              {
                  throw new ConfigurationException( "cannot contextualize factory manager", ce );
              }
          }
  
          if( targetManager instanceof LogTargetFactoryManageable )
          {
              targetManager.setLogTargetFactoryManager( targetFactoryManager );
          }
  
          if( targetManager instanceof Configurable )
          {
              targetManager.configure( configuration );
          }
  
          return targetManager;
      }
  
      /**
       * Setup Loggers
       *
       * @param categories []  The array object of configurations for categories.
       * @throws ConfigurationException if the configuration is malformed
       */
      private final void setupLoggers( final LogTargetManager targetManager,
                                       final String parentCategory,
                                       final Configuration[] categories )
          throws ConfigurationException
      {
          for( int i = 0; i < categories.length; i++ )
          {
              final String category = categories[ i ].getAttribute( "name" );
              final String loglevel = categories[ i ].getAttribute( "log-level" ).toUpperCase();
  
              final Configuration[] targets = categories[ i ].getChildren( "log-target" );
              final LogTarget[] logTargets = new LogTarget[ targets.length ];
              for( int j = 0; j < targets.length; j++ )
              {
                  final String id = targets[ j ].getAttribute( "id-ref" );
                  logTargets[ j ] = targetManager.getLogTarget( id );
              }
  
              if( "".equals( category ) && logTargets.length > 0 )
              {
                  m_hierarchy.setDefaultPriority( Priority.getPriorityForName( loglevel ) );
                  m_hierarchy.setDefaultLogTargets( logTargets );
              }
  
              final String fullCategory;
              if( null == parentCategory )
              {
                  fullCategory = category;
              }
              else
              {
                  fullCategory = parentCategory + org.apache.log.Logger.CATEGORY_SEPARATOR + category;
              }
  
              final org.apache.log.Logger logger = m_hierarchy.getLoggerFor( fullCategory );
              m_loggers.put( fullCategory, new LogKitLogger( logger ) );
              if( m_defaultLogger.isDebugEnabled() )
              {
                  m_defaultLogger.debug( "added logger for category " + fullCategory );
              }
              logger.setPriority( Priority.getPriorityForName( loglevel ) );
              logger.setLogTargets( logTargets );
  
              final Configuration[] subCategories = categories[ i ].getChildren( "category" );
              if( null != subCategories )
              {
                  setupLoggers( targetManager, fullCategory, subCategories );
              }
          }
      }
  }
  
  
  
  1.1                  jakarta-avalon-excalibur/logger/src/java/org/apache/avalon/excalibur/logger/LogKitManageable.java
  
  Index: LogKitManageable.java
  ===================================================================
  /*
   * Copyright (C) The Apache Software Foundation. All rights reserved.
   *
   * This software is published under the terms of the Apache Software License
   * version 1.1, a copy of which has been included  with this distribution in
   * the LICENSE.txt file.
   */
  package org.apache.avalon.excalibur.logger;
  
  /**
   * LogKitManageable Interface, use this to set the LogKitManagers for child
   * Components.
   *
   * @author <a href="mailto:giacomo@apache.org">Giacomo Pati</a>
   * @version CVS $Revision: 1.1 $ $Date: 2002/04/04 02:34:14 $
   * @since 4.0
   */
  public interface LogKitManageable
  {
      /**
       * Sets the LogKitManager for child components.  Can be for special
       * purpose components, however it is used mostly internally.
       */
      void setLogKitManager( final LogKitManager logmanager );
  }
  
  
  
  1.1                  jakarta-avalon-excalibur/logger/src/java/org/apache/avalon/excalibur/logger/LogKitManager.java
  
  Index: LogKitManager.java
  ===================================================================
  /*
   * Copyright (C) The Apache Software Foundation. All rights reserved.
   *
   * This software is published under the terms of the Apache Software License
   * version 1.1, a copy of which has been included  with this distribution in
   * the LICENSE.txt file.
   */
  package org.apache.avalon.excalibur.logger;
  
  import org.apache.log.Hierarchy;
  import org.apache.log.Logger;
  
  /**
   * LogKitManager Interface.
   *
   * @deprecated we should use the new LoggerManager interface that directly
   *             supports the new framework Logger interface.
   *
   * @author <a href="mailto:giacomo@apache.org">Giacomo Pati</a>
   * @version CVS $Revision: 1.1 $ $Date: 2002/04/04 02:34:14 $
   */
  public interface LogKitManager
  {
      /**
       * Find a logger based on a category name.
       */
      Logger getLogger( String categoryName );
  
      /**
       * Retrieve Hierarchy for Loggers configured by the system.
       *
       * @return the Hierarchy
       */
      Hierarchy getHierarchy();
  }
  
  
  
  1.1                  jakarta-avalon-excalibur/logger/src/java/org/apache/avalon/excalibur/logger/LogTargetFactory.java
  
  Index: LogTargetFactory.java
  ===================================================================
  /*
   * Copyright (C) The Apache Software Foundation. All rights reserved.
   *
   * This software is published under the terms of the Apache Software License
   * version 1.1, a copy of which has been included  with this distribution in
   * the LICENSE.txt file.
   */
  package org.apache.avalon.excalibur.logger;
  
  import org.apache.avalon.framework.configuration.Configuration;
  import org.apache.avalon.framework.configuration.ConfigurationException;
  import org.apache.log.LogTarget;
  
  /**
   * LogTargetFactory Interface.
   *
   * @author <a href="mailto:giacomo@apache.org">Giacomo Pati</a>
   * @version CVS $Revision: 1.1 $ $Date: 2002/04/04 02:34:14 $
   * @since 4.0
   */
  public interface LogTargetFactory
  {
      /**
       * Create a LogTarget based on a Configuration
       */
      LogTarget createTarget( Configuration configuration ) throws ConfigurationException;
  }
  
  
  
  1.1                  jakarta-avalon-excalibur/logger/src/java/org/apache/avalon/excalibur/logger/LogTargetFactoryManageable.java
  
  Index: LogTargetFactoryManageable.java
  ===================================================================
  /*
   * Copyright (C) The Apache Software Foundation. All rights reserved.
   *
   * This software is published under the terms of the Apache Software License
   * version 1.1, a copy of which has been included  with this distribution in
   * the LICENSE.txt file.
   */
  package org.apache.avalon.excalibur.logger;
  
  /**
   * LogTargetFactoryManageable Interface, use this to set the LogTargetFactoryManager
   * for child Components.
   *
   * @author <a href="mailto:giacomo@apache.org">Giacomo Pati</a>
   * @version CVS $Revision: 1.1 $ $Date: 2002/04/04 02:34:14 $
   * @since 4.0
   */
  public interface LogTargetFactoryManageable
  {
      /**
       * Sets the LogTargetFactoryManager for child components.  Can be for special
       * purpose components, however it is used mostly internally.
       */
      void setLogTargetFactoryManager( LogTargetFactoryManager logTargetFactoryManager );
  }
  
  
  
  1.1                  jakarta-avalon-excalibur/logger/src/java/org/apache/avalon/excalibur/logger/LogTargetFactoryManager.java
  
  Index: LogTargetFactoryManager.java
  ===================================================================
  /*
   * Copyright (C) The Apache Software Foundation. All rights reserved.
   *
   * This software is published under the terms of the Apache Software License
   * version 1.1, a copy of which has been included  with this distribution in
   * the LICENSE.txt file.
   */
  package org.apache.avalon.excalibur.logger;
  
  /**
   * LogTargetFactoryManager Interface.
   *
   * @author <a href="mailto:giacomo@apache.org">Giacomo Pati</a>
   * @version CVS $Revision: 1.1 $ $Date: 2002/04/04 02:34:14 $
   * @since 4.0
   */
  public interface LogTargetFactoryManager
  {
      /**
       * Find a factory for LogTargets based on a name.
       */
      LogTargetFactory getLogTargetFactory( String factoryName );
  }
  
  
  
  1.1                  jakarta-avalon-excalibur/logger/src/java/org/apache/avalon/excalibur/logger/LogTargetManager.java
  
  Index: LogTargetManager.java
  ===================================================================
  /*
   * Copyright (C) The Apache Software Foundation. All rights reserved.
   *
   * This software is published under the terms of the Apache Software License
   * version 1.1, a copy of which has been included  with this distribution in
   * the LICENSE.txt file.
   */
  package org.apache.avalon.excalibur.logger;
  
  import org.apache.log.LogTarget;
  
  /**
   * LogTargetManager Interface.
   *
   * @author <a href="mailto:giacomo@apache.org">Giacomo Pati</a>
   * @version CVS $Revision: 1.1 $ $Date: 2002/04/04 02:34:14 $
   * @since 4.0
   */
  public interface LogTargetManager
  {
      /**
       * Find a logger based on a category name.
       */
      LogTarget getLogTarget( String targetId );
  }
  
  
  
  1.1                  jakarta-avalon-excalibur/logger/src/java/org/apache/avalon/excalibur/logger/LoggerManager.java
  
  Index: LoggerManager.java
  ===================================================================
  /*
   * Copyright (C) The Apache Software Foundation. All rights reserved.
   *
   * This software is published under the terms of the Apache Software License
   * version 1.1, a copy of which has been included  with this distribution in
   * the LICENSE.txt file.
   */
  package org.apache.avalon.excalibur.logger;
  
  import org.apache.avalon.framework.logger.Logger;
  
  /**
   * LoggerManager Interface.  This is the interface used to get instances of
   * a Logger for your system.
   *
   * @author <a href="mailto:bloritsch@apache.org">Berin Loritsch</a>
   * @version CVS $Revision: 1.1 $ $Date: 2002/04/04 02:34:15 $
   */
  public interface LoggerManager
  {
      /**
       * Return the Logger for the specified category.
       */
      Logger getLoggerForCategory( String categoryName );
  
      /**
       * Return the default Logger.  This is basically the same
       * as getting the Logger for the "" category.
       */
      Logger getDefaultLogger();
  }
  
  
  1.1                  jakarta-avalon-excalibur/logger/src/java/org/apache/avalon/excalibur/logger/package.html
  
  Index: package.html
  ===================================================================
  <html>
  <body>
  Logging utilities.
  </body>
  </html>
  
  
  
  1.1                  jakarta-avalon-excalibur/logger/src/java/org/apache/avalon/excalibur/logger/factory/AbstractTargetFactory.java
  
  Index: AbstractTargetFactory.java
  ===================================================================
  /*
   * Copyright (C) The Apache Software Foundation. All rights reserved.
   *
   * This software is published under the terms of the Apache Software License
   * version 1.1, a copy of which has been included  with this distribution in
   * the LICENSE.txt file.
   */
  package org.apache.avalon.excalibur.logger.factory;
  
  import org.apache.avalon.excalibur.logger.LogTargetFactory;
  import org.apache.avalon.framework.configuration.Configurable;
  import org.apache.avalon.framework.configuration.Configuration;
  import org.apache.avalon.framework.configuration.ConfigurationException;
  import org.apache.avalon.framework.context.Context;
  import org.apache.avalon.framework.context.ContextException;
  import org.apache.avalon.framework.context.Contextualizable;
  import org.apache.avalon.framework.logger.AbstractLogEnabled;
  import org.apache.log.LogTarget;
  
  /**
   * AbstractTargetFactory class.
   *
   * This factory implements basic functionality for LogTargetFactories
   *
   * @author <a href="mailto:giacomo@apache.org">Giacomo Pati</a>
   * @version CVS $Revision: 1.1 $ $Date: 2002/04/04 02:34:15 $
   * @since 4.0
   */
  public abstract class AbstractTargetFactory
      extends AbstractLogEnabled
      implements LogTargetFactory,
      Configurable,
      Contextualizable
  {
      public abstract LogTarget createTarget( Configuration configuration )
          throws ConfigurationException;
  
      /** The Configuration object */
      protected Configuration m_configuration;
  
      /** The Context object */
      protected Context m_context;
  
      /**
       * Get the Configuration object
       */
      public void configure( Configuration configuration )
          throws ConfigurationException
      {
          this.m_configuration = configuration;
      }
  
      /**
       * Get the Context object
       */
      public void contextualize( Context context )
          throws ContextException
      {
          this.m_context = context;
      }
  }
  
  
  
  1.1                  jakarta-avalon-excalibur/logger/src/java/org/apache/avalon/excalibur/logger/factory/AsyncLogTargetFactory.java
  
  Index: AsyncLogTargetFactory.java
  ===================================================================
  /*
   * Copyright (C) The Apache Software Foundation. All rights reserved.
   *
   * This software is published under the terms of the Apache Software License
   * version 1.1, a copy of which has been included  with this distribution in
   * the LICENSE.txt file.
   */
  package org.apache.avalon.excalibur.logger.factory;
  
  import org.apache.avalon.excalibur.logger.LogTargetFactory;
  import org.apache.avalon.excalibur.logger.LogTargetFactoryManageable;
  import org.apache.avalon.excalibur.logger.LogTargetFactoryManager;
  import org.apache.avalon.framework.configuration.Configuration;
  import org.apache.avalon.framework.configuration.ConfigurationException;
  import org.apache.log.LogTarget;
  import org.apache.log.output.AsyncLogTarget;
  
  /**
   * AsyncLogTargetFactory class.
   *
   * This factory creates LogTargets with a wrapped AsyncLogTarget around it:
   *
   * <pre>
   *
   * &lt;async-target id="target-id" queue-size=".." priority="MIN|NORM|MAX|n"&gt;
   *  &lt;any-target-definition/&gt;
   * &lt;/async-target&gt;
   *
   * </pre>
   * <p>
   *  This factory creates a AsyncLogTarget object with a specified queue-size
   *  attribute (which defaults to what the AsyncLogTarget uses if absent).
   *  The LogTarget to wrap is described in a child element of the configuration (in
   *  the sample above named as &lt;any-target-definition/&gt;).
   *  The Thread of the created AsyncLogTarget will have a priority specified by the
   *  priotity attribute (which defaults to Thread.MIN_PRIORITY). The priority values
   *  corresponds to those defined in the Thread class which are:
   * </p>
   * <p>
   * <blockquote>
   * MIN=Thread.MIN_PRIORITY<br>
   * NORM=Thread.NORM_PRIORITY<br>
   * MAX=Thread.MAX_PRIORITY<br>
   * number=priority number (see class java.lang.Thread)<br>
   * </blockquote>
   * </p>
   *
   * @author <a href="mailto:giacomo@apache.org">Giacomo Pati</a>
   * @version CVS $Revision: 1.1 $ $Date: 2002/04/04 02:34:15 $
   * @since 4.0
   */
  public final class AsyncLogTargetFactory
      extends AbstractTargetFactory
      implements LogTargetFactoryManageable
  {
      /** The LogTargetFactoryManager */
      protected LogTargetFactoryManager m_logTargetFactoryManager;
  
      /**
       * create a LogTarget based on a Configuration
       */
      public final LogTarget createTarget( final Configuration configuration )
          throws ConfigurationException
      {
          final int queuesize = configuration.getAttributeAsInteger( "queue-size", -1 );
          final Configuration config = configuration.getChildren()[ 0 ];
          final LogTargetFactory factory = m_logTargetFactoryManager.getLogTargetFactory( config.getName() );
          final LogTarget target = factory.createTarget( config );
          final AsyncLogTarget asyncTarget;
          if( queuesize == -1 )
          {
              asyncTarget = new AsyncLogTarget( target );
          }
          else
          {
              asyncTarget = new AsyncLogTarget( target, queuesize );
          }
  
          final String priority = configuration.getAttribute( "priority", null );
          final int threadPriority;
          if( "MIN".equalsIgnoreCase( priority ) )
          {
              threadPriority = Thread.MIN_PRIORITY;
          }
          else if( "NORM".equalsIgnoreCase( priority ) )
          {
              threadPriority = Thread.NORM_PRIORITY;
          }
          else if( "NORM".equalsIgnoreCase( priority ) )
          {
              threadPriority = Thread.NORM_PRIORITY;
          }
          else
          {
              threadPriority = configuration.getAttributeAsInteger( "priority", 1 );
          }
          final Thread thread = new Thread( asyncTarget );
          thread.setPriority( threadPriority );
          thread.setDaemon( true );
          thread.start();
          return asyncTarget;
      }
  
      /**
       * get the LogTargetFactoryManager
       */
      public final void setLogTargetFactoryManager( LogTargetFactoryManager logTargetFactoryManager )
      {
          m_logTargetFactoryManager = logTargetFactoryManager;
      }
  
  }
  
  
  
  
  1.1                  jakarta-avalon-excalibur/logger/src/java/org/apache/avalon/excalibur/logger/factory/DatagramTargetFactory.java
  
  Index: DatagramTargetFactory.java
  ===================================================================
  /*
   * Copyright (C) The Apache Software Foundation. All rights reserved.
   *
   * This software is published under the terms of the Apache Software License
   * version 1.1, a copy of which has been included  with this distribution in
   * the LICENSE file.
   */
  package org.apache.avalon.excalibur.logger.factory;
  
  import java.io.IOException;
  import java.net.InetAddress;
  import java.net.UnknownHostException;
  import org.apache.avalon.framework.configuration.Configuration;
  import org.apache.avalon.framework.configuration.ConfigurationException;
  import org.apache.log.LogTarget;
  import org.apache.log.format.ExtendedPatternFormatter;
  import org.apache.log.format.Formatter;
  import org.apache.log.format.PatternFormatter;
  import org.apache.log.format.RawFormatter;
  import org.apache.log.output.net.DatagramOutputTarget;
  
  /**
   * This factory creates LogTargets with a wrapped DatagramOutputTarget around it.
   * <p>
   * Configuration syntax:
   * <pre>
   * &lt;datagram-target id="target-id"&gt;
   *   &lt;address hostname="hostname" port="4455" /&gt;
   *     &lt;format type="extended"&gt;
   *                %7.7{priority} %23.23{time:yyyy-MM-dd HH:mm:ss:SSS} [%25.25{category}] : %{message}\n%{throwable}
   *     &lt;/format&gt;
   * &lt;/datagram-target&gt;
   * </pre>
   * </p>
   * <p>
   *  This factory creates a DatagramOutputTarget object which will
   *  sends datagrams to the specified address. The name of the target is specified by the hostname attribute
   *  of the &lt;address&gt; element and the port by the port attribute.The &lt;address&gt; element
   *  wraps the format to output the log.
   * </p>
   *
   *
   * @author <a href="mailto:rghorpade@onebridge.de"> Rajendra Ghorpade </a>
   */
  public class DatagramTargetFactory
      extends AbstractTargetFactory
  {
      /**  Default format */
      private static final String FORMAT =
          "%7.7{priority} %5.5{time}   [%8.8{category}] (%{context}): %{message}\\n%{throwable}";
  
      /**
       * Create a LogTarget based on a Configuration
       */
      public LogTarget createTarget( final Configuration conf )
          throws ConfigurationException
      {
          InetAddress address;
  
          final Configuration configChild = conf.getChild( "address", false );
          if( null == configChild )
          {
              throw new ConfigurationException( "target address not specified in the config" );
          }
  
          try
          {
              address = InetAddress.getByName( configChild.getAttribute( "hostname" ) );
          }
          catch( UnknownHostException uhex )
          {
              throw new ConfigurationException( "Host specified in datagram target adress is unknown!", uhex );
          }
  
          int port = configChild.getAttributeAsInteger( "port" );
  
          final Formatter formatter = getFormatter( conf.getChild( "format", false ) );
  
          try
          {
              return new DatagramOutputTarget( address, port, formatter );
          }
          catch( IOException ioex )
          {
              throw new ConfigurationException( "Failed to create target!", ioex );
          }
      }
  
      /**
       * Returns the Formatter
       *
       * @param conf Configuration for the formatter
       */
      protected Formatter getFormatter( final Configuration conf )
      {
          final String type = conf.getAttribute( "type", "pattern" );
          final String format = conf.getValue( FORMAT );
  
          if( "extended".equals( type ) )
          {
              return new ExtendedPatternFormatter( format );
          }
          else if( "raw".equals( type ) )
          {
              return new RawFormatter();
          }
  
          /**  default formatter */
          return new PatternFormatter( format );
      }
  }
  
  
  
  
  1.1                  jakarta-avalon-excalibur/logger/src/java/org/apache/avalon/excalibur/logger/factory/FileTargetFactory.java
  
  Index: FileTargetFactory.java
  ===================================================================
  /*
   * Copyright (C) The Apache Software Foundation. All rights reserved.
   *
   * This software is published under the terms of the Apache Software License
   * version 1.1, a copy of which has been included  with this distribution in
   * the LICENSE.txt file.
   */
  package org.apache.avalon.excalibur.logger.factory;
  
  import java.io.File;
  import java.io.IOException;
  import java.util.StringTokenizer;
  import org.apache.avalon.framework.configuration.Configuration;
  import org.apache.avalon.framework.configuration.ConfigurationException;
  import org.apache.avalon.framework.context.ContextException;
  import org.apache.log.LogTarget;
  import org.apache.log.format.Formatter;
  import org.apache.log.output.io.FileTarget;
  import org.apache.log.output.io.rotate.FileStrategy;
  import org.apache.log.output.io.rotate.OrRotateStrategy;
  import org.apache.log.output.io.rotate.RevolvingFileStrategy;
  import org.apache.log.output.io.rotate.RotateStrategy;
  import org.apache.log.output.io.rotate.RotateStrategyByDate;
  import org.apache.log.output.io.rotate.RotateStrategyBySize;
  import org.apache.log.output.io.rotate.RotateStrategyByTime;
  import org.apache.log.output.io.rotate.RotatingFileTarget;
  import org.apache.log.output.io.rotate.UniqueFileStrategy;
  
  /**
   * FileTargetFactory class.
   *
   * This factory is able to create different FileLogTargets according to the following
   * configuration syntax:
   *
   * <pre>
   * &lt;file id="foo"&gt;
   *  &lt;filename&gt;${context-key}/real-name/...&lt;/filename&gt;
   *  &lt;format type="raw|pattern|extended"&gt;pattern to be used if needed&lt;/format&gt;
   *  &lt;append&gt;true|false&lt;/append&gt;
   *  &lt;rotation type="revolving" init="5" max="10"&gt;
   *
   * or
   *
   *  &lt;rotation type="unique" pattern="yyyy-MM-dd-hh-mm-ss" suffix=".log"&gt;
   *   &lt;or&gt;
   *    &lt;size&gt;10000000&lt;/size&gt;
   *    &lt;time&gt;24:00:00&lt;/time&gt;
   *    &lt;time&gt;12:00:00&lt;/time&gt;
   *   &lt;/or&gt;
   *  &lt;/rotation&gt;
   * &lt;/file&gt;
   * </pre>
   *
   * <p>Some explanations about the Elements used in the configuration:</p>
   * <dl>
   *  <dt>&lt;filename&gt;</dt>
   *  <dd>
   *   This denotes the name of the file to log to. It can be constructed
   *   out of entries in the passed Context object as ${context-key}.
   *   This element is required.
   *  </dd>
   *  <dt>&lt;format&gt;</dt>
   *  <dd>
   *   The type attribute of the pattern element denotes the type of
   *   Formatter to be used and according to it the pattern to use for.
   *   This elements defaults to:
   *   <p>
   *    %7.7{priority} %5.5{time}   [%8.8{category}] (%{context}): %{message}\\n%{throwable}
   *   </p>
   *  </dd>
   *  <dt>&lt;append&gt;<dt>
   *  <dd>
   *   If the log file should be deleted every time the logger is creates
   *   (normally at the start of the applcation) or not and thus the log
   *   entries will be appended. This elements defaults to false.
   *  </dd>
   *  <dt>&lt;rotation&gt;</dt>
   *  <dd>
   *   This is an optional element.
   *   The type attribute determines which FileStrategy to user
   *   (revolving=RevolvingFileStrategy, unique=UniqueFileStrategy).
   *   The required init and max attribute are used to determine the initial and
   *   maximum rotation to use on a type="revolving" attribute.
   *   The optional pattern and suffix attribute are used to form filenames on
   *   a type="unique" attribute.
   *  </dd>
   *  <dt>&lt;or&gt;</dt>
   *  <dd>uses the OrRotateStrategy to combine the children</dd>
   *  <dt>&lt;size&gt;</dt>
   *  <dd>
   *   The number of bytes if no suffix used or kilo bytes (1024) if suffixed with
   *   'k' or mega bytes (1024k) if suffixed with 'm' when a file rotation should
   *   occur. It doesn't make sense to specify more than one.
   *  </dd>
   *  <dt>&lt;time&gt;</dt>
   *  <dd>
   *   The time as HH:MM:SS when a rotation should occur. If you like to rotate
   *   a logfile more than once a day put an &lt;or&gt; element immediately after the
   *   &lt;rotation&gt; element and specify the times (and one size, too) inside the
   *   &lt;or&gt; element.
   *  </dd>
   *  <dt>&lt;date&gt;</dt>
   *  <dd>
   *   Rotation occur when string formatted date changed. Specify date formatting pattern.
   *  </dd>
   * </dl>
   *
   * @author <a href="mailto:giacomo@apache.org">Giacomo Pati</a>
   * @version CVS $Revision: 1.1 $ $Date: 2002/04/04 02:34:15 $
   * @since 4.0
   */
  public class FileTargetFactory
      extends AbstractTargetFactory
  {
  
      /**
       * Create a LogTarget based on a Configuration
       */
      public final LogTarget createTarget( final Configuration configuration )
          throws ConfigurationException
      {
          final Configuration confFilename = configuration.getChild( "filename" );
          final String filename = getFilename( confFilename.getValue() );
  
          final Configuration confRotation = configuration.getChild( "rotation", false );
  
          final Configuration confFormat = configuration.getChild( "format" );
  
          final Configuration confAppend = configuration.getChild( "append" );
          final boolean append = confAppend.getValueAsBoolean( false );
  
          final LogTarget logtarget;
  
          final File file = new File( filename );
          final Formatter formatter = getFormatter( confFormat );
  
          try
          {
              if( null == confRotation )
              {
                  logtarget = new FileTarget( file, append, formatter );
              }
              else
              {
                  final Configuration confStrategy = confRotation.getChildren()[ 0 ];
                  final RotateStrategy rotateStrategy = getRotateStrategy( confStrategy );
                  final FileStrategy fileStrategy = getFileStrategy( confRotation, file );
  
                  logtarget =
                      new RotatingFileTarget( append, formatter, rotateStrategy, fileStrategy );
              }
          }
          catch( final IOException ioe )
          {
              throw new ConfigurationException( "cannot create FileTarget", ioe );
          }
  
          return logtarget;
      }
  
      private static final long SECOND = 1000;
      private static final long MINUTE = 60 * SECOND;
      private static final long HOUR = 60 * MINUTE;
      private static final long DAY = 24 * HOUR;
  
      private static final long KILOBYTE = 1000;
      private static final long MEGABYTE = 1000 * KILOBYTE;
  
      private RotateStrategy getRotateStrategy( final Configuration conf )
      {
          final String type = conf.getName();
  
          if( "or".equals( type ) )
          {
              final Configuration[] configurations = conf.getChildren();
              final int size = configurations.length;
  
              final RotateStrategy[] strategies = new RotateStrategy[ size ];
              for( int i = 0; i < size; i++ )
              {
                  strategies[ i ] = getRotateStrategy( configurations[ i ] );
              }
  
              return new OrRotateStrategy( strategies );
          }
  
          if( "size".equals( type ) )
          {
              final String value = conf.getValue( "2m" );
  
              final int count = value.length();
              final char end = value.charAt( count - 1 );
              final long no;
              final long size;
  
              switch( end )
              {
                  case 'm':
                      no = Long.parseLong( value.substring( 0, count - 1 ) );
                      size = no * MEGABYTE;
                      break;
                  case 'k':
                      no = Long.parseLong( value.substring( 0, count - 1 ) );
                      size = no * KILOBYTE;
                      break;
                  default:
                      size = Long.parseLong( value );
              }
  
              return new RotateStrategyBySize( size );
          }
  
          if( "date".equals( type ) )
          {
              final String value = conf.getValue( "yyyyMMdd" );
              return new RotateStrategyByDate( value );
          }
  
          // default rotate strategy
          final String value = conf.getValue( "24:00:00" );
  
          // interpret a string like: ddd:hh:mm:ss ...
          final StringTokenizer tokenizer = new StringTokenizer( value, ":" );
          final int count = tokenizer.countTokens();
          long time = 0;
          for( int i = count; i > 0; i-- )
          {
              final long no = Long.parseLong( tokenizer.nextToken() );
              if( 4 == i )
              {
                  time += no * DAY;
              }
              if( 3 == i )
              {
                  time += no * HOUR;
              }
              if( 2 == i )
              {
                  time += no * MINUTE;
              }
              if( 1 == i )
              {
                  time += no * SECOND;
              }
          }
  
          return new RotateStrategyByTime( time );
      }
  
      protected FileStrategy getFileStrategy( final Configuration conf, final File file )
      {
          final String type = conf.getAttribute( "type", "unique" );
  
          if( "revolving".equals( type ) )
          {
              final int initialRotation =
                  conf.getAttributeAsInteger( "init", 5 );
              final int maxRotation =
                  conf.getAttributeAsInteger( "max", 10 );
  
              return new RevolvingFileStrategy( file, initialRotation, maxRotation );
          }
  
          // default file strategy
          final String pattern = conf.getAttribute( "pattern", null );
          final String suffix = conf.getAttribute( "suffix", null );
          if( pattern == null )
          {
              return new UniqueFileStrategy( file );
          }
          else
          {
              if( suffix == null )
              {
                  return new UniqueFileStrategy( file, pattern );
              }
              else
              {
                  return new UniqueFileStrategy( file, pattern, suffix );
              }
          }
      }
  
      protected Formatter getFormatter( final Configuration conf )
      {
          Formatter formatter = null;
  
          if( null != conf )
          {
              final FormatterFactory formatterFactory = new FormatterFactory();
              formatter = formatterFactory.createFormatter( conf );
          }
  
          return formatter;
      }
  
      /**
       * Process the file name.
       *
       * This method scans the file name passed for occurrences of
       * ${foo}. These strings get replaced by values from the Context
       * object indexed by the name (here foo).
       *
       * @param rawFilename The filename with substitutable placeholders
       * @return The processed file name
       * @exception ConfigurationException if substitutable values are not in the
       * Context object.
       */
      protected final String getFilename( String rawFilename )
          throws ConfigurationException
      {
          StringBuffer sb = new StringBuffer();
          int i = 0;
          int j = -1;
          while( ( j = rawFilename.indexOf( "${", i ) ) > -1 )
          {
              if( m_context == null )
              {
                  throw new ConfigurationException( "Context not available." );
              }
              if( i < j )
              {
                  sb.append( rawFilename.substring( i, j ) );
              }
              int k = rawFilename.indexOf( '}', j );
              final String ctxName = rawFilename.substring( j + 2, k );
              final Object ctx;
              try
              {
                  ctx = m_context.get( ctxName );
              }
              catch( final ContextException ce )
              {
                  throw new ConfigurationException(
                      "missing entry '" + ctxName + "' in Context." );
              }
              sb.append( ctx.toString() );
              i = k + 1;
          }
          if( i < rawFilename.length() )
          {
              sb.append( rawFilename.substring( i, rawFilename.length() ) );
          }
          return sb.toString();
      }
  }
  
  
  
  
  1.1                  jakarta-avalon-excalibur/logger/src/java/org/apache/avalon/excalibur/logger/factory/FormatterFactory.java
  
  Index: FormatterFactory.java
  ===================================================================
  /*
   * FormatterFactory.java
   *
   * Created on August 29, 2001, 10:43 PM
   */
  
  package org.apache.avalon.excalibur.logger.factory;
  
  import org.apache.avalon.framework.configuration.Configuration;
  import org.apache.avalon.framework.logger.AvalonFormatter;
  import org.apache.log.format.ExtendedPatternFormatter;
  import org.apache.log.format.Formatter;
  import org.apache.log.format.PatternFormatter;
  import org.apache.log.format.RawFormatter;
  import org.apache.log.format.SyslogFormatter;
  import org.apache.log.format.XMLFormatter;
  
  /**
   * Factory for Formatter-s.
   */
  public class FormatterFactory
  {
  
      //Format of default formatter
      private static final String FORMAT =
          "%7.7{priority} %5.5{time}   [%8.8{category}] (%{context}): %{message}\\n%{throwable}";
  
      public Formatter createFormatter( final Configuration conf )
      {
          final String type = conf.getAttribute( "type", "pattern" );
          final String format = conf.getValue( FORMAT );
  
          if( "avalon".equals( type ) )
          {
              int depth = conf.getAttributeAsInteger( "depth", AvalonFormatter.DEFAULT_STACK_DEPTH );
              boolean printCascading = conf.getAttributeAsBoolean( "cascading", AvalonFormatter.DEFAULT_PRINT_CASCADING );
              return new AvalonFormatter( format, depth, printCascading );
          }
  
          if( "extended".equals( type ) )
          {
              return new ExtendedPatternFormatter( format );
          }
  
          if( "raw".equals( type ) )
          {
              return new RawFormatter();
          }
  
          if( "xml".equals( type ) )
          {
              return new XMLFormatter();
          }
  
          if( "syslog".equals( type ) )
          {
              return new SyslogFormatter();
          }
  
          // default formatter
          return new PatternFormatter( format );
      }
  
  }
  
  
  
  1.1                  jakarta-avalon-excalibur/logger/src/java/org/apache/avalon/excalibur/logger/factory/JDBCTargetFactory.java
  
  Index: JDBCTargetFactory.java
  ===================================================================
  /*
   * Copyright (C) The Apache Software Foundation. All rights reserved.
   *
   * This software is published under the terms of the Apache Software License
   * version 1.1, a copy of which has been included  with this distribution in
   * the LICENSE.txt file.
   */
  package org.apache.avalon.excalibur.logger.factory;
  
  import javax.naming.Context;
  import javax.naming.InitialContext;
  import javax.naming.NamingException;
  import javax.sql.DataSource;
  import org.apache.avalon.excalibur.logger.LogTargetFactory;
  import org.apache.avalon.framework.configuration.Configuration;
  import org.apache.avalon.framework.configuration.ConfigurationException;
  import org.apache.log.LogTarget;
  import org.apache.log.output.db.ColumnInfo;
  import org.apache.log.output.db.ColumnType;
  import org.apache.log.output.db.DefaultJDBCTarget;
  import org.apache.log.output.db.NormalizedJDBCTarget;
  
  /**
   * Factory for JDBCLogTarget-s. The configuration looks like this:
   *
   * <pre>
   *  &lt;jdbc id="database"&gt;
   *      &lt;datasource&gt;java:/LogTargetDataSource&lt;/datasource&gt;
   *      &lt;normalized&gt;true&lt;/normalized&gt;
   *      &lt;table name="LOG"&gt;
   *         &lt;sequence&gt;ID&lt;/sequence&gt;
   *          &lt;category&gt;CATEGORY&lt;/category&gt;
   *          &lt;priority&gt;PRIORITY&lt;/priority&gt;
   *          &lt;message&gt;MESSAGE&lt;/message&gt;
   *          &lt;time&gt;TIME&lt;/time&gt;
   *          &lt;rtime&gt;RTIME&lt;/rtime&gt;
   *          &lt;throwable&gt;THROWABLE&lt;/throwable&gt;
   *          &lt;hostname&gt;HOSTNAME&lt;/hostname&gt;
   *          &lt;static aux="-"&gt;STATIC&lt;/static&gt;
   *          &lt;context aux="principal"&gt;PRINCIPAL&lt;/context&gt;
   *          &lt;context aux="ipaddress"&gt;IPADDRESS&lt;/context&gt;
   *          &lt;context aux="username"&gt;USERNAME&lt;/context&gt;
   *      &lt;/table&gt;
   *  &lt;/jdbc&gt;
   * </pre>
   *
   * @author <a href="mailto:mirceatoma@home.com">Mircea Toma</a>;
   * @version CVS $Revision: 1.1 $ $Date: 2002/04/04 02:34:15 $
   */
  public class JDBCTargetFactory implements LogTargetFactory
  {
      public LogTarget createTarget( Configuration configuration )
          throws ConfigurationException
      {
          final String dataSourceName =
              configuration.getChild( "datasource", true ).getValue();
  
          final boolean normalized =
              configuration.getChild( "normalized", true ).getValueAsBoolean( false );
  
          final Configuration tableConfiguration =
              configuration.getChild( "table" );
  
          final String table = tableConfiguration.getAttribute( "name" );
  
          final Configuration[] conf = tableConfiguration.getChildren();
          final ColumnInfo[] columns = new ColumnInfo[ conf.length ];
  
          for( int i = 0; i < conf.length; i++ )
          {
              final String name = conf[ i ].getValue();
              final int type = ColumnType.getTypeIdFor( conf[ i ].getName() );
              final String aux = conf[ i ].getAttribute( "aux", null );
  
              columns[ i ] = new ColumnInfo( name, type, aux );
          }
  
          final DataSource dataSource;
  
          try
          {
              Context ctx = new InitialContext();
              dataSource = (DataSource)ctx.lookup( dataSourceName );
          }
          catch( final NamingException ne )
          {
              throw new ConfigurationException( "Cannot lookup data source", ne );
          }
  
          final LogTarget logTarget;
          if( normalized )
          {
              logTarget = new NormalizedJDBCTarget( dataSource, table, columns );
          }
          else
          {
              logTarget = new DefaultJDBCTarget( dataSource, table, columns );
          }
  
          return logTarget;
      }
  }
  
  
  
  1.1                  jakarta-avalon-excalibur/logger/src/java/org/apache/avalon/excalibur/logger/factory/JMSTargetFactory.java
  
  Index: JMSTargetFactory.java
  ===================================================================
  /*
   * JMSTopicTargetFactory.java
   *
   * Created on August 26, 2001, 5:17 PM
   */
  
  package org.apache.avalon.excalibur.logger.factory;
  
  import javax.jms.ConnectionFactory;
  import javax.jms.Destination;
  import javax.jms.Queue;
  import javax.jms.QueueConnectionFactory;
  import javax.jms.Topic;
  import javax.jms.TopicConnectionFactory;
  import javax.naming.Context;
  import javax.naming.InitialContext;
  import javax.naming.NameNotFoundException;
  import javax.naming.NamingException;
  import org.apache.avalon.excalibur.logger.LogTargetFactory;
  import org.apache.avalon.framework.configuration.Configuration;
  import org.apache.avalon.framework.configuration.ConfigurationException;
  import org.apache.log.LogTarget;
  import org.apache.log.format.Formatter;
  import org.apache.log.output.jms.JMSQueueTarget;
  import org.apache.log.output.jms.JMSTopicTarget;
  import org.apache.log.output.jms.MessageBuilder;
  import org.apache.log.output.jms.ObjectMessageBuilder;
  import org.apache.log.output.jms.PropertyInfo;
  import org.apache.log.output.jms.PropertyType;
  import org.apache.log.output.jms.TextMessageBuilder;
  
  /**
   * Factory for JMS LogTarget-s. The configuration looks like this:
   *
   * <pre>
   *   &lt;jms id="name"&gt;
   *           &lt;connection-factory&gt;java:/TopicConectionFactory&lt;/connection-factory&gt;
   *           &lt;destination type="topic|queue"&gt;jms/LogDestination&lt;/destination&gt;
   *           &lt;message type="object|text"&gt;
   *
   * -if type="text":
   *                   &lt;property&gt;
   *                           &lt;category&gt;CATEGORY&lt;/category&gt;
   *                           &lt;priority&gt;PRIORITY&lt;/priority&gt;
   *                           &lt;time&gt;TIME&lt;/time&gt;
   *                           &lt;rtime&gt;RTIME&lt;/rtime&gt;
   *                           &lt;throwable&gt;THROWABLE&lt;/throwable&gt;
   *                           &lt;hostname&gt;HOSTNAME&lt;/hostname&gt;
   *                           &lt;static aux="234523454325"&gt;SYSTEM&lt;/static&gt;
   *                           &lt;context aux="principal"&gt;PRINCIPAL&lt;/context&gt;
   *                           &lt;context aux="ipaddress"&gt;IPADDRESS&lt;/context&gt;
   *                           &lt;context aux="username"&gt;USERNAME&lt;/context&gt;
   *                   &lt;/property&gt;
   *                   &lt;format type="exteded"&gt;%7.7{priority} %5.5{time}   [%8.8{category}] (%{context}): %{message}\n%{throwable}&lt;/format&gt;
   *           &lt;/message&gt;
   *   &lt;/jms&gt;
   * </pre>
   *
   * @author <a href="mailto:mirceatoma@home.com">Mircea Toma</a>;
   * @version CVS $Revision: 1.1 $ $Date: 2002/04/04 02:34:15 $
   */
  public class JMSTargetFactory implements LogTargetFactory
  {
  
      public LogTarget createTarget( final Configuration configuration )
          throws ConfigurationException
      {
          final String factoryName =
              configuration.getChild( "connection-factory", true ).getValue();
  
          final Configuration destinationConf =
              configuration.getChild( "destination", true );
  
          final String destinationName = destinationConf.getValue();
          final String destinationType =
              destinationConf.getAttribute( "type", "topic" );
  
          final Configuration messageConf =
              configuration.getChild( "message", true );
  
          final MessageBuilder messageBuilder = getMessageBuilder( messageConf );
          final ConnectionFactory factory;
          final Destination destination;
          final LogTarget logTarget;
  
          try
          {
              Context ctx = new InitialContext();
              factory = (ConnectionFactory)ctx.lookup( factoryName );
              destination = (Destination)ctx.lookup( destinationName );
          }
          catch( NameNotFoundException nnfe )
          {
              throw new ConfigurationException( "Cannot lookup object", nnfe );
          }
          catch( NamingException ne )
          {
              throw new ConfigurationException( "Cannot get naming context", ne );
          }
  
          if( "queue".equals( destinationType ) )
          {
              logTarget = new JMSQueueTarget( messageBuilder,
                                              (QueueConnectionFactory)factory, (Queue)destination );
          }
          else
          {
              logTarget = new JMSTopicTarget( messageBuilder,
                                              (TopicConnectionFactory)factory, (Topic)destination );
          }
  
          return logTarget;
      }
  
      private MessageBuilder getMessageBuilder( final Configuration configuration )
          throws ConfigurationException
      {
          final String messageType = configuration.getAttribute( "type", "object" );
  
          if( "text".equals( messageType ) )
          {
              final Configuration[] propertyConf =
                  configuration.getChild( "property", true ).getChildren();
              final Configuration formatterConf = configuration.getChild( "format" );
  
              final PropertyInfo[] properties = new PropertyInfo[ propertyConf.length ];
  
              for( int i = 0; i < properties.length; i++ )
              {
                  final String name = propertyConf[ i ].getValue();
                  final int type = PropertyType.getTypeIdFor( propertyConf[ i ].getName() );
                  final String aux = propertyConf[ i ].getAttribute( "aux", null );
  
                  properties[ i ] = new PropertyInfo( name, type, aux );
              }
  
              final Formatter formatter = getFormatter( formatterConf );
  
              return new TextMessageBuilder( properties, formatter );
          }
  
          return new ObjectMessageBuilder();
      }
  
      protected Formatter getFormatter( final Configuration conf )
      {
          Formatter formatter = null;
  
          if( null != conf )
          {
              final FormatterFactory formatterFactory = new FormatterFactory();
              formatter = formatterFactory.createFormatter( conf );
          }
  
          return formatter;
      }
  }
  
  
  
  1.1                  jakarta-avalon-excalibur/logger/src/java/org/apache/avalon/excalibur/logger/factory/PriorityFilterTargetFactory.java
  
  Index: PriorityFilterTargetFactory.java
  ===================================================================
  /*
   * Copyright (C) The Apache Software Foundation. All rights reserved.
   *
   * This software is published under the terms of the Apache Software License
   * version 1.1, a copy of which has been included  with this distribution in
   * the LICENSE.txt file.
   */
  package org.apache.avalon.excalibur.logger.factory;
  
  import org.apache.avalon.excalibur.logger.LogTargetFactory;
  import org.apache.avalon.excalibur.logger.LogTargetFactoryManageable;
  import org.apache.avalon.excalibur.logger.LogTargetFactoryManager;
  import org.apache.avalon.framework.configuration.Configuration;
  import org.apache.avalon.framework.configuration.ConfigurationException;
  import org.apache.log.LogTarget;
  import org.apache.log.Priority;
  import org.apache.log.filter.PriorityFilter;
  
  /**
   * PriorityFilterTargetFactory class.
   *
   * This factory creates LogTargets with a wrapped PriorityFilter around it:
   *
   * <pre>
   *
   * &lt;priority-filter id="target-id" log-level="ERROR"&gt;
   *  &lt;any-target-definition/&gt;
   *  ...
   *  &lt;any-target-definition/&gt;
   * &lt;/priority-filter&gt;
   *
   * </pre>
   * <p>
   *  This factory creates a PriorityFilter object with a logging Priority set
   *  to the value of the log-level attribute (which defaults to INFO if absent).
   *  The LogTarget to filter is described in child elements of the configuration (in
   *  the sample above named as &lt;any-target-definition/&gt;).
   * </p>
   *
   * @author <a href="mailto:giacomo@apache.org">Giacomo Pati</a>
   * @version CVS $Revision: 1.1 $ $Date: 2002/04/04 02:34:15 $
   * @since 4.0
   */
  public final class PriorityFilterTargetFactory
      extends AbstractTargetFactory
      implements LogTargetFactoryManageable
  {
      /** The LogTargetFactoryManager */
      protected LogTargetFactoryManager m_logTargetFactoryManager;
  
      /**
       * create a LogTarget based on a Configuration
       */
      public final LogTarget createTarget( final Configuration configuration )
          throws ConfigurationException
      {
          final String loglevel = configuration.getAttribute( "log-level", "INFO" );
          getLogger().debug( "loglevel is " + loglevel );
          final PriorityFilter filter = new PriorityFilter( Priority.getPriorityForName( loglevel ) );
  
          final Configuration[] configs = configuration.getChildren();
          for( int i = 0; i < configs.length; i++ )
          {
              final LogTargetFactory factory = m_logTargetFactoryManager.getLogTargetFactory( configs[ i ].getName() );
              getLogger().debug( "creating target " + configs[ i ].getName() + ": " + configs[ i ].toString() );
              final LogTarget logtarget = factory.createTarget( configs[ i ] );
              filter.addTarget( logtarget );
          }
          return filter;
      }
  
      /**
       * get the LogTargetFactoryManager
       */
      public final void setLogTargetFactoryManager( LogTargetFactoryManager logTargetFactoryManager )
      {
          m_logTargetFactoryManager = logTargetFactoryManager;
      }
  
  }
  
  
  
  
  1.1                  jakarta-avalon-excalibur/logger/src/java/org/apache/avalon/excalibur/logger/factory/ServletTargetFactory.java
  
  Index: ServletTargetFactory.java
  ===================================================================
  /*
   * Copyright (C) The Apache Software Foundation. All rights reserved.
   *
   * This software is published under the terms of the Apache Software License
   * version 1.1, a copy of which has been included  with this distribution in
   * the LICENSE.txt file.
   */
  package org.apache.avalon.excalibur.logger.factory;
  
  import javax.servlet.ServletContext;
  import org.apache.avalon.framework.configuration.Configuration;
  import org.apache.avalon.framework.configuration.ConfigurationException;
  import org.apache.avalon.framework.context.ContextException;
  import org.apache.log.LogTarget;
  import org.apache.log.format.Formatter;
  import org.apache.log.output.ServletOutputLogTarget;
  
  /**
   * ServletTargetFactory class.
   *
   * This factory creates a ServletOutputLogTargets. It uses the
   * context-key attribute to locate the required ServletContext from
   * the Context object passed to this factory.  The default context-key
   * is <code>servlet-context</code>.
   *
   * <pre>
   *
   * &lt;servlet id="target-id" context-key="context-key-to-servlet-context-object"&gt;
   *  &lt;format type="raw|pattern|extended"&gt;pattern to be used if needed&lt;/format&gt;
   * &lt;/servlet&gt;
   *
   * </pre>
   * <dl>
   *  <dt>&lt;format&gt;</dt>
   *  <dd>
   *   The type attribute of the pattern element denotes the type of
   *   Formatter to be used and according to it the pattern to use for.
   *   This elements defaults to:
   *   <p>
   *    %7.7{priority} %5.5{time}   [%8.8{category}] (%{context}): %{message}\\n%{throwable}
   *   </p>
   *  </dd>
   * </dl>
   *
   * @author <a href="mailto:giacomo@apache.org">Giacomo Pati</a>
   * @version CVS $Revision: 1.1 $ $Date: 2002/04/04 02:34:15 $
   * @since 4.0
   */
  public final class ServletTargetFactory
      extends AbstractTargetFactory
  {
  
      /**
       * create a LogTarget based on a Configuration
       */
      public final LogTarget createTarget( final Configuration configuration )
          throws ConfigurationException
      {
          if( m_context == null )
          {
              throw new ConfigurationException( "Context not available." );
          }
          final String contextkey =
              m_configuration.getAttribute( "context-key", "servlet-context" );
          final ServletContext sctx;
  
          final Configuration confFormat = configuration.getChild( "format" );
          final Formatter formatter = getFormatter( confFormat );
  
          try
          {
              sctx = (ServletContext)m_context.get( contextkey );
          }
          catch( final ContextException ce )
          {
              throw new ConfigurationException( "Cannot find ServletContext object in " +
                                                "application context", ce );
          }
  
          return new ServletOutputLogTarget( sctx );
      }
  
      protected Formatter getFormatter( final Configuration conf )
      {
          Formatter formatter = null;
  
          if( null != conf )
          {
              final FormatterFactory formatterFactory = new FormatterFactory();
              formatter = formatterFactory.createFormatter( conf );
          }
  
          return formatter;
      }
  }
  
  
  
  1.1                  jakarta-avalon-excalibur/logger/src/java/org/apache/avalon/excalibur/logger/factory/SocketTargetFactory.java
  
  Index: SocketTargetFactory.java
  ===================================================================
  package org.apache.avalon.excalibur.logger.factory;
  
  import java.io.IOException;
  import java.net.InetAddress;
  import java.net.UnknownHostException;
  import org.apache.avalon.framework.configuration.Configuration;
  import org.apache.avalon.framework.configuration.ConfigurationException;
  import org.apache.log.LogTarget;
  import org.apache.log.output.net.SocketOutputTarget;
  
  /**
   * This factory creates LogTargets with a wrapped SocketOutputTarget around it.
   * <p>
   * Configuration syntax:
   * <pre>
   * &lt;socket-target id="target-id"&gt;
   *   &lt;address hostname="hostname" port="4455" /&gt;
   * &lt;/socket-target&gt;
   * </pre>
   * </p>
   * <p>
   *  This factory creates a SocketOutputTarget object which will
   *  TCP/IP socket to communicate with the server. The name of the target is specified by the
   *  hostname attribute of the &lt;address&gt; element and the port by the port attribute.
   *  In the config file above the formatting for the log messages is not embedded as it should
   *  be specified on the server side
   * </p>
   *
   *
   * @author <a href="mailto:rghorpade@onebridge.de"> Rajendra Ghorpade </a>
   */
  public class SocketTargetFactory extends AbstractTargetFactory
  {
  
      /**
       * Creates a log target based on Configuration
       *
       *@param conf Configuration requied for creating the log target
       *@exception ConfigurationException if something goes wrong while reading from
       *          configuration
       */
      public LogTarget createTarget( final Configuration conf )
          throws ConfigurationException
      {
          final InetAddress address;
  
          final Configuration configChild = conf.getChild( "address", false );
          if( null == configChild )
          {
              throw new ConfigurationException( "target address not specified in the config" );
          }
  
          try
          {
              address = InetAddress.getByName( configChild.getAttribute( "hostname" ) );
          }
          catch( UnknownHostException uhex )
          {
              throw new ConfigurationException( "Host specified in socket target adress is unknown!", uhex );
          }
  
          final int port = configChild.getAttributeAsInteger( "port" );
  
          try
          {
              return new SocketOutputTarget( address, port );
          }
          catch( final IOException ioex )
          {
              throw new ConfigurationException( "Failed to create target!", ioex.fillInStackTrace() );
          }
      }
  }
  
  
  
  1.1                  jakarta-avalon-excalibur/logger/src/java/org/apache/avalon/excalibur/logger/factory/StreamTargetFactory.java
  
  Index: StreamTargetFactory.java
  ===================================================================
  /*
   * Copyright (C) The Apache Software Foundation. All rights reserved.
   *
   * This software is published under the terms of the Apache Software License
   * version 1.1, a copy of which has been included  with this distribution in
   * the LICENSE.txt file.
   */
  package org.apache.avalon.excalibur.logger.factory;
  
  import java.io.OutputStream;
  import org.apache.avalon.framework.configuration.Configuration;
  import org.apache.avalon.framework.configuration.ConfigurationException;
  import org.apache.avalon.framework.context.Context;
  import org.apache.avalon.framework.context.ContextException;
  import org.apache.avalon.framework.context.Contextualizable;
  import org.apache.avalon.framework.context.DefaultContext;
  import org.apache.log.LogTarget;
  import org.apache.log.format.Formatter;
  import org.apache.log.output.io.StreamTarget;
  
  /**
   * TargetFactory for {@link org.apache.log.output.io.StreamTarget}.
   *
   * This factory is able to create different StreamTargets according to the following
   * configuration syntax:
   * <pre>
   * &lt;stream id="foo"&gt;
   *  &lt;stream&gt;<i>stream-context-name</i>&lt;/stream&gt;
   *  &lt;format type="<i>raw|pattern|extended</i>"&gt;<i>pattern to be used if needed</i>&lt;/format&gt;
   * &lt;/stream&gt;
   * </pre>
   *
   * <p>The "stream-context-name" is the name of an <code>java.io.OutputStream</code> that
   * is fetched in the context. This context contains two predefined streams :
   * <li>"<code>System.out</code>" for the system output stream,</li>
   * <li>"<code>System.err</code>" for the system error stream.</li>
   * </p>
   *
   * <p>The syntax of "format" is the same as in <code>FileTargetFactory</code>.</p>
   *
   * @author <a href="mailto:sylvain@apache.org">Sylvain Wallez</a>
   * @version CVS $Revision: 1.1 $ $Date: 2002/04/04 02:34:15 $
   */
  public class StreamTargetFactory
      extends AbstractTargetFactory
      implements Contextualizable
  {
  
      /**
       * Create a LogTarget based on a Configuration
       */
      public LogTarget createTarget( final Configuration configuration )
          throws ConfigurationException
      {
          OutputStream stream;
  
          final Configuration streamConfig = configuration.getChild( "stream", false );
          if( null == streamConfig )
          {
              stream = System.err;
          }
          else
          {
              final String streamName = streamConfig.getValue();
              try
              {
                  stream = (OutputStream)m_context.get( streamName );
              }
              catch( Exception e )
              {
                  throw new ConfigurationException( "Error resolving stream '" +
                                                    streamName + "' at " +
                                                    streamConfig.getLocation(), e );
              }
          }
  
          final Configuration formatterConf = configuration.getChild( "format" );
          final Formatter formatter = getFormatter( formatterConf );
  
          return new StreamTarget( stream, formatter );
      }
  
      public void contextualize( final Context context )
          throws ContextException
      {
          // Add System output streams
          final DefaultContext newContext = new DefaultContext( context );
  
          newContext.put( "System.out", System.out );
          newContext.put( "System.err", System.err );
  
          super.contextualize( newContext );
      }
  
      protected Formatter getFormatter( final Configuration conf )
      {
          Formatter formatter = null;
  
          if( null != conf )
          {
              final FormatterFactory formatterFactory = new FormatterFactory();
              formatter = formatterFactory.createFormatter( conf );
          }
  
          return formatter;
      }
  }
  
  
  
  
  1.1                  jakarta-avalon-excalibur/logger/src/test/org/apache/avalon/excalibur/logger/test/LogKitManagementTest.java
  
  Index: LogKitManagementTest.java
  ===================================================================
  /*
   * Copyright (C) The Apache Software Foundation. All rights reserved.
   *
   * This software is published under the terms of the Apache Software License
   * version 1.1, a copy of which has been included  with this distribution in
   * the LICENSE.txt file.
   */
  package org.apache.avalon.excalibur.logger.test;
  
  import java.io.InputStream;
  import org.apache.avalon.excalibur.logger.DefaultLogKitManager;
  import org.apache.avalon.excalibur.logger.LogKitManager;
  import org.apache.avalon.framework.configuration.Configuration;
  import org.apache.avalon.framework.configuration.DefaultConfigurationBuilder;
  import org.apache.avalon.framework.context.Context;
  import org.apache.avalon.framework.context.DefaultContext;
  import org.apache.avalon.framework.logger.LogKitLogger;
  import org.apache.log.Hierarchy;
  import org.apache.log.LogTarget;
  import org.apache.log.Logger;
  import org.apache.log.Priority;
  import org.apache.log.format.PatternFormatter;
  import org.apache.log.output.io.StreamTarget;
  
  /**
   * LogKitManagementTest.
   *
   * @author <a href="mailto:giacomo@apache,org">Giacomo Pati</a>
   * @version CVS $Revision: 1.1 $ $Date: 2002/04/04 02:34:16 $
   */
  public class LogKitManagementTest
  {
      ///Format of default formatter
      private static final String FORMAT =
          "%7.7{priority} %5.5{time}   [%8.8{category}] (%{context}): %{message}\\n%{throwable}";
  
      //The default logger
      private Logger m_logger;
  
      protected Priority m_logPriority = Priority.DEBUG;
      protected LogKitManager m_lkm;
  
      public static void main( String[] args ) throws Exception
      {
          LogKitManagementTest lkmt = new LogKitManagementTest();
          lkmt.initialize();
          lkmt.test();
          lkmt.dispose();
      }
  
      protected void test()
      {
          Logger log1 = m_lkm.getLogger( "cocoon" );
          log1.debug( "this is the cocoon logger" );
          log1.info( "this is the cocoon logger" );
          log1.info( "this is the cocoon logger" );
          Logger log2 = log1.getChildLogger( "classloader" );
          log2.debug( "this is the childlogger classloader of the cocoon logger" );
          log2.info( "this is the childlogger classloader of the cocoon logger" );
          Logger log3 = m_lkm.getLogger( "cocoon.classloader" );
          log3.debug( "this is the cocoon.classloader logger" );
          log3.info( "this is the cocoon.classloader logger" );
          Logger log4 = m_lkm.getLogger( "foo" );
          log4.debug( "this is the foo logger" );
          log4.info( "this is the foo logger" );
      }
  
      /** Return the logger */
      protected Logger getLogger()
      {
          return m_logger;
      }
  
      /**
       * Initializes the ComponentManager
       *
       * The configuration file is determined by the class name plus .xtest appended,
       * all '.' replaced by '/' and loaded as a resource via classpath
       */
      protected void initialize()
          throws Exception
      {
          final String resourceName = this.getClass().getName().replace( '.', '/' ) + ".xtest";
          System.out.println( "ResourceName = " + resourceName );
          initialize( this.getClass().getClassLoader().getResource( resourceName ).openStream() );
      }
  
      /**
       * Initializes the ComponentManager
       *
       * @param testconf The configuration file is passed as a <code>InputStream</code>     *
       * A common way to supply a InputStream is to overwrite the initialize() method
       * in the sub class, do there whatever is needed to get the right InputStream object
       * supplying a conformant xtest configuartion and pass it to this initialize method.
       * the mentioned initialize method is also the place to set a different logging priority
       * to the member variable m_logPriority.
       */
      protected final void initialize( final InputStream testconf )
          throws Exception
      {
          m_logger = setupLogger();
          m_logger.debug( "LogKitManagementTest.initialize" );
  
          final DefaultConfigurationBuilder builder = new DefaultConfigurationBuilder();
          final Configuration conf = builder.build( testconf );
          final Context context = setupContext( conf.getChild( "context" ) );
  
          final DefaultLogKitManager lkm = new DefaultLogKitManager();
          lkm.enableLogging( new LogKitLogger( m_logger ) );
          lkm.contextualize( context );
          lkm.configure( conf );
          m_lkm = lkm;
      }
  
      /**
       * Disposes the <code>ComponentManager</code>
       */
      final private void dispose()
      {
      }
  
      /**
       * Set up logger configuration
       */
      private Logger setupLogger()
          throws Exception
      {
          //FIXME(GP): This method should setup a LogConfigurator and LogManager
          //           according to the configuration spec. not yet completed/implemented
          //           It will return a default logger for now.
          final Logger logger = Hierarchy.getDefaultHierarchy().getLoggerFor( "" );
          logger.setPriority( m_logPriority );
  
          final PatternFormatter formatter = new PatternFormatter( FORMAT );
          final StreamTarget target = new StreamTarget( System.out, formatter );
          logger.setLogTargets( new LogTarget[]{target} );
  
          return logger;
      }
  
      /**
       * set up a context according to the xtest configuration specifications context
       * element.
       *
       * A method addContext(DefaultContext context) is called here to enable subclasses
       * to put additional objects into the context programmatically.
       */
      private Context setupContext( final Configuration configuration )
          throws Exception
      {
          //FIXME(GP): This method should setup the Context object according to the
          //           configuration spec. not yet completed
          final DefaultContext context = new DefaultContext();
          return ( context );
      }
  }
  
  
  
  1.1                  jakarta-avalon-excalibur/logger/src/test/org/apache/avalon/excalibur/logger/test/LogKitManagementTest.xtest
  
  Index: LogKitManagementTest.xtest
  ===================================================================
  <?xml version="1.0"?>
  
  <logkit>
    <factories>
      <factory type="file" class="org.apache.avalon.excalibur.logger.factory.FileTargetFactory"/>
      <!--
      <factory type="property-filter" class="org.apache.avalon.excalibur.logger.factory.FilterTargetFactory"/>
      <factory type="servlet" class="org.apache.avalon.excalibur.logger.factory.ServletTargetFactory"/>
      -->
    </factories>
  
    <targets>
      <file id="root">
        <filename>logs/main.log</filename>
        <format type="extended">%7.7{priority} %5.5{time}   [%8.8{category}] (%{context}): %{message}\n%{throwable}</format>
        <append>true</append>
      </file>
      <file id="classloader">
        <filename>logs/classloader.log</filename>
        <format type="raw"/>
      </file>
      <file id="foo">
        <filename>logs/foo.log</filename>
        <format type="pattern">%7.7{priority} %5.5{time}: %{message}\n%{throwable}</format>
      </file>
      <!--
      <priority-filter id="servlet" log-level="ERROR">
        <servlet/>
      </priority-filter>
      -->
    </targets>
  
    <categories>
      <category name="cocoon" log-level="INFO">
        <log-target id-ref="root"/>
        <!--
        <log-target id-ref="servlet"/>
        -->
  
        <category name="classloader" log-level="DEBUG">
          <log-target id-ref="classloader"/>
        </category>
      </category>
      <category name="foo" log-level="INFO">
        <log-target id-ref="foo"/>
      </category>
    </categories>
  </logkit>
  
  
  
  1.1                  jakarta-avalon-excalibur/logger/src/test/org/apache/avalon/excalibur/logger/test/LogKitManagementTestCase.java
  
  Index: LogKitManagementTestCase.java
  ===================================================================
  /*
   * Copyright (C) The Apache Software Foundation. All rights reserved.
   *
   * This software is published under the terms of the Apache Software License
   * version 1.1, a copy of which has been included  with this distribution in
   * the LICENSE.txt file.
   */
  package org.apache.avalon.excalibur.logger.test;
  
  import junit.swingui.TestRunner;
  import org.apache.avalon.excalibur.testcase.CascadingAssertionFailedError;
  import org.apache.avalon.excalibur.testcase.ExcaliburTestCase;
  
  /**
   * LogKitManagementTest.
   *
   * @author <a href="mailto:giacomo@apache,org">Giacomo Pati</a>
   * @version CVS $Revision: 1.1 $ $Date: 2002/04/04 02:34:16 $
   */
  public class LogKitManagementTestCase
      extends ExcaliburTestCase
  {
  
      public static void main( final String[] args ) throws Exception
      {
          final String[] testCaseName = {LogKitManagementTestCase.class.getName()};
          TestRunner.main( testCaseName );
      }
  
      public LogKitManagementTestCase( final String name )
      {
          super( name );
  
          // Set the priority for default log output.
          m_logPriority = org.apache.log.Priority.INFO;
      }
  
      public void testComponent()
          throws CascadingAssertionFailedError
      {
          TestComponent tc = null;
  
          try
          {
              tc = (TestComponent)manager.lookup( TestComponent.ROLE + "/A" );
              tc.test( getLogEnabledLogger(), "Test log entry A" );
          }
          catch( Exception e )
          {
              throw new CascadingAssertionFailedError( "There was an error in the LogKitManagement test", e );
          }
          finally
          {
              assertTrue( "The test component could not be retrieved.", null != tc );
              manager.release( tc );
          }
  
          try
          {
              tc = (TestComponent)manager.lookup( TestComponent.ROLE + "/B" );
              tc.test( getLogEnabledLogger(), "Test log entry B" );
          }
          catch( Exception e )
          {
              throw new CascadingAssertionFailedError( "There was an error in the LogKitManagement test", e );
          }
          finally
          {
              assertTrue( "The test component could not be retrieved.", null != tc );
              manager.release( tc );
          }
  
          try
          {
              tc = (TestComponent)manager.lookup( TestComponent.ROLE + "/C" );
              tc.test( getLogEnabledLogger(), "Test log entry C" );
          }
          catch( Exception e )
          {
              throw new CascadingAssertionFailedError( "There was an error in the LogKitManagement test", e );
          }
          finally
          {
              assertTrue( "The test component could not be retrieved.", null != tc );
              manager.release( tc );
          }
      }
  }
  
  
  
  1.1                  jakarta-avalon-excalibur/logger/src/test/org/apache/avalon/excalibur/logger/test/LogKitManagementTestCase.xtest
  
  Index: LogKitManagementTestCase.xtest
  ===================================================================
  <?xml version="1.0"?>
  
  <testcase>
    <annotation>
      <title>LogKitManagement tests</title>
      <para>
        Simple tests of the LogKitManagement system
      </para>
    </annotation>
    <logkit>
      <factories>
        <factory type="file" class="org.apache.avalon.excalibur.logger.factory.FileTargetFactory"/>
        <factory type="priority-filter" class="org.apache.avalon.excalibur.logger.factory.PriorityFilterTargetFactory"/>
      </factories>
  
      <targets>
        <file id="root">
          <filename>lolo/${current-dir}/lala/${foo}/logs/main.log</filename>
          <format type="extended">
            %7.7{priority} %5.5{time}   [%8.8{category}] (%{context}): %{message}\n%{throwable}
          </format>
          <append>true</append>
        </file>
        <file id="classloader">
          <filename>logs/classloader.log</filename>
          <format type="raw"/>
        </file>
        <priority-filter id="foo" log-level="WARN">
          <file>
            <filename>logs/foo.log</filename>
            <format type="extended">%7.7{priority} %5.5{time}: %{message}\n%{throwable}</format>
          </file>
        </priority-filter>
      </targets>
  
      <categories>
        <category name="cocoon" log-level="INFO">
          <log-target id-ref="root"/>
  
          <category name="classloader" log-level="DEBUG">
            <log-target id-ref="classloader"/>
          </category>
        </category>
        <category name="foo" log-level="DEBUG">
          <log-target id-ref="foo"/>
        </category>
      </categories>
    </logkit>
  
    <context>
      <entry name="foo" value="bar"/>
      <entry name="current-dir" value="lili"/>
    </context>
  
    <roles>
      <role name="org.apache.avalon.excalibur.logger.test.TestComponent/A"
            shorthand="testA"
            default-class="org.apache.avalon.excalibur.logger.test.TestComponentImpl">
      </role>
      <role name="org.apache.avalon.excalibur.logger.test.TestComponent/B"
            shorthand="testB"
            default-class="org.apache.avalon.excalibur.logger.test.TestComponentImpl">
      </role>
      <role name="org.apache.avalon.excalibur.logger.test.TestComponent/C"
            shorthand="testC"
            default-class="org.apache.avalon.excalibur.logger.test.TestComponentImpl">
      </role>
    </roles>
  
    <components>
      <testA logger="cocoon"/>
      <testB logger="cocoon.classloader"/>
      <testC logger="foo"/>
    </components>
  
  </testcase>
  
  
  
  1.1                  jakarta-avalon-excalibur/logger/src/test/org/apache/avalon/excalibur/logger/test/TestComponent.java
  
  Index: TestComponent.java
  ===================================================================
  /*
   * Copyright (C) The Apache Software Foundation. All rights reserved.
   *
   * This software is published under the terms of the Apache Software License
   * version 1.1, a copy of which has been included  with this distribution in
   * the LICENSE.txt file.
   */
  package org.apache.avalon.excalibur.logger.test;
  
  import org.apache.avalon.framework.component.Component;
  import org.apache.avalon.framework.logger.Logger;
  
  /**
   * TestComponent.
   *
   * @author <a href="mailto:giacomo@apache,org">Giacomo Pati</a>
   * @version CVS $Revision: 1.1 $ $Date: 2002/04/04 02:34:16 $
   */
  public interface TestComponent
      extends Component
  {
      String ROLE = TestComponent.class.getName();
  
      void test( Logger defaultLogger, String message );
  }
  
  
  
  1.1                  jakarta-avalon-excalibur/logger/src/test/org/apache/avalon/excalibur/logger/test/TestComponentImpl.java
  
  Index: TestComponentImpl.java
  ===================================================================
  /*
   * Copyright (C) The Apache Software Foundation. All rights reserved.
   *
   * This software is published under the terms of the Apache Software License
   * version 1.1, a copy of which has been included  with this distribution in
   * the LICENSE.txt file.
   */
  package org.apache.avalon.excalibur.logger.test;
  
  import org.apache.avalon.framework.logger.AbstractLogEnabled;
  import org.apache.avalon.framework.logger.Logger;
  
  /**
   * TestComponent.
   *
   * @author <a href="mailto:giacomo@apache,org">Giacomo Pati</a>
   * @version CVS $Revision: 1.1 $ $Date: 2002/04/04 02:34:16 $
   */
  public class TestComponentImpl
      extends AbstractLogEnabled
      implements TestComponent
  {
      public void test( Logger defaultLogger, String message )
      {
          final Logger logger = getLogger();
          //final String cat = logger.getCategory();
          //defaultLogger.info( "Category is " + cat );
          logger.debug( message );
          logger.info( message );
          logger.warn( message );
          logger.error( message );
          logger.fatalError( message );
      }
  }
  
  
  
  1.1                  jakarta-avalon-excalibur/logger/src/xdocs/index.xml
  
  Index: index.xml
  ===================================================================
  <?xml version="1.0"?>
  
  <document>
      <header>
          <title>Excalibur TestCase</title>
          <subtitle>TestCase Utilities</subtitle>
          <authors>
              <person name="Peter Donald" email="peter@apache.org"/>
              <person name="Leif Mortenson" email="leif@tanukisoftware.com"/>
          </authors>
      </header>
      <body>
          <s1 title="Introduction">
              <p>
              This project contains utilities which can be used to write Excalibur Test Cases.
              </p>
          </s1>
      </body>
      <footer>
          <legal>
            Copyright (c) @year@ The Jakarta Apache Project All rights reserved.
            $Revision: 1.1 $ $Date: 2002/04/04 02:34:16 $
          </legal>
      </footer>
  </document>
  
  
  

--
To unsubscribe, e-mail:   <ma...@jakarta.apache.org>
For additional commands, e-mail: <ma...@jakarta.apache.org>