mcconnell    2002/09/07 00:27:12

  Modified:    assembly .cvsignore README.TXT build.xml default.properties
               assembly/src/etc demo.mf kernel.xml project.mf
               assembly/src/java/org/apache/excalibur/merlin/assembly
                        ContainerManager.java TypeManager.java
               assembly/src/java/org/apache/excalibur/merlin/container
                        Container.java ContainerFactory.java
                        DefaultContainer.java DefaultContainer.xinfo
               assembly/src/java/org/apache/excalibur/merlin/kernel
                        DefaultKernel.java
               assembly/src/java/org/apache/excalibur/merlin/resource
                        DeploymentHelper.java
               assembly/src/java/org/apache/excalibur/playground
                        BasicComponent.xinfo CustomContainer.xinfo
                        CustomContainer.xprofile
  Added:       assembly/lib corbaloc-1.0.jar openorb-1.3.0.jar orb-2.0.jar
               assembly/src/etc/activator client.xml server.xml
               assembly/src/idl demo.idl
               assembly/src/java/org/apache/excalibur/merlin/activation
                        DefaultRemoteResource.java
                        DefaultRemoteResourceFactory.java
                        DefaultRemoteResourceFactory.xinfo
                        DefaultServiceResolver.java
                        DefaultServiceResolver.xinfo RemoteResource.java
                        RemoteResourceFactory.java package.html
               assembly/src/java/org/apache/excalibur/merlin/container
                        ContainerHelper.java
               assembly/src/java/org/apache/excalibur/merlin/resource
                        DefaultResourceFactory.java ResourceFactory.java
               assembly/src/java/org/apache/excalibur/merlin/service
                        DefaultServiceManagementContext.java Handler.java
                        InvalidPathException.java
                        ServiceManagementContext.java
                        ServiceURLConnection.java ServiceURLFactory.java
                        UnknownServiceException.java package.html
               assembly/src/java/org/apache/excalibur/playground/activation
                        ActivationClient.java ActivationClient.xinfo
  Removed:     assembly/src/etc meta.mf
  Log:
  Addition of support for the declaration of the host under the kernel, 
improvements to bootstrap component loading, on-demand custom resource factory 
loading, reduction of logging implementation dependencies, simplification of 
the container factory implementation, separation of default container logic 
from per-container thread-management, kernel enhancements, improvements to 
exception messages, additional sample applications (mainly related to container 
embedding), addition of support for remote service activation (experimental). 
General enhancements towards transparent service distribution across containers.
  
  Revision  Changes    Path
  1.11      +2 -0      jakarta-avalon-excalibur/assembly/.cvsignore
  
  Index: .cvsignore
  ===================================================================
  RCS file: /home/cvs/jakarta-avalon-excalibur/assembly/.cvsignore,v
  retrieving revision 1.10
  retrieving revision 1.11
  diff -u -r1.10 -r1.11
  --- .cvsignore        21 Aug 2002 23:19:35 -0000      1.10
  +++ .cvsignore        7 Sep 2002 07:27:10 -0000       1.11
  @@ -7,3 +7,5 @@
   extensions
   sevak-conf.xml
   pss
  +backup
  +distributions
  
  
  
  1.16      +3 -0      jakarta-avalon-excalibur/assembly/README.TXT
  
  Index: README.TXT
  ===================================================================
  RCS file: /home/cvs/jakarta-avalon-excalibur/assembly/README.TXT,v
  retrieving revision 1.15
  retrieving revision 1.16
  diff -u -r1.15 -r1.16
  --- README.TXT        23 Aug 2002 07:02:40 -0000      1.15
  +++ README.TXT        7 Sep 2002 07:27:10 -0000       1.16
  @@ -12,6 +12,9 @@
   Status
   ------
   
  +07-SEP-2002
  +Addition of support for the declaration of the host under the kernel, 
improvements to bootstrap component loading, on-demand custom resource factory 
loading, reduction of logging implementation dependencies, simplification of 
the container factory implementation, separation of default container logic 
from per-container thread-management, kernel enhancements, improvements to 
exception messages, additional sample applications (mainly related to container 
embedding), addition of support for remote service activation (experimental). 
General enhancements towards transparent service distribution across containers.
  +
   23-AUG-2002 
   Checkstyle validation completed for all sources, general javadoc 
improvements, correction of a context key error in pooled manager reference 
within the kernel.
   
  
  
  
  1.55      +82 -19    jakarta-avalon-excalibur/assembly/build.xml
  
  Index: build.xml
  ===================================================================
  RCS file: /home/cvs/jakarta-avalon-excalibur/assembly/build.xml,v
  retrieving revision 1.54
  retrieving revision 1.55
  diff -u -r1.54 -r1.55
  --- build.xml 31 Aug 2002 14:53:59 -0000      1.54
  +++ build.xml 7 Sep 2002 07:27:10 -0000       1.55
  @@ -9,26 +9,32 @@
       <property file="${basedir}/../default.properties"/>
       <property file="${basedir}/default.properties"/>
   
  -
       <!-- Classpath for product -->
       <path id="project.class.path">
  -        <pathelement location="${logkit.jar}"/>
  -        <pathelement location="${avalon-framework.jar}"/>
  -        <pathelement location="${excalibur-i18n.jar}"/>
  -        <pathelement location="${excalibur-configuration.jar}"/>
  -        <pathelement location="${excalibur-container.jar}"/>
  -        <pathelement location="${excalibur-meta.jar}"/>
  -        <pathelement location="${excalibur-extension.jar}"/>
  -        <pathelement location="${excalibur-logger.jar}"/>
  -        <pathelement location="${excalibur-event.jar}"/>
  -        <pathelement location="${build.classes}"/>
  -        <pathelement location="${checkstyle.jar}"/>
  -        <pathelement location="${xml-apis.jar}"/>
  -        <pathelement path="${java.class.path}"/>
  +      <pathelement location="${logkit.jar}"/>
  +      <pathelement location="${avalon-framework.jar}"/>
  +      <pathelement location="${excalibur-i18n.jar}"/>
  +      <pathelement location="${excalibur-configuration.jar}"/>
  +      <pathelement location="${excalibur-container.jar}"/>
  +      <pathelement location="${excalibur-meta.jar}"/>
  +      <pathelement location="${excalibur-extension.jar}"/>
  +      <pathelement location="${excalibur-logger.jar}"/>
  +      <pathelement location="${excalibur-event.jar}"/>
  +      <pathelement location="${build.classes}"/>
  +      <pathelement location="${checkstyle.jar}"/>
  +      <pathelement location="${xml-apis.jar}"/>
  +      <pathelement path="${java.class.path}"/>
  +      <fileset dir="${lib.dir}">
  +        <include name="orb*.jar" />
  +        <include name="corbaloc*.jar" />
  +        <include name="openorb*.jar" />
  +      </fileset>
  +      <pathelement location="${idl-compiler.jar}"/>
       </path>
   
       <path id="tools.class.path">
           <pathelement location="${junit.jar}"/>
  +        <pathelement location="${idl-compiler.jar}"/>
       </path>
   
       <path id="test.class.path">
  @@ -90,12 +96,38 @@
              <include name="xerces-2.0.1.jar"/>
              <include name="xml-apis.jar"/>
              <include name="xalan-2.3.1.jar"/>
  +           <include name="openorb*.jar"/>
  +           <include name="orb*.jar"/>
  +           <include name="corbaloc*.jar"/>
            </fileset>
          </copy>
       </target>
   
  +  <target name="idl.context" depends="dependencies,orb.update">
  +    <mkdir dir="${build.dir}/src"/>
  +    <uptodate property="idl.modified" targetfile="${idl.dir}/demo.idl">
  +      <srcfiles dir="${build.dir}/src">
  +       <include name="**/*"/>
  +      </srcfiles>
  +    </uptodate>
  +  </target>
  +
  +  <target name="idl" depends="idl.context" if="idl.modified">
  +     <java failonerror="true" classname="${idl.class}" fork="true">
  +          <classpath>
  +             <path refid="project.class.path"/>
  +         </classpath>
  +         <arg line="-silence"/>
  +         <arg line="-native URL java.net.URL"/>
  +         <arg line="-d ${build.dir}/src"/>
  +         <arg line="-I ${idl.dir}"/>
  +         <arg line="demo.idl" />
  +      </java>
  +  </target>
  +
       <!-- Compiles the source code -->
  -    <target name="compile" depends="dependencies" description="Compiles the 
source code">
  +    <target name="compile" depends="idl,orb.update,corbaloc.update" 
  +       description="Compiles the source code">
   
           <mkdir dir="${build.classes}"/>
   
  @@ -106,8 +138,10 @@
               optimize="${build.optimize}"
               deprecation="${build.deprecation}"
               target="1.2">
  -            <classpath refid="project.class.path" />
  -            <include name="**/*.java"/>
  +          <src path="${java.dir}" />
  +          <src path="${build.dir}/src" />
  +          <classpath refid="project.class.path" />
  +          <include name="**/*.java"/>
           </javac>
   
           <!-- copy resources to same location as .class files -->
  @@ -120,6 +154,7 @@
   
       </target>
   
  +
       <!-- Compiles the unit test source code -->
       <target name="compile-test" depends="compile, dependencies-test" 
description="Compiles the source code">
           <mkdir dir="${build.testsrc}"/>
  @@ -406,10 +441,38 @@
           <delete dir="${dist.base}" />
       </target>
   
  +  <!--
  +  Update the local copy of the ORB.
  +  -->
  +
  +  <target name="orb.context">
  +    <available property="orb.available" 
file="${apps.dir}/enterprise/orb/build/orb-2.0.jar"/>
  +  </target>
  +
  +  <target name="orb.update" depends="orb.context" if="orb.available">
  +    <copy toDir="${lib.dir}" 
file="${apps.dir}/enterprise/orb/build/orb-2.0.jar"/>
  +  </target>
  +
  +  <!--
  +  Update the local copy of the corbaloc resolver.
  +  -->
  +
  +  <target name="corbaloc.context">
  +    <available property="corbaloc.available" 
file="${apps.dir}/enterprise/corbaloc/build/corbaloc-1.0.jar"/>
  +  </target>
  +
  +  <target name="corbaloc.update" depends="corbaloc.context" 
if="corbaloc.available">
  +    <copy toDir="${lib.dir}" 
file="${apps.dir}/enterprise/corbaloc/build/corbaloc-1.0.jar"/>
  +  </target>
  +
  +  <!--
  +  Misc. utilities.
  +  -->
  +
     <target name="patch">
       <replace dir="src/java" 
  -       token="org.apache.excalibur.merlin.resource.ContainerResource"
  -       value="org.apache.excalibur.merlin.container.ContainerResource" >
  +       token="org.apache.excalibur.merlin.container.service"
  +       value="org.apache.excalibur.merlin.service" >
        <include name="**/*.java"/>
       </replace>
     </target>
  
  
  
  1.11      +9 -1      jakarta-avalon-excalibur/assembly/default.properties
  
  Index: default.properties
  ===================================================================
  RCS file: /home/cvs/jakarta-avalon-excalibur/assembly/default.properties,v
  retrieving revision 1.10
  retrieving revision 1.11
  diff -u -r1.10 -r1.11
  --- default.properties        28 Aug 2002 16:22:50 -0000      1.10
  +++ default.properties        7 Sep 2002 07:27:10 -0000       1.11
  @@ -109,6 +109,7 @@
   conf.dir = ${src.dir}/conf
   test.dir = ${src.dir}/test
   
  +lib.dir = lib
   tools.dir=${basedir}/../../jakarta-avalon/tools
   
   #  Set the properties for distribution directories
  @@ -129,9 +130,16 @@
   # project specific properties
   
   lib.dir = lib
  +idl.dir = ${src.dir}/idl
   extension.dir = extensions
   demo.name = demo
   demo.jar = ${demo.name}.jar
   sar.name = ${name}-${version}.sar
  -
  +local-tools.dir = tools
  +idl-compiler.jar = ${local-tools.dir}/openorb_tools-1.3.0.jar
  +idl.class = org.openorb.compiler.IdlCompiler
  +
  +# avalon apps reference
  +excalibur.dir = ./..
  +apps.dir = ${excalibur.dir}/../jakarta-avalon-apps
   
  
  
  
  1.1                  jakarta-avalon-excalibur/assembly/lib/corbaloc-1.0.jar
  
        <<Binary file>>
  
  
  1.1                  jakarta-avalon-excalibur/assembly/lib/openorb-1.3.0.jar
  
        <<Binary file>>
  
  
  1.1                  jakarta-avalon-excalibur/assembly/lib/orb-2.0.jar
  
        <<Binary file>>
  
  
  1.3       +3 -0      jakarta-avalon-excalibur/assembly/src/etc/demo.mf
  
  Index: demo.mf
  ===================================================================
  RCS file: /home/cvs/jakarta-avalon-excalibur/assembly/src/etc/demo.mf,v
  retrieving revision 1.2
  retrieving revision 1.3
  diff -u -r1.2 -r1.3
  --- demo.mf   31 Aug 2002 14:54:00 -0000      1.2
  +++ demo.mf   7 Sep 2002 07:27:10 -0000       1.3
  @@ -27,3 +27,6 @@
   
   Name: org/apache/excalibur/playground/CustomContainer.class
   Avalon: Type
  +
  +Name: org/apache/excalibur/playground/activation/ActivationClient.class
  +Avalon: Type
  
  
  
  1.41      +8 -0      jakarta-avalon-excalibur/assembly/src/etc/kernel.xml
  
  Index: kernel.xml
  ===================================================================
  RCS file: /home/cvs/jakarta-avalon-excalibur/assembly/src/etc/kernel.xml,v
  retrieving revision 1.40
  retrieving revision 1.41
  diff -u -r1.40 -r1.41
  --- kernel.xml        31 Aug 2002 14:54:00 -0000      1.40
  +++ kernel.xml        7 Sep 2002 07:27:10 -0000       1.41
  @@ -22,6 +22,14 @@
   <kernel>
   
      <!--
  +   Declaration of the domain name that this kernel is operating within.
  +   -->
  +
  +   <system>
  +     <host>localhost</host>
  +   </system>
  +
  +   <!--
      Optional logging catagory creation directive.  The logging element 
declares
      the application wide default logging priority.  
      A target element enables defintion of a logging file to which log entries 
will 
  
  
  
  1.16      +7 -0      jakarta-avalon-excalibur/assembly/src/etc/project.mf
  
  Index: project.mf
  ===================================================================
  RCS file: /home/cvs/jakarta-avalon-excalibur/assembly/src/etc/project.mf,v
  retrieving revision 1.15
  retrieving revision 1.16
  diff -u -r1.15 -r1.16
  --- project.mf        20 Aug 2002 23:23:07 -0000      1.15
  +++ project.mf        7 Sep 2002 07:27:10 -0000       1.16
  @@ -34,8 +34,15 @@
   Class-Path: logkit.jar xerces-2.0.1.jar xml-apis.jar xalan-2.3.1.jar
   Main-Class: org.apache.excalibur.merlin.Main
   
  +Name: org/apache/excalibur/merlin/container/StructuralExtension.class
  +Avalon: Type
  +
   Name: org/apache/excalibur/merlin/container/DefaultContainer.class
   Avalon: Type
   
   Name: org/apache/excalibur/merlin/kernel/DefaultKernel.class
   Avalon: Type
  +
  +Name: org/apache/excalibur/merlin/activation/DefaultServiceResolver.class
  +Avalon: Type
  +
  
  
  
  1.1                  
jakarta-avalon-excalibur/assembly/src/etc/activator/client.xml
  
  Index: client.xml
  ===================================================================
  
  <!--
  Assemble a component instance.
  -->
  
  <kernel>
  
     <logging priority="INFO" target="default">
        <category priority="WARN"  name="logging" />
        <target name="kernel">
          <file location="kernel.log" />
        </target>
     </logging>
  
     <categories priority="INFO">
       <category priority="WARN"  name="loader" />
       <category priority="INFO"  name="export" />
     </categories>
  
     <library dir=".">
       <include name="extensions"/>
     </library>
  
     <!--
     Defintion of a container within a PSS enhanced ORB folowed by a Property
     service.
     -->
  
     <container name="root">
  
       <categories priority="INFO">
         <category priority="WARN"  name="loader" />
       </categories>
  
       <!--
       Create a classpath including the ORB resources, ORB component extensions,
       and the CORBA container.  This container demonstrates the use of the 
       corbaloc package under the JDK 1.4.1 ORB.
       -->
  
       <classpath>
         <fileset dir="lib">
           <include name="corbaloc-1.0.jar"/>
         </fileset>
         <fileset dir="build/lib">
           <include name="demo.jar"/>
         </fileset>
       </classpath>
  
       <!--
       Request assembly of the client component.  The client is depedent on a 
       ORB service which will be resolved automatically.
       -->
  
       <component name="client" 
class="org.apache.excalibur.playground.ActivationClient" activation="true">
          <categories priority="DEBUG"/>
          <configuration>
            <connection url="corbaloc:iiop:[EMAIL PROTECTED]:2056/activator"/>
          </configuration>
       </component>
  
     </container>
  
  </kernel>
  
  
  
  1.1                  
jakarta-avalon-excalibur/assembly/src/etc/activator/server.xml
  
  Index: server.xml
  ===================================================================
  
  <!--
  Assemble a component instance.
  -->
  
  <kernel>
  
     <system>
       <host>home.osm.net</host>
     </system>
  
     <logging priority="INFO" target="default">
        <category priority="WARN"  name="logging" />
        <target name="kernel">
          <file location="kernel.log" />
        </target>
     </logging>
  
     <categories priority="INFO">
       <category priority="WARN"  name="loader" />
     </categories>
  
     <library dir=".">
       <include name="extensions"/>
     </library>
  
     <!--
     Defintion of a container within a PSS enhanced ORB folowed by a Property
     service.
     -->
  
     <container name="root">
  
       <categories priority="INFO">
         <category priority="WARN"  name="loader" />
       </categories>
  
       <classpath>
         <fileset dir="lib">
           <include name="openorb-1.3.0.jar"/>
           <include name="orb-2.0.jar"/>
           <include name="corbaloc-1.0.jar"/>
         </fileset>
       </classpath>
  
       <component name="orb" class="org.apache.orb.ORB" activation="true">
          <categories priority="DEBUG"/>
          <configuration>
            <property name="iiop.port" value="2056"/>
            <initializer class="org.openorb.adapter.fwd.ForwardInitializer" 
name="forward"/>
          </configuration>
       </component>
  
       <container name="activator" 
class="org.apache.excalibur.merlin.activation.DefaultServiceResolver">
          <categories priority="INFO"/>
       </container>
  
     </container>
  
  </kernel>
  
  
  
  1.1                  jakarta-avalon-excalibur/assembly/src/idl/demo.idl
  
  Index: demo.idl
  ===================================================================
  //
  // demo.idl
  //
  
  #ifndef _DEMO_IDL_
  #define _DEMO_IDL_
  #pragma prefix "excalibur.apache.org"
  
  module playground
  {
      module remote
      {
  
         /**
          * A simple minimal test system interface defintion.
          */
          interface TestCase
          {
              boolean test();
          };
      };
  };
  
  #endif // _DEMO_IDL_
  
  
  
  1.1                  
jakarta-avalon-excalibur/assembly/src/java/org/apache/excalibur/merlin/activation/DefaultRemoteResource.java
  
  Index: DefaultRemoteResource.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.excalibur.merlin.activation;
  
  import org.apache.avalon.framework.logger.AbstractLogEnabled;
  import org.apache.avalon.framework.context.Context;
  import org.apache.avalon.framework.activity.Disposable;
  import org.apache.excalibur.merlin.model.Profile;
  import org.apache.excalibur.merlin.model.Resource;
  import org.apache.excalibur.meta.info.ServiceDescriptor;
  import org.apache.excalibur.merlin.assembly.ContainerManager;
  import org.apache.excalibur.merlin.resource.DefaultResource;
  import org.apache.excalibur.merlin.resource.LifestyleHandler;
  
  import org.apache.orb.ORB;
  
  
  /**
   * Opaque type that maps a path to a profile.
   *
   * @author <a href="mailto:[EMAIL PROTECTED]">Stephen McConnell</a>
   * @version $Revision: 1.1 $ $Date: 2002/09/07 07:27:11 $
   */
  public class DefaultRemoteResource extends DefaultResource implements 
RemoteResource
  {
      
//==========================================================================
      // state
      
//==========================================================================
  
     /**
      * The path of the profile designator.
      */
      private final ORB m_orb;
  
     /**
      * A profile containing POA servant activation criteria.
      */
      private final Profile m_profile;
  
      
//==========================================================================
      // constructor
      
//==========================================================================
  
      /**
       * Create a new remote resource instance.
       *
       * @param manager the container type manager
       * @param profile the resource's profile
       * @param context the deployment context
       * @param handler the lifestyle handler
       * @param orb the object request broker
       */
      public DefaultRemoteResource( final ContainerManager manager,
                             final Profile profile,
                             final Context context,
                             final LifestyleHandler handler,
                             final ORB orb )
      {
          super( manager, profile, context, handler );
          m_profile = profile;
          m_orb = orb;
      }
  
      
//==========================================================================
      // RemoteResource
      
//==========================================================================
  
     /**
      * Returns an object reference to the resource.
      * @return the object reference
      */
      public org.omg.CORBA.Object getReference()
      {
          return null;
      }
  
      
//==========================================================================
      // implementation
      
//==========================================================================
  
  
     /**
      * Returns a string representation of the resoruce.
      *
      * @return a string describing the resource
      */
      public String toString()
      {
          return "RemoteResource - profile:" + m_profile;
      }
  }
  
  
  
  1.1                  
jakarta-avalon-excalibur/assembly/src/java/org/apache/excalibur/merlin/activation/DefaultRemoteResourceFactory.java
  
  Index: DefaultRemoteResourceFactory.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.
   *
   * Original contribution by OSM SARL, http://www.osm.net
   */
  package org.apache.excalibur.merlin.activation;
  
  import org.apache.avalon.framework.context.Context;
  import org.apache.avalon.framework.service.ServiceManager;
  import org.apache.avalon.framework.service.ServiceException;
  import org.apache.avalon.framework.service.Serviceable;
  import org.apache.excalibur.merlin.assembly.ContainerManager;
  import org.apache.excalibur.merlin.resource.LifestyleHandler;
  import org.apache.excalibur.merlin.model.Profile;
  import org.apache.excalibur.merlin.model.Resource;
  
  import org.apache.orb.ORB;
  
  /**
   * The default resource factory.
   *
   * @author <a href="mailto:[EMAIL PROTECTED]">Stephen McConnell</a>
   */
  public class DefaultRemoteResourceFactory implements RemoteResourceFactory
  {
       private ORB m_orb;
  
      /**
       * Factory servicing invoked by the factory container.  The remote
       * factory resource is supplied with an ORB as part of dependency 
       * resolution.
       * 
       * @param manager the service manager.
       * @exception ServiceException if the manager does not provide the 
       *  required services.
       */
       public void service( ServiceManager manager ) throws ServiceException
       {
           m_orb = (ORB) manager.lookup( "orb" );
       }
  
      /**
       * Creation of a new resource.
       * 
       * @param manager the type manager
       * @param profile the component profile
       * @param context the deployment context
       * @param handler the lifestyle handler
       * @return the resource instance
       * @exception NullPointerException if any of the supplied arguments are 
null
       */
       public Resource createResource( 
                        ContainerManager manager, 
                        Profile profile, 
                        Context context, 
                        LifestyleHandler handler ) throws NullPointerException
       {
           if( manager == null )
           {
               throw new NullPointerException( "manager" );
           }
           if( profile == null )
           {
               throw new NullPointerException( "profile" );
           }
           if( context == null )
           {
               throw new NullPointerException( "context" );
           }
           if( handler == null )
           {
               throw new NullPointerException( "handler" );
           }
  
           return new DefaultRemoteResource( manager, profile, context, 
handler, m_orb );
       }
  }
  
  
  
  1.1                  
jakarta-avalon-excalibur/assembly/src/java/org/apache/excalibur/merlin/activation/DefaultRemoteResourceFactory.xinfo
  
  Index: DefaultRemoteResourceFactory.xinfo
  ===================================================================
  <?xml version="1.0"?>
  
  <!--
   Copyright 2000 OSM SARL. All Rights Reserved.
   
   This software is the proprietary information of OSM SARL.  
   Use is subject to license terms.
    
   @author  Stephen McConnell
   @version 1.0 12/03/2001
  -->
  
  <type>
  
    <component>
      <name>remote-factory</name>
    </component>
  
    <services>
      <service>
        <reference 
type="org.apache.excalibur.merlin.resource.RemoteResourceFactory" />
      </service>
    </services>
  
    <!-- 
    dependencies that this type has on other services 
    -->
  
    <dependencies>
      <dependency>
        <role>orb</role>
        <reference type="org.apache.orb.ORB" version="2.4"/>
      </dependency>
    </dependencies>
  
  </type>
  
  
  
  
  1.1                  
jakarta-avalon-excalibur/assembly/src/java/org/apache/excalibur/merlin/activation/DefaultServiceResolver.java
  
  Index: DefaultServiceResolver.java
  ===================================================================
  
  package org.apache.excalibur.merlin.activation;
  
  import java.io.Serializable;
  import java.net.URL;
  import java.net.URI;
  import java.net.MalformedURLException;
  import java.net.URISyntaxException;
  
  import org.apache.avalon.framework.context.Context;
  import org.apache.avalon.framework.context.ContextException;
  import org.apache.avalon.framework.configuration.Configuration;
  import org.apache.avalon.framework.configuration.ConfigurationException;
  import org.apache.avalon.framework.service.Serviceable;
  import org.apache.avalon.framework.service.ServiceManager;
  
  import org.apache.orb.ORB;
  import org.apache.orb.corbaloc.InvalidQuery;
  import org.apache.orb.corbaloc.ServiceRedirection;
  import org.apache.orb.corbaloc.UnknownReference;
  import org.apache.orb.corbaloc.InvalidReference;
  import org.apache.orb.corbaloc.Handler;
  import org.apache.orb.corbaloc.Resolver;
  import org.apache.orb.corbaloc.ServiceResolver;
  import org.apache.orb.corbaloc.ServiceResolverOperations;
  import org.apache.orb.corbaloc.ServiceResolverPOATie;
  import org.apache.orb.corbaloc.ServiceResolverHelper;
  
  import org.openorb.corbaloc.CorbalocService;
  import org.openorb.corbaloc.CorbalocServiceHelper;
  
  import org.apache.excalibur.merlin.assembly.ContainerManager;
  import org.apache.excalibur.merlin.container.Container;
  import org.apache.excalibur.merlin.container.DefaultContainer;
  import org.apache.excalibur.merlin.service.ServiceManagementContext;
  import org.apache.excalibur.merlin.service.UnknownServiceException;
  import org.apache.excalibur.merlin.service.InvalidPathException;
  import org.apache.excalibur.merlin.model.Resource;
  
  import org.omg.CORBA.Any;
  import org.omg.PortableServer.POA;
  import org.omg.PortableServer.Servant;
  import org.omg.PortableServer.IdAssignmentPolicyValue;
  import org.omg.PortableServer.LifespanPolicyValue;
  import org.omg.CORBA.Policy;
  
  /**
   * Implementation of a container that provides support for remotely
   * accessible services.  Services managed by this container my be 
   * accessed using a corbaloc URL.  The implemetation handles the management
   * of incomming requests by redirecting requests to servant implementation
   * exposing remotely accessible services.
   *
   * @author <a href="mailto:[EMAIL PROTECTED]">Stephen McConnell</a>
   */
  
  public class DefaultServiceResolver extends DefaultContainer
  implements ServiceResolverOperations, Serviceable
  {
     /**
      * The service manager from which we aquire the ORB.
      */
      private ServiceManager m_manager;
  
     /**
      * The configuration (not used currently)
      */
      private Configuration m_config;
  
     /**
      * The context from which we access the component name.
      */
      private Context m_context;
  
     /**
      * The server ORB used to locate the corbaloc service, POA service, and 
      * handle POA activation.
      */
      private ORB m_orb;
  
     /**
      * The root POA.
      */
      private POA m_root;
  
     /**
      * The POA for this servant.
      */
      private POA m_poa;
  
     /**
      * Internal reference to the object reference to this server. 
      */
      private ServiceResolver m_resolver;
  
     /**
      * The name of this server.
      */
      private String m_name;
  
     /**
      * The URL that this container is published under.
      */
      private URL m_corbaloc;
  
     /**
      * The container's resource registry.
      */
      private ServiceManagementContext m_registry;
      
      //=================================================================
      // Contextualizable
      //=================================================================
  
     /**
      * Method invoked by the ORB initializer to declare the runtime context.
      * @param context runtime application context
      * @exception ContextException if the supplied context does not meet 
      *   contextulization criteria
      */
      public void contextualize( Context context ) throws ContextException
      {
          super.contextualize( context );
          m_name = (String) context.get("avalon:name");
          m_registry = (ServiceManagementContext) context.get( REGISTRY_KEY );
          m_context = context;
      }
  
      //=======================================================================
      // Configurable
      //=======================================================================
      
     /**
      * Method invoked by the ORB initializer to declare the static 
configuration.
      * @param config application static configuration
      * @exception ConfigurationException if an error during the configuration 
stage occurs
      */
      public void configure( final Configuration config )
          throws ConfigurationException
      {
          super.configure( config );
          m_config = config;
      }
  
      //=======================================================================
      // Serviceable
      //=======================================================================
      
     /**
      * Method invoked by the container to provide dependent services.
      * @param manager the service manager
      */
      public void service( final ServiceManager manager )
      {
          m_manager = manager;
      }
  
  
      //=======================================================================
      // Initializable
      //=======================================================================
  
     /**
      * Initialization of the server.  The initialization validates that a 
      * logging channel is available, that configuration exists, and that 
      * context is not null.  Folowing validation, the implementation 
      * creates an ORB based on a child configuration named 'orb' supplied
      * during Initializer establishment.  Once the ORB is obtained, the 
      * implementation handles the establishment of the POA and servant.
      *
      * @exception Exception if initialization fails
      */
      public void initialize()
      throws Exception
      {       
          super.initialize();
  
          //
          // get the POA
          //
  
          m_orb = (ORB) m_manager.lookup("orb");
          m_root = (POA) m_orb.resolve_initial_references("RootPOA");
  
          CorbalocService registry = CorbalocServiceHelper.narrow(
                m_orb.resolve_initial_references( "CorbalocService" ) );
  
          final String key = m_name;
          try
          {
              m_poa = m_root.create_POA(
                key,
                m_root.the_POAManager(),
                new Policy[]
                {
                   m_root.create_id_assignment_policy( 
IdAssignmentPolicyValue.USER_ID ),
                   m_root.create_lifespan_policy( 
LifespanPolicyValue.PERSISTENT ) 
                } 
              );
  
              Servant servant = new ServiceResolverPOATie( this );
              byte[] id = key.getBytes();
              m_poa.activate_object_with_id( id, servant );
              m_resolver = ServiceResolverHelper.narrow( m_poa.id_to_reference( 
id ) );
          }
          catch( Throwable e )
          {
              String error = "Unable to create the application POA: " + 
e.toString();
              getLogger().error( error, e );
              throw new Exception( error );
          }
  
          String path = registry.put_object( m_resolver, key );
          m_corbaloc = new URL( null, path, new Handler( m_orb ) );
  
          getLogger().info("remote: " + m_corbaloc );
      }
  
      //=======================================================================
      // Startable
      //=======================================================================
      
      /**
       * Start the container.
       * @exception Exception if a startup error occurs
       */
      public void start()
      throws Exception
      {
          m_poa.the_POAManager().activate();
          super.start();
      }
  
     /**
      * Stops the container.
      * @exception Exception if a shutdown error occurs
      */
      public void stop()
      throws Exception
      {
          super.stop();
          try
          {
              m_poa.destroy( true, true );
          }
          catch( Throwable e )
          {
              if( getLogger().isWarnEnabled() ) 
              {
                  getLogger().warn( "ignoring POA related exception" );
              }
          }
      }
  
      //=======================================================================
      // corbaloc::Resolver
      //=======================================================================
  
      /**
       * Process a corbaloc request.
       * 
       * @param path a path relative to this container
       * @return an object reference
       * @exception  InvalidQuery if the supplied path is invalid
       * @exception  ServiceRedirection if the ref resolution is being 
redirected
       */
      public org.omg.CORBA.Object resolve( String path )
          throws InvalidQuery, ServiceRedirection, UnknownReference, 
InvalidReference
      {
  
          //
          // check if this is a reference to ourselves
          //
  
          if( path.equals("") )
          {
              // 
              // the URI is refering to ourselves
              //
  
              //Any any = m_orb.create_any();
              //ServiceResolverHelper.insert( any, m_resolver );
              return m_resolver;
          }
  
          //
          // convert the relative corbaloc path to an absolute path relative to 
the 
          // the registries base path (i.e. transform from the corbaloc 
namespace to 
          // the container namespace)
          //
  
          URI base = m_registry.getBase();
          URI uri = base.resolve( path );
  
          getLogger().info("path: '" + path + "'");
          getLogger().info("resolved: " + uri );
  
          try
          {
              Resource resource = m_registry.locate( uri );
              getLogger().info("## located a resource: " + resource );
  
              //
              // we have located a resource matching the resolved uri
              // so we need to verify if the object type backing the resource
              // can be passed back to the client inside an any
              //
  
  /*
              String policy = 
resource.getProfile().getType().getInfo().getAttribute(
                "corba:adaptive", "false" );
              if( policy.equalsIgnoreCase("false") )
              {
                  //
                  // this resource does not implement an adaptrive interface
                  //
  
                  final String error = 
                    "Service is not IIOP addressable.";
                  throw new InvalidReference( m_url, error );
              }
              else
              {
                  //
                  // get the object - if it is a corba object reference
                  // then return it otherwise 
                  //
  
                  try
                  {
                      Object object = resource.access();
                      return ((Adaptive)object).getAdapter();
                  }
                  catch( Throwable e )
                  {
                      final String error = "Unable to establish an adaptive 
object refererence.";
                      throw new InvalidReference( path, error );
                  }
              }
  */
          }
          catch( UnknownServiceException use )
          {
              getLogger().error( use.toString() );
              throw new UnknownReference( path, use.getMessage() );
          }
          catch( InvalidPathException ipe )
          {
              getLogger().error( ipe.toString() );
              throw new InvalidReference( path, ipe.getMessage() );
          }
  
          //
          // temporary fallback - return a reference to ourselves
          //
  
          //Any any = m_orb.create_any();
          //ServiceResolverHelper.insert( any, m_resolver );
          //return any;
  
          return m_resolver;
     }
  
      //=======================================================================
      // Disposable
      //=======================================================================
      
     /**
      * Disposal of the server.  This method is triggered by a shutdown hook
      * becuase initializers are not cleared by an ORB on shutdown.
      */
      public void dispose()
      {
          super.dispose();
      }
  
      //=======================================================================
      // implementation
      //=======================================================================
      
     /**
      * Pack a value in an.
      * @param any the Any 
      * @return Object the any contents as a Java Object
      */
      private Any putResult( Any any, Object object )
      {
          if( any == null )
          { 
              throw new NullPointerException("any");
          }
          if( object == null )
          { 
              throw new NullPointerException("object");
          }
  
          if( object instanceof org.omg.CORBA.Object )
          {
              any.insert_Object( (org.omg.CORBA.Object) object );
              return any;
          }
          else if( object instanceof Serializable )
          {
              any.insert_Value((Serializable) object );
              return any;
          }
          else
          {
             throw new IllegalStateException( 
                "Object type: " + any.type().kind().value() + " unsupported.");
          }
      }
  }
  
  
  
  1.1                  
jakarta-avalon-excalibur/assembly/src/java/org/apache/excalibur/merlin/activation/DefaultServiceResolver.xinfo
  
  Index: DefaultServiceResolver.xinfo
  ===================================================================
  <?xml version="1.0"?>
  
  <!--
   Copyright 2000 OSM SARL. All Rights Reserved.
   
   This software is the proprietary information of OSM SARL.  
   Use is subject to license terms.
    
   @author  Stephen McConnell
   @version 1.0 12/03/2001
  -->
  
  <type>
  
    <component>
      <name>activator</name>
    </component>
  
    <context>
      <entry key="avalon:name" />
      <entry key="merlin:container.descriptor" 
        type="org.apache.excalibur.merlin.model.ContainerDescriptor" />
      <entry key="merlin:container.manager"
        type="org.apache.excalibur.merlin.assembly.ContainerManager"/>
      <entry key="merlin:container.services" type="java.util.Map"/>
      <entry key="merlin:container.state-listener" 
        type="org.apache.excalibur.merlin.container.StateListener" 
        optional="true"/>
      <entry key="merlin:container.container-listener" 
        type="org.apache.excalibur.merlin.container.ContainerListener" 
        optional="true"/>
      <entry key="merlin:container.registry" 
        type="org.apache.excalibur.merlin.service.ServiceManagementContext"/>
    </context>
  
    <services>
      <service>
        <attributes>
          <attribute key="corba:helper" 
value="org.apache.orb.corbaloc.ServiceResolver"/>
        </attributes>
        <reference type="org.apache.orb.corbaloc.ServiceResolverOperations" />
      </service>
      <service>
        <reference type="org.apache.excalibur.merlin.container.Container" />
      </service>
    </services>
  
    <!-- 
    dependencies that this type has on other services 
    -->
  
    <dependencies>
      <dependency>
        <role>orb</role>
        <reference type="org.apache.orb.ORB" version="2.4"/>
      </dependency>
    </dependencies>
  
    <stages>
       <stage>
          <reference type="org.apache.excalibur.merlin.container.Structural"/>
       </stage>
    </stages>
  
  
  </type>
  
  
  
  
  1.1                  
jakarta-avalon-excalibur/assembly/src/java/org/apache/excalibur/merlin/activation/RemoteResource.java
  
  Index: RemoteResource.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.excalibur.merlin.activation;
  
  import org.apache.excalibur.merlin.model.Resource;
  import org.apache.excalibur.meta.info.ServiceDescriptor;
  import org.apache.avalon.framework.activity.Disposable;
  
  /**
   * Interface implemented by object capable of exporting a CORBA object 
reference.
   *
   * @author <a href="mailto:[EMAIL PROTECTED]">Stephen McConnell</a>
   * @version $Revision: 1.1 $ $Date: 2002/09/07 07:27:11 $
   */
  public interface RemoteResource extends Resource
  {
     /**
      * Returns an object reference to the resource.
      * @return the object reference
      */
      org.omg.CORBA.Object getReference();
  
  }
  
  
  
  1.1                  
jakarta-avalon-excalibur/assembly/src/java/org/apache/excalibur/merlin/activation/RemoteResourceFactory.java
  
  Index: RemoteResourceFactory.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.
   *
   * Original contribution by OSM SARL, http://www.osm.net
   */
  package org.apache.excalibur.merlin.activation;
  
  import org.apache.excalibur.merlin.resource.ResourceFactory;
  
  
  /**
   * Interface implemented by a classes capable of creating resource instances.
   *
   * @author <a href="mailto:[EMAIL PROTECTED]">Stephen McConnell</a>
   */
  public interface RemoteResourceFactory extends ResourceFactory
  {
  
  }
  
  
  1.1                  
jakarta-avalon-excalibur/assembly/src/java/org/apache/excalibur/merlin/activation/package.html
  
  Index: package.html
  ===================================================================
  
  <body>
  <p>
  The <code>activation</code> package contains interfaces and classes 
supporting remote
  service activation over a CORBA IIOP protocol.
  </p>
  
  </body>
  
  
  
  1.30      +85 -22    
jakarta-avalon-excalibur/assembly/src/java/org/apache/excalibur/merlin/assembly/ContainerManager.java
  
  Index: ContainerManager.java
  ===================================================================
  RCS file: 
/home/cvs/jakarta-avalon-excalibur/assembly/src/java/org/apache/excalibur/merlin/assembly/ContainerManager.java,v
  retrieving revision 1.29
  retrieving revision 1.30
  diff -u -r1.29 -r1.30
  --- ContainerManager.java     31 Aug 2002 14:54:00 -0000      1.29
  +++ ContainerManager.java     7 Sep 2002 07:27:11 -0000       1.30
  @@ -28,6 +28,8 @@
   import org.apache.excalibur.merlin.resource.LifestyleManager;
   import org.apache.excalibur.merlin.resource.LifecycleHelper;
   import org.apache.excalibur.merlin.resource.DeploymentHelper;
  +import org.apache.excalibur.merlin.resource.ResourceFactory;
  +import org.apache.excalibur.merlin.resource.DefaultResourceFactory;
   import org.apache.excalibur.merlin.model.ContainerDescriptor;
   import org.apache.excalibur.merlin.model.ClasspathDescriptor;
   import org.apache.excalibur.merlin.model.LoggingDescriptor;
  @@ -83,6 +85,8 @@
       */
       public static final String LIFESTYLES_KEY = "lifestyles";
   
  +    private static final ResourceFactory c_resourceFactory = new 
DefaultResourceFactory();
  +
       //===================================================================
       // state
       //===================================================================
  @@ -515,6 +519,20 @@
           CategoriesDescriptor categories = descriptor.getCategories();
           getLoggingManager().addCategories( path, categories );
   
  +
  +        //
  +        // if the container descriptor includes a merlin:lifestyle-manager
  +        // attribute, load the manager using this type manager and associate
  +        // it with the new type manager
  +        //
  +
  +        //String classname = 
descriptor.getType().getInfo().getAttributes().getAttribute(
  +        //  "merlin:lifestyle-manager", null );
  +        //if( classname != null )
  +        //{
  +        //    Profile profile = 
  +        //}
  +
           //
           // create a new profile manager as a child of this manager
           //
  @@ -861,16 +879,64 @@
           c.put("app.home", m_home );
   
           //
  -        // continue on with resource creation
  +        // get the lifestyle handler
           //
   
  +        LifestyleManager lifestyles = getLifestyleManager();
  +        LifestyleHandler handler;
           try
           {
  -            LifestyleManager lifestyles = getLifestyleManager();
  -            LifestyleHandler handler =
  -              lifestyles.getHandler( this, m_deployment, m_helper, profile, 
c );
  -            DefaultResource res;
  +            handler = lifestyles.getHandler( this, m_deployment, m_helper, 
profile, c );
  +        }
  +        catch( Throwable e )
  +        {
  +            final String error = "Could not establish a lifestyle handler 
for the profile: "
  +             + profile.getName();
  +            throw new ResourceException( error, e );
  +        }
  +
  +        //
  +        // if the profile contains a resource factory declaration then 
  +        // hand resource creation responsibility to it, otherwise apply
  +        // the default resource creation mechanisms
  +        //
  +
  +        String classname = 
  +          profile.getType().getInfo().getAttribute(
  +            "merlin:resource-factory", null );
  +
  +        if( classname != null )
  +        {
  +            Profile factoryProfile = getProfile( 
  +              new ReferenceDescriptor( classname ) );
   
  +            if( factoryProfile == null )
  +            {
  +                final String error = "The profile: '" + profile.getName() 
  +                  + "' contains a reference to an unknown custom resource 
factory component."
  +                  + " Factory service interface: " + classname + " is not 
recognized.";
  +                throw new ResourceException( error );
  +            }
  + 
  +            try
  +            {
  +                Resource factoryResource = getResource( factoryProfile, 
context );
  +                ResourceFactory factory = (ResourceFactory) 
factoryResource.access();
  +                Resource res = factory.createResource( this, profile, c, 
handler );
  +                m_resources.put( profile, res );
  +                return res;
  +            }
  +            catch( Throwable e )
  +            {
  +                final String error = 
  +                  "Unexpected exception while creating a custom resource for 
profile: " 
  +                  + profile.getName() + " using resource factory: " + 
factoryProfile;
  +                throw new ResourceException( error, e );
  +            }
  +        }
  +        else
  +        {
  +            Resource res;
               if( profile instanceof ContainerDescriptor )
               {
                   res = new ContainerResource( this, profile, context, handler 
);
  @@ -879,20 +945,14 @@
               {
                   res = new DefaultResource( this, profile, context, handler );
               }
  -            res.enableLogging( getLocalLogger().getChildLogger( "resource" ) 
);
  +            ((LogEnabled)res).enableLogging( 
getLocalLogger().getChildLogger( "resource" ) );
               m_resources.put( profile, res );
               return res;
           }
  -        catch( Throwable e )
  -        {
  -            final String error =
  -              "Unexpected error while attempting to prepare a lifestyle 
handler.";
  -            throw new ResourceException( error, e );
  -        }
       }
   
      /**
  -    * Assemble a profile dependecies independently of the application scope. 
This
  +    * Assemble a profile dependencies independently of the application 
scope. This
       * method is typically applied to the establishment of associations 
between 
       * bootstrap components such as containers, their depedecies and extension
       * stage providers.
  @@ -1049,15 +1109,18 @@
           for( int i=0; i<startup.length; i++ )
           {
               Profile profile = startup[i];
  -            try
  -            {
  -                list.add( getResource( profile ) );
  -            }
  -            catch( Throwable e )
  +            if( isLocal( profile ) )
               {
  -                final String warning = 
  -                  "Missing resource for profile: " + profile;
  -                getLocalLogger().warn( warning );
  +                try
  +                {
  +                    list.add( getResource( profile ) );
  +                }
  +                catch( Throwable e )
  +                {
  +                    final String warning = 
  +                      "Missing resource for profile: " + profile;
  +                    getLocalLogger().warn( warning );
  +                }
               }
           }
           return (Resource[]) list.toArray( new Resource[ list.size() ] );
  
  
  
  1.17      +41 -20    
jakarta-avalon-excalibur/assembly/src/java/org/apache/excalibur/merlin/assembly/TypeManager.java
  
  Index: TypeManager.java
  ===================================================================
  RCS file: 
/home/cvs/jakarta-avalon-excalibur/assembly/src/java/org/apache/excalibur/merlin/assembly/TypeManager.java,v
  retrieving revision 1.16
  retrieving revision 1.17
  diff -u -r1.16 -r1.17
  --- TypeManager.java  23 Aug 2002 09:23:02 -0000      1.16
  +++ TypeManager.java  7 Sep 2002 07:27:11 -0000       1.17
  @@ -18,6 +18,7 @@
   import java.util.Iterator;
   import java.util.Map;
   import java.util.List;
  +import java.util.StringTokenizer;
   import java.net.URLClassLoader;
   import java.net.URL;
   import java.net.JarURLConnection;
  @@ -71,17 +72,12 @@
       */
       public static final String CLASSPATH_DESCRIPTOR_KEY = "classpath";
   
  -   /**
  -    * The default Merlin container implementation class name.
  -    */
  -    public static final String DEFAULT_CONTAINER_CLASS = 
  -      "org.apache.excalibur.merlin.container.DefaultContainer";
   
      /**
  -    * The default Merlin container structural extension class name.
  +    * Flag indicating of the bootstap sequence of evaluating the classpath
  +    * and extensions declared at JVM launch have been assesed or not.
       */
  -    public static final String DEFAULT_STRUCTURE_CLASS = 
  -      "org.apache.excalibur.merlin.container.StructuralExtension";
  +    private static boolean m_bootstrap = true;
   
   
       //===================================================================
  @@ -220,6 +216,42 @@
           m_types = new TypeRegistry( this, getLocalLogger().getChildLogger( 
"types" ) );
   
           //
  +        // handle the bootstrap process
  +        //
  +
  +        File root = new File( System.getProperty( "user.dir" ) ); 
  +        if( m_bootstrap )
  +        {
  +            System.out.println("##### BOOTSTRAP " + m_extensions + " #####" 
);
  +            String sep = System.getProperty("path.separator");
  +            String classpath = System.getProperty("java.class.path");
  +            System.out.println("\tclasspath: " + classpath );
  +
  +            StringTokenizer tokenizer = new StringTokenizer( classpath, sep 
);
  +            while( tokenizer.hasMoreTokens() )
  +            {
  +                String token = tokenizer.nextToken();
  +                URL jar = new File( root, token ).toURL();
  +                System.out.println("\tcp-term: " + jar );
  +                scan( jar );
  +            }
  +/*
  +            String ext = System.getProperty("java.ext.dirs").trim();
  +            System.out.println("\text: '" + ext + "'");
  +
  +            tokenizer = new StringTokenizer( ext, sep );
  +            while( tokenizer.hasMoreTokens() )
  +            {
  +                String token = tokenizer.nextToken();
  +                URL extension = new File( root, token ).toURL();
  +                System.out.println("\ttoken: " + extension );
  +                scan( extension );
  +            }
  +*/
  +            m_bootstrap = false;
  +        }
  +
  +        //
           // setup the extension directories
           //
   
  @@ -259,17 +291,6 @@
               getLocalLogger().debug("installing classpath");
               addClasspath( m_classpath );
           }
  -
  -        //
  -        // declare bootstrap types
  -        //
  -
  -        if( !( getParent() instanceof TypeManager ))
  -        {
  -            m_types.addType( DEFAULT_CONTAINER_CLASS );
  -            m_types.addType( DEFAULT_STRUCTURE_CLASS );
  -        }
  -
       }
   
      /**
  
  
  
  1.18      +7 -7      
jakarta-avalon-excalibur/assembly/src/java/org/apache/excalibur/merlin/container/Container.java
  
  Index: Container.java
  ===================================================================
  RCS file: 
/home/cvs/jakarta-avalon-excalibur/assembly/src/java/org/apache/excalibur/merlin/container/Container.java,v
  retrieving revision 1.17
  retrieving revision 1.18
  diff -u -r1.17 -r1.18
  --- Container.java    31 Aug 2002 14:52:21 -0000      1.17
  +++ Container.java    7 Sep 2002 07:27:11 -0000       1.18
  @@ -41,12 +41,6 @@
       static final String DESCRIPTOR_KEY = "merlin:container.descriptor";
   
      /**
  -    * Context key used to locate the logging manager.
  -    * @see org.apache.excalibur.merlin.assembly.DefaultLoggerManager
  -    */
  -    static final String LOGGING_KEY = "merlin:container.logging";
  -
  -   /**
       * Context key used to locate the container services map associating 
       * container descriptors as keys against container resources
       * @see java.util.Map
  @@ -54,6 +48,12 @@
       * @see org.apache.excalibur.merlin.container.ContainerResource
       */
       static final String SERVICES_KEY = "merlin:container.services";
  +
  +   /**
  +    * Context key used to locate the service management context.
  +    * @see org.apache.excalibur.merlin.service.ServiceManagementContext
  +    */
  +    static final String REGISTRY_KEY = "merlin:container.registry";
   
      /**
       * Adds a <code>StateListener</code> to the container.
  
  
  
  1.7       +46 -255   
jakarta-avalon-excalibur/assembly/src/java/org/apache/excalibur/merlin/container/ContainerFactory.java
  
  Index: ContainerFactory.java
  ===================================================================
  RCS file: 
/home/cvs/jakarta-avalon-excalibur/assembly/src/java/org/apache/excalibur/merlin/container/ContainerFactory.java,v
  retrieving revision 1.6
  retrieving revision 1.7
  diff -u -r1.6 -r1.7
  --- ContainerFactory.java     31 Aug 2002 14:54:00 -0000      1.6
  +++ ContainerFactory.java     7 Sep 2002 07:27:11 -0000       1.7
  @@ -3,270 +3,61 @@
    *
    * 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.
  + * the LICENSE.TXT file.
  + *
  + * Original contribution by OSM SARL, http://www.osm.net
    */
  -
   package org.apache.excalibur.merlin.container;
   
  -import java.util.Map;
  -import java.util.Hashtable;
  -import java.util.ArrayList;
  -
  -import org.apache.avalon.excalibur.i18n.ResourceManager;
  -import org.apache.avalon.excalibur.i18n.Resources;
  -import org.apache.avalon.framework.logger.AbstractLogEnabled;
  -import org.apache.avalon.framework.configuration.Configuration;
  -import org.apache.avalon.framework.context.DefaultContext;
  -import org.apache.excalibur.meta.info.Type;
  -import org.apache.excalibur.merlin.assembly.KernelManager;
  -import org.apache.excalibur.merlin.assembly.TypeException;
  +import org.apache.avalon.framework.context.Context;
   import org.apache.excalibur.merlin.assembly.ContainerManager;
  -import org.apache.excalibur.merlin.assembly.DefaultLoggerManager;
  -import org.apache.excalibur.merlin.model.ContainerDescriptor;
  -import org.apache.excalibur.merlin.model.ClasspathDescriptor;
  +import org.apache.excalibur.merlin.resource.ResourceFactory;
  +import org.apache.excalibur.merlin.resource.LifestyleHandler;
   import org.apache.excalibur.merlin.model.Profile;
  -import org.apache.excalibur.merlin.model.builder.XMLContainerCreator;
  -import org.apache.excalibur.merlin.resource.LifestyleManager;
  -import org.apache.excalibur.merlin.container.ContainerResource;
  +import org.apache.excalibur.merlin.model.Profile;
  +import org.apache.excalibur.merlin.model.Resource;
   
   /**
  - * Utility class that provides support for the creation of containers
  - * based on configuration criteria or meta-data. A ContainerFactory 
  - * provides support for the establishment of subsidiary containers 
  - * relative to a parent (where the parant may be kerenl or parent
  - * container).
  + * Default resource factory.
    *
  - * @author <a href="mailto:[EMAIL PROTECTED]">Stephen McConnell</a>
  - * @version $Revision$ $Date$
  + * @author <a href="mailto:[EMAIL PROTECTED]">Stephen McConnell</a>
    */
  -public class ContainerFactory extends AbstractLogEnabled
  +public class ContainerFactory implements ResourceFactory
   {
  -    //=======================================================================
  -    // static
  -    //=======================================================================
  -
  -    private static final Resources REZ =
  -        ResourceManager.getPackageResources( ContainerFactory.class );
  -
  -    //=======================================================================
  -    // state
  -    //=======================================================================
  -
  -   /**
  -    * Utility class that provides support for marshalling an XML 
configuration
  -    * into meta-data and meta-info instances.
  -    */
  -    private XMLContainerCreator m_creator = new XMLContainerCreator();
  -
  -   /**
  -    * Constructor supplied reference to the type manager.
  -    */
  -    private ContainerManager m_manager;
  -
  -   /**
  -    * The logging manager to pass to the created container.
  -    */
  -    private DefaultLoggerManager m_logging;
  -
  -   /**
  -    * The logging manager to pass to the created container.
  -    */
  -    private LifestyleManager m_lifestyles;
  -
  -    //=======================================================================
  -    // constructor
  -    //=======================================================================
  -
  -   /**
  -    * Creation of a container factory that supports the creation of 
  -    * container reference instances.
  -    *
  -    * @param manager the context type manager
  -    * @param logging the logging manager
  -    */
  -    public ContainerFactory( 
  -                        ContainerManager manager, 
  -                        DefaultLoggerManager logging )
  -    {
  -        this( manager, logging, null );
  -    }
  -
  -   /**
  -    * Creation of a container factory that supports the creation of 
  -    * new container references.
  -    *
  -    * @param manager the context type manager
  -    * @param logging the logging manager
  -    * @param lifestyles the lifestyle manager
  -    * @exception NullPointerException if the manager or logging arguments 
are null
  -    */
  -    public ContainerFactory( 
  -                        ContainerManager manager, 
  -                        DefaultLoggerManager logging,
  -                        LifestyleManager lifestyles )
  -      throws NullPointerException
  -       
  -    {
  -        if( manager == null )
  -        {
  -            throw new NullPointerException("manager");
  -        }
  -
  -        if( logging == null )
  -        {
  -            throw new NullPointerException("logging");
  -        }
  -
  -        m_manager = manager;
  -        m_logging = logging;
  -        m_lifestyles = lifestyles;
  -    }
  -
  -   /**
  -    * Creation of a ContainerReference based on a container descriptor and 
classpath
  -    * definition.  The ContainerReference returned from this is a delegate 
to an 
  -    * actual container and manages the execution of the container under a 
seperate
  -    * thread of execution.
  -    *
  -    * @param descriptor the subsidiary container descriptor
  -    * @param classpath the classpath descriptor
  -    * @return the resource holding the container 
  -    *
  -    * @exception Exception is an error occurs
  -    * @exception NullPointerException if the descriptor or classpath 
argument is null
  -    */
  -    public ContainerResource build( 
  -                         ContainerDescriptor descriptor, 
  -                         ClasspathDescriptor classpath ) 
  -      throws Exception, NullPointerException
  -    {
  -        if( descriptor == null )
  -        {
  -            throw new NullPointerException( "descriptor" );
  -        }
  -
  -        if( classpath == null )
  -        {
  -            throw new NullPointerException( "classpath" );
  -        }
  -
  -        final ContainerManager manager = 
  -          m_manager.createContainerManager( descriptor, classpath, 
m_lifestyles );
  -
  -        return createContainerResource( descriptor, manager, new Hashtable() 
);
  -    }
  -
  -
  -   /**
  -    * Create a container resource.
  -    *
  -    * @param config the container configuration
  -    * @return the <code>ContainerResource</code>
  -    * @exception Exception if an error occurs
  -    */
  -    public ContainerResource build( Configuration config )
  -      throws Exception
  -    {
  -
  -        final String name = 
  -          config.getAttribute( "name" );
  -
  -        final String classname = 
  -          config.getAttribute( "class", DefaultContainer.class.getName() );
  -
  -        try
  -        {
  -            //
  -            // create the empty container descriptor
  -            //
  -
  -            Type type = m_manager.getType( classname );
  -            ContainerDescriptor descriptor = 
  -              m_creator.createContainerDescriptor( type, config );
  -
  -            //
  -            // create the container manager
  -            //
  -
  -            final ClasspathDescriptor classpath = 
  -              m_creator.createClasspathDescriptor( 
config.getChild("classpath") );
  -
  -            final ContainerManager manager = 
  -              m_manager.createContainerManager( descriptor, classpath, 
m_lifestyles );
  -
  -            //
  -            // populate the descriptor with component profiles
  -            //
  -
  -            Configuration[] components = config.getChildren("component");
  -            for( int i=0; i<components.length; i++ )
  -            {
  -                final Configuration component = components[i];
  -                final String c = component.getAttribute("class");
  -                try
  -                {
  -                    final Type t = manager.getType( c );
  -                    final Profile profile = m_creator.createProfile( t, 
component );
  -                    descriptor.addComponent( profile );
  -                    manager.addProfile( profile );
  -                }
  -                catch( TypeException e )
  -                {
  -                    final String warning =
  -                      "Ignoring component declaration at " 
  -                      + component.getLocation() 
  -                      + " due to unknown type: " + c;
  -                    getLogger().warn( warning );
  -                }
  -            }
  -
  -            //
  -            // populate the descriptor with subsidiary container descriptors
  -            //
  -
  -            Map map = new Hashtable();
  -            ContainerFactory factory = new ContainerFactory( manager, 
m_logging );
  -            factory.enableLogging( getLogger().getChildLogger( 
descriptor.getName() ) );
  -
  -            Configuration[] containers = config.getChildren("container");
  -            for( int i=0; i<containers.length; i++ )
  -            {
  -                final Configuration container = containers[i];
  -                ContainerResource resource = factory.build( container );
  -                ContainerDescriptor child = (ContainerDescriptor) 
resource.getProfile();
  -                descriptor.addContainer( child );
  -                map.put( child, resource );
  -            }
  -            return createContainerResource( descriptor, manager, map );
  -
  -        }
  -        catch( Throwable e )
  -        {
  -            final String error = "Error building container descriptor.";
  -            throw new ContainerException( error, e );
  -        }
  -    }
  -
  -    private ContainerResource createContainerResource( 
  -                     ContainerDescriptor descriptor, 
  -                     ContainerManager manager, 
  -                     Map services ) throws Exception
  -    {
  -        //
  -        // create the container context
  -        //
  -
  -        DefaultContext context = new DefaultContext();
  -        context.put( Container.MANAGER_KEY, manager );
  -        context.put( Container.DESCRIPTOR_KEY, descriptor );
  -        context.put( Container.LOGGING_KEY, m_logging );
  -        context.put( Container.SERVICES_KEY, services );
  +    /**
  +     * Creation of a new container resource.
  +     * 
  +     * @param manager the type manager
  +     * @param profile the component profile
  +     * @param context the deployment context
  +     * @param handler the lifestyle handler
  +     * @return the resource instance
  +     * @exception NullPointerException if any of the supplied arguments are 
null
  +     */
  +     public Resource createResource( 
  +                      ContainerManager manager, 
  +                      Profile profile, 
  +                      Context context, 
  +                      LifestyleHandler handler ) throws NullPointerException
  +     {
  +         if( manager == null )
  +         {
  +             throw new NullPointerException( "manager" );
  +         }
  +         if( profile == null )
  +         {
  +             throw new NullPointerException( "profile" );
  +         }
  +         if( context == null )
  +         {
  +             throw new NullPointerException( "context" );
  +         }
  +         if( handler == null )
  +         {
  +             throw new NullPointerException( "handler" );
  +         }
   
  -        //
  -        // assemble the descriptor to ensure that all dependecies are 
  -        // resolved and return a reference to the container
  -        //
  +         return new ContainerResource( manager, profile, context, handler );
  +     }
   
  -        return (ContainerResource) m_manager.assemble( descriptor, context );
  -    }
  -}
  +}
  \ No newline at end of file
  
  
  
  1.38      +109 -104  
jakarta-avalon-excalibur/assembly/src/java/org/apache/excalibur/merlin/container/DefaultContainer.java
  
  Index: DefaultContainer.java
  ===================================================================
  RCS file: 
/home/cvs/jakarta-avalon-excalibur/assembly/src/java/org/apache/excalibur/merlin/container/DefaultContainer.java,v
  retrieving revision 1.37
  retrieving revision 1.38
  diff -u -r1.37 -r1.38
  --- DefaultContainer.java     31 Aug 2002 14:50:11 -0000      1.37
  +++ DefaultContainer.java     7 Sep 2002 07:27:11 -0000       1.38
  @@ -8,9 +8,10 @@
   
   package org.apache.excalibur.merlin.container;
   
  +import java.net.URL;
   import java.util.Map;
   import java.util.List;
  -import java.util.LinkedList;
  +import java.util.Hashtable;
   import java.util.ArrayList;
   import java.util.Iterator;
   
  @@ -29,7 +30,6 @@
   import org.apache.avalon.framework.context.ContextException;
   import org.apache.excalibur.merlin.assembly.AssemblyException;
   import org.apache.excalibur.merlin.assembly.ContainerManager;
  -import org.apache.excalibur.merlin.assembly.DefaultLoggerManager;
   import org.apache.excalibur.merlin.assembly.DependencyGraph;
   import org.apache.excalibur.merlin.model.ContainerDescriptor;
   import org.apache.excalibur.merlin.model.ClasspathDescriptor;
  @@ -37,6 +37,9 @@
   import org.apache.excalibur.merlin.model.Resource;
   import org.apache.excalibur.merlin.model.builder.XMLContainerCreator;
   import org.apache.excalibur.merlin.container.ContainerResource;
  +import org.apache.excalibur.merlin.service.Handler;
  +import org.apache.excalibur.merlin.service.ServiceURLFactory;
  +import org.apache.excalibur.merlin.service.ServiceManagementContext;
   
   /**
    * Default container implementation that manages a registry of componet 
providers and 
  @@ -49,7 +52,7 @@
    */
   public class DefaultContainer extends AbstractLogEnabled implements 
Container, 
     Contextualizable, Configurable, Structural, Initializable, Startable, 
Suspendable, 
  -  Disposable, StateListener
  +  Disposable
   {
       //=======================================================================
       // static
  @@ -71,7 +74,7 @@
      /**
       * The list of initialized embedded containers wrapped in Container 
instances.
       */
  -    private List m_containers = new LinkedList();
  +    private Map m_containers = new Hashtable();
   
      /**
       * The classloader resolved from the meta model.
  @@ -114,19 +117,28 @@
       private ArrayList m_containerListeners = new ArrayList();
   
      /**
  -    * The thread group holding the threads of the subsidiary containers.
  +    * The map from which we determin the startup and shutdown sequence.
  +    * (only relevant when launching components with startup policy and even
  +    * then it isn't mandatory due to lifecycle encapsulation).
       */
  -    private ThreadGroup m_threadGroup;
  -
  -    private ContainerFactory m_factory;
  +    private DependencyGraph m_map;
   
  -    private DefaultLoggerManager m_logging;
  +   /**
  +    * A map of container descriptors keys and corresponding container 
resource
  +    * values.
  +    */
  +    private Map m_services;
   
  -    private Throwable m_error;
  +   /**
  +    * The service management context into which resources are bound.
  +    */
  +    private ServiceManagementContext m_registry;
   
  -    private DependencyGraph m_map;
  +   /**
  +    * Flag indicating if the container has been through the assembly stage.
  +    */
  +    private boolean m_assembled = false;
   
  -    private Map m_services;
   
       //=======================================================================
       // Contextualizable
  @@ -143,8 +155,6 @@
       *         [EMAIL PROTECTED] ContainerDescriptor} (REQUIRED}</li>
       *  <li>[EMAIL PROTECTED] #SERVICES_KEY} the container services 
       *         [EMAIL PROTECTED] Map} (REQUIRED}</li>
  -    *  <li>[EMAIL PROTECTED] #LOGGING_KEY} the logging manager 
  -    *          [EMAIL PROTECTED] DefaultLoggerManager} (REQUIRED}</li>
       * </ul>
       * @param context the service context value
       * @exception ContextException if a contextualization error occurs 
  @@ -153,8 +163,8 @@
       {
           m_manager = (ContainerManager) context.get( MANAGER_KEY );
           m_descriptor = (ContainerDescriptor) context.get( DESCRIPTOR_KEY );
  -        m_logging = (DefaultLoggerManager) context.get( LOGGING_KEY );
           m_services = (Map) context.get( SERVICES_KEY );
  +        m_registry = (ServiceManagementContext) context.get( REGISTRY_KEY );
   
           //
           // set the context classloader
  @@ -166,7 +176,6 @@
               + "' with context type manager: '" + 
Thread.currentThread().getContextClassLoader()
               + "'.");
   
  -        m_factory = new ContainerFactory( m_manager, m_logging );
       }
   
       //=======================================================================
  @@ -220,6 +229,8 @@
               final String error = "Assembly failure.";
               throw new AssemblyException( error, e );
           }
  +
  +        m_assembled = true;
       }
   
       //=======================================================================
  @@ -238,21 +249,33 @@
           {
               throw new IllegalStateException("Container has not been 
contextualized.");
           }
  -        if( m_map == null )
  +        if( !m_assembled )
           {
               final String error = 
                 "Container has not been assembled.";
               throw new IllegalStateException( error );
           }
  +
           if( m_state >= StateEvent.INITIALIZED ) 
           {
               return;
           }
   
           //
  -        // creation of the subsidiary containers
  +        // register exportable resources into the service management context
           //
   
  +        Resource[] resources = getResources();
  +        for( int i=0; i<resources.length; i++ )
  +        {
  +            Resource resource = resources[i];
  +            getLogger().debug( "registering resource: " + 
resource.getProfile().getName() );
  +            m_registry.bind( resource );
  +        }
  +
  +        //
  +        // creation of the subsidiary containers
  +        //
   
           ContainerDescriptor[] containers = m_descriptor.getContainers();
           getLogger().info("subsidiary container creation (" + 
containers.length + ")" );
  @@ -269,12 +292,11 @@
               }
   
               //
  -            // add ourselves as a state listener to the embedded container 
  -            // and request its instantiation
  +            // instantiate the container
               //
   
  -            resource.addStateListener( this );
  -            resource.access();
  +            Container container = (Container) resource.access();
  +            m_containers.put( descriptor, container );
           }
   
           //
  @@ -283,6 +305,7 @@
           //
   
           m_state = StateEvent.INITIALIZED;
  +
           fireStateChange( new StateEvent( this, m_descriptor.getName(), 
StateEvent.INITIALIZED ) );
       }
   
  @@ -317,7 +340,6 @@
           // request startup of any unstarted components
           //
   
  -        //m_manager.start( m_map.getStartupGraph() );
           m_manager.start();
   
           //
  @@ -327,14 +349,12 @@
           getLogger().info("initiating startup of " + m_containers.size() + " 
subsidiary containers.");
           synchronized( m_containers )
           {
  -            Iterator iterator = m_containers.iterator();
  +            Iterator iterator = m_containers.keySet().iterator();
               while( iterator.hasNext() )
               {
  -                Object next = iterator.next();
  -                if( next instanceof Startable )
  -                {
  -                    ((Container)next).start();
  -                }
  +                ContainerDescriptor next = (ContainerDescriptor) 
iterator.next();
  +                Container container = (Container) m_containers.get( next );
  +                container.start();
               }
           }
   
  @@ -375,24 +395,12 @@
   
           synchronized( m_containers )
           {
  -            Iterator iterator = m_containers.iterator();
  +            Iterator iterator = m_containers.keySet().iterator();
               while( iterator.hasNext() )
               {
  -                Object next = iterator.next();
  -                if( next instanceof Startable )
  -                {
  -                    try
  -                    {
  -                        ((Container)next).stop();
  -                    }
  -                    catch( Throwable e )
  -                    {
  -                        final String warning = 
  -                          "Failed to stop sub-container: " 
  -                          + ((Container)next);
  -                        getLogger().warn( warning, e );
  -                    }
  -                }
  +                ContainerDescriptor next = (ContainerDescriptor) 
iterator.next();
  +                Container container = (Container) m_containers.get( next );
  +                container.stop();
               }
           }
   
  @@ -433,15 +441,12 @@
   
           synchronized( m_containers )
           {
  -            Iterator iterator = m_containers.iterator();
  -
  +            Iterator iterator = m_containers.keySet().iterator();
               while( iterator.hasNext() )
               {
  -                Object next = iterator.next();
  -                if( next instanceof Suspendable )
  -                {
  -                    ((Container)next).suspend();
  -                }
  +                ContainerDescriptor next = (ContainerDescriptor) 
iterator.next();
  +                Container container = (Container) m_containers.get( next );
  +                container.suspend();
               }
           }
   
  @@ -475,7 +480,6 @@
           try
           {
               m_manager.start( );
  -            //m_manager.start( m_map.getStartupGraph() );
           }
           catch( Throwable e )
           {
  @@ -489,15 +493,12 @@
   
           synchronized( m_containers )
           {
  -            Iterator iterator = m_containers.iterator();
  -
  +            Iterator iterator = m_containers.keySet().iterator();
               while( iterator.hasNext() )
               {
  -                Object next = iterator.next();
  -                if( next instanceof Suspendable )
  -                {
  -                    ((Container)next).resume();
  -                }
  +                ContainerDescriptor next = (ContainerDescriptor) 
iterator.next();
  +                Container container = (Container) m_containers.get( next );
  +                container.resume();
               }
           }
   
  @@ -507,42 +508,6 @@
       }
   
       //=======================================================================
  -    // StateListener
  -    //=======================================================================
  -
  -   /**
  -    * Method invoked when the root container state changes.  When subsidiary
  -    * containers transition to intialized state they will be published
  -    * by this container under a [EMAIL PROTECTED] ContainerEvent} event.
  -    * @param event the event norifying us of a subsidiary container state 
change
  -    */
  -    public void stateChanged( StateEvent event )
  -    {
  -        int state = event.getState();
  -        Container container = (Container) event.getSource();
  -        switch( state )
  -        {
  -            case StateEvent.INITIALIZED:
  -                synchronized( m_containers )
  -                {
  -                    m_containers.add( container );
  -                }
  -                fireStructuralChange( 
  -                  new ContainerEvent( this, container, ContainerEvent.ADD ) 
); 
  -                break;
  -            case StateEvent.DISPOSED:
  -                synchronized( m_containers )
  -                {
  -                    getLogger().debug(
  -                      "removing subsidiary container: " + event.getName() );
  -                    m_containers.remove( container );
  -                }
  -                fireStructuralChange( 
  -                  new ContainerEvent( this, container, ContainerEvent.REMOVE 
) );
  -        }
  -    }
  -
  -    //=======================================================================
       // Container
       //=======================================================================
   
  @@ -599,12 +564,11 @@
       *
       * @return the set of exported resources
       */
  -/*
       public Resource[] getResources()
       {
  -        if( m_state < StateEvent.INITIALIZED )
  +        if( !m_assembled )
           {
  -          throw new IllegalStateException("not-initialized");
  +          throw new IllegalStateException("pre-assembly");
           }
   
           ArrayList list = new ArrayList();
  @@ -613,9 +577,10 @@
           {
               list.add( local[i] );
           }
  +        /*
           synchronized( m_containers )
           {
  -            Iterator iterator = m_containers.iterator();
  +            Iterator iterator = m_containers.entrySet().iterator();
               while( iterator.hasNext() )
               {
                   Container container = (Container)iterator.next();
  @@ -630,9 +595,9 @@
                   }
               }
           }
  +        */
           return (Resource[]) list.toArray( new Resource[0] );
       }
  -*/
   
      /**
       * Returns the set of subsidiary continers container within this 
container.
  @@ -643,10 +608,34 @@
       {
           synchronized( m_containers )
           {
  -            return (Container[]) m_containers.toArray( new Container[0] );
  +            return (Container[]) m_containers.entrySet().toArray( new 
Container[0] );
  +        }
  +    }
  +
  +   /**
  +    * Returns a reference to a subsidiary container.
  +    *
  +    * @param name the container name
  +    * @return the container of null if the name is unknown
  +    */
  +    protected Container getContainer( String name )
  +    {
  +        synchronized( m_containers )
  +        {
  +            Iterator iterator = m_containers.keySet().iterator();
  +            while( iterator.hasNext() )
  +            {
  +                ContainerDescriptor profile = 
(ContainerDescriptor)iterator.next();
  +                if( profile.getName().equals(name ) )
  +                {
  +                    return (Container) m_containers.get( profile );
  +                }
  +            }
           }
  +        return null;
       }
   
  +
      /**
       * Add and assemble the supplied set of profiles.
       * @param profiles the profiles to assemble
  @@ -675,6 +664,21 @@
           }
   
           m_manager.install( profiles );
  +
  +        Resource[] resources = getResources();
  +        for( int i=0; i<resources.length; i++ )
  +        {
  +            Resource resource = resources[i];
  +            try
  +            {
  +                m_registry.bind( resource );
  +                getLogger().debug( "registering resource: " + 
resource.getProfile().getName() );
  +            }
  +            catch( IllegalArgumentException iae )
  +            {
  +                // ignore it - just means that its a reference to an 
existing resource
  +            }
  +        }
       }
   
       //=======================================================================
  @@ -718,7 +722,7 @@
           // dispose of all of the nested containers
           //
   
  -        Object[] containers = m_containers.toArray();
  +        Object[] containers = m_containers.entrySet().toArray();
           for( int i=0; i<containers.length; i++ )
           {
               Object object = containers[i];
  @@ -732,6 +736,7 @@
           getLogger().debug("done");
           m_state = StateEvent.DISPOSED;
           fireStateChange( new StateEvent( this, m_descriptor.getName(), 
StateEvent.DISPOSED, error ) );
  +        m_containers.clear();
       }
   
       //=======================================================================
  
  
  
  1.11      +2 -2      
jakarta-avalon-excalibur/assembly/src/java/org/apache/excalibur/merlin/container/DefaultContainer.xinfo
  
  Index: DefaultContainer.xinfo
  ===================================================================
  RCS file: 
/home/cvs/jakarta-avalon-excalibur/assembly/src/java/org/apache/excalibur/merlin/container/DefaultContainer.xinfo,v
  retrieving revision 1.10
  retrieving revision 1.11
  diff -u -r1.10 -r1.11
  --- DefaultContainer.xinfo    27 Aug 2002 11:08:26 -0000      1.10
  +++ DefaultContainer.xinfo    7 Sep 2002 07:27:11 -0000       1.11
  @@ -26,14 +26,14 @@
       <entry key="merlin:container.manager"
         type="org.apache.excalibur.merlin.assembly.ContainerManager"/>
       <entry key="merlin:container.services" type="java.util.Map"/>
  +    <entry key="merlin:container.registry" 
  +      type="org.apache.excalibur.merlin.service.ServiceManagementContext"/>
       <entry key="merlin:container.state-listener" 
         type="org.apache.excalibur.merlin.container.StateListener" 
         optional="true"/>
       <entry key="merlin:container.container-listener" 
         type="org.apache.excalibur.merlin.container.ContainerListener" 
         optional="true"/>
  -    <entry key="merlin:container.logging" 
  -      type="org.apache.excalibur.merlin.assembly.DefaultLoggerManager"/>
     </context>
   
     <services>
  
  
  
  1.1                  
jakarta-avalon-excalibur/assembly/src/java/org/apache/excalibur/merlin/container/ContainerHelper.java
  
  Index: ContainerHelper.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.excalibur.merlin.container;
  
  import java.util.Map;
  import java.util.Hashtable;
  import java.util.ArrayList;
  
  import org.apache.avalon.excalibur.i18n.ResourceManager;
  import org.apache.avalon.excalibur.i18n.Resources;
  import org.apache.avalon.framework.logger.AbstractLogEnabled;
  import org.apache.avalon.framework.configuration.Configuration;
  import org.apache.avalon.framework.context.DefaultContext;
  import org.apache.excalibur.meta.info.Type;
  import org.apache.excalibur.merlin.assembly.KernelManager;
  import org.apache.excalibur.merlin.assembly.TypeException;
  import org.apache.excalibur.merlin.assembly.ContainerManager;
  import org.apache.excalibur.merlin.assembly.DefaultLoggerManager;
  import org.apache.excalibur.merlin.model.ContainerDescriptor;
  import org.apache.excalibur.merlin.model.ClasspathDescriptor;
  import org.apache.excalibur.merlin.model.Profile;
  import org.apache.excalibur.merlin.model.builder.XMLContainerCreator;
  import org.apache.excalibur.merlin.resource.LifestyleManager;
  import org.apache.excalibur.merlin.container.ContainerResource;
  import org.apache.excalibur.merlin.service.ServiceManagementContext;
  
  /**
   * Utility class that provides support for the creation of containers
   * based on configuration criteria or meta-data. A ContainerHelper 
   * provides support for the establishment of subsidiary containers 
   * relative to a parent (where the parant may be kerenl or parent
   * container).
   *
   * @author <a href="mailto:[EMAIL PROTECTED]">Stephen McConnell</a>
   * @version $Revision: 1.1 $ $Date: 2002/09/07 07:27:11 $
   */
  public class ContainerHelper extends AbstractLogEnabled 
  {
      //=======================================================================
      // static
      //=======================================================================
  
      private static final Resources REZ =
          ResourceManager.getPackageResources( ContainerHelper.class );
  
      //=======================================================================
      // state
      //=======================================================================
  
     /**
      * Utility class that provides support for marshalling an XML configuration
      * into meta-data and meta-info instances.
      */
      private XMLContainerCreator m_creator = new XMLContainerCreator();
  
     /**
      * Constructor supplied reference to the type manager.
      */
      private ContainerManager m_manager;
  
     /**
      * The logging manager to pass to the created container.
      */
  
     /**
      * The logging manager to pass to the created container.
      */
      private LifestyleManager m_lifestyles;
  
     /**
      * The service manager.
      */
      private ServiceManagementContext m_registry;
  
      //=======================================================================
      // constructor
      //=======================================================================
  
     /**
      * Creation of a container factory that supports the creation of 
      * container reference instances.
      *
      * @param manager the context type manager
      * @param logging the logging manager
      */
      public ContainerHelper( 
                          ContainerManager manager, 
                          ServiceManagementContext context )
      {
          this( manager, null, context );
      }
  
     /**
      * Creation of a container factory that supports the creation of 
      * new container references.
      *
      * @param manager the context type manager
      * @param lifestyles the lifestyle manager
      * @param context the service management context
      * @exception NullPointerException if the manager arguments is null
      */
      public ContainerHelper( 
                          ContainerManager manager, 
                          LifestyleManager lifestyles,
                          ServiceManagementContext context )
        throws NullPointerException
      {
          if( manager == null )
          {
              throw new NullPointerException("manager");
          }
  
          m_manager = manager;
          m_lifestyles = lifestyles;
          m_registry = context;
      }
  
  
  
     /**
      * Create a container resource.
      *
      * @param config the container configuration
      * @return the <code>ContainerResource</code>
      * @exception Exception if an error occurs
      */
      public ContainerResource build( Configuration config )
        throws Exception
      {
  
          final String name = 
            config.getAttribute( "name" );
  
          final String classname = 
            config.getAttribute( "class", DefaultContainer.class.getName() );
  
          try
          {
              //
              // create the empty container descriptor
              //
  
              Type type = m_manager.getType( classname );
  
              ContainerDescriptor descriptor = 
                m_creator.createContainerDescriptor( type, config );
  
              //
              // create the container manager
              //
  
              final ClasspathDescriptor classpath = 
                m_creator.createClasspathDescriptor( 
config.getChild("classpath") );
  
              final ContainerManager manager = 
                m_manager.createContainerManager( descriptor, classpath, 
m_lifestyles );
  
              //
              // populate the descriptor with component profiles
              //
  
              Configuration[] components = config.getChildren("component");
              for( int i=0; i<components.length; i++ )
              {
                  final Configuration component = components[i];
                  final String c = component.getAttribute("class");
                  try
                  {
                      final Type t = manager.getType( c );
                      final Profile profile = m_creator.createProfile( t, 
component );
                      descriptor.addComponent( profile );
                      manager.addProfile( profile );
                  }
                  catch( TypeException e )
                  {
                      final String warning =
                        "Ignoring component declaration at " 
                        + component.getLocation() 
                        + " due to unknown type: " + c;
                      getLogger().warn( warning );
                  }
              }
  
              //
              // populate the descriptor with subsidiary container descriptors
              //
  
              Map map = new Hashtable();
              ContainerHelper factory = new ContainerHelper( 
                manager, m_registry.createChild( descriptor.getName() ) );
              factory.enableLogging( getLogger().getChildLogger( 
descriptor.getName() ) );
  
              Configuration[] containers = config.getChildren("container");
              for( int i=0; i<containers.length; i++ )
              {
                  final Configuration container = containers[i];
                  ContainerResource resource = factory.build( container );
                  ContainerDescriptor child = (ContainerDescriptor) 
resource.getProfile();
                  descriptor.addContainer( child );
                  map.put( child, resource );
              }
              return createContainerResource( descriptor, manager, map );
  
          }
          catch( Throwable e )
          {
              final String error = "Error building container descriptor.";
              throw new ContainerException( error, e );
          }
      }
  
      private ContainerResource createContainerResource( 
                       ContainerDescriptor descriptor, 
                       ContainerManager manager, 
                       Map services ) throws Exception
      {
          //
          // create the container context
          //
  
          DefaultContext context = new DefaultContext();
          context.put( Container.MANAGER_KEY, manager );
          context.put( Container.DESCRIPTOR_KEY, descriptor );
          context.put( Container.SERVICES_KEY, services );
          context.put( Container.REGISTRY_KEY, m_registry );
  
          //
          // assemble the descriptor to ensure that all dependecies are 
          // resolved and return a reference to the container
          //
  
          return (ContainerResource) m_manager.assemble( descriptor, context );
      }
  }
  
  
  
  1.48      +34 -10    
jakarta-avalon-excalibur/assembly/src/java/org/apache/excalibur/merlin/kernel/DefaultKernel.java
  
  Index: DefaultKernel.java
  ===================================================================
  RCS file: 
/home/cvs/jakarta-avalon-excalibur/assembly/src/java/org/apache/excalibur/merlin/kernel/DefaultKernel.java,v
  retrieving revision 1.47
  retrieving revision 1.48
  diff -u -r1.47 -r1.48
  --- DefaultKernel.java        31 Aug 2002 14:54:00 -0000      1.47
  +++ DefaultKernel.java        7 Sep 2002 07:27:11 -0000       1.48
  @@ -12,6 +12,7 @@
   import java.util.ArrayList;
   import java.io.FileInputStream;
   import java.io.InputStream;
  +import java.net.URL;
   
   import org.apache.avalon.framework.logger.Logger;
   import org.apache.avalon.framework.logger.LogEnabled;
  @@ -33,7 +34,7 @@
   import org.apache.excalibur.merlin.assembly.KernelManager;
   import org.apache.excalibur.merlin.assembly.DefaultLoggerManager;
   import org.apache.excalibur.merlin.container.Container;
  -import org.apache.excalibur.merlin.container.ContainerFactory;
  +import org.apache.excalibur.merlin.container.ContainerHelper;
   import org.apache.excalibur.merlin.model.verifier.AssemblyVerifier;
   import org.apache.excalibur.merlin.model.verifier.MetaDataVerifier;
   import org.apache.excalibur.merlin.model.builder.XMLContainerCreator;
  @@ -44,8 +45,11 @@
   import org.apache.excalibur.merlin.model.Profile;
   import org.apache.excalibur.merlin.model.Resource;
   import org.apache.excalibur.merlin.container.ContainerResource;
  +import org.apache.excalibur.merlin.service.ServiceURLFactory;
   import org.apache.excalibur.merlin.resource.LifestyleManager;
   import org.apache.excalibur.merlin.resource.DefaultLifestyleManager;
  +import org.apache.excalibur.merlin.service.ServiceManagementContext;
  +import org.apache.excalibur.merlin.service.DefaultServiceManagementContext;
   import org.apache.excalibur.meta.verifier.VerifyException;
   import org.apache.excalibur.mpool.DefaultPoolManager;
   import org.apache.excalibur.mpool.PoolManager;
  @@ -109,6 +113,7 @@
     implements Kernel, Contextualizable, Configurable, Initializable, 
Startable, 
     Disposable
   {
  +
       //=======================================================================
       // state
       //=======================================================================
  @@ -186,6 +191,8 @@
   
       private File m_baseDirectory;
   
  +    private ServiceManagementContext m_registry;
  +
       //=======================================================================
       // Contextualizable
       //=======================================================================
  @@ -284,7 +291,7 @@
           ClassLoader classloader = 
Thread.currentThread().getContextClassLoader();
           final Configuration config = m_config.getChild("container");
           String name = config.getAttribute("name");
  -
  +        String domain = 
m_config.getChild("system").getChild("host").getValue("localhost");
   
           //
           // If this kernel has been created inside container scope then
  @@ -295,13 +302,12 @@
           if( classloader instanceof ContainerManager )
           {
               ContainerManager manager = (ContainerManager) classloader;
  -System.out.println("## creating a nested kernel in: " + manager );
   
               m_base = manager.getPath().replace('/','.').substring(1) + "." + 
name;
               m_logger = getLoggingManager().getLoggerForCategory( m_base );
               m_localLogger = m_logger.getChildLogger("kernel");
   
  -            ContainerFactory factory = new ContainerFactory( manager, 
getLoggingManager() );
  +            ContainerHelper factory = new ContainerHelper( manager, 
m_registry );
               factory.enableLogging( m_logger );
   
               ContainerResource resource = factory.build( config );
  @@ -318,6 +324,8 @@
   
           try
           {
  +
  +
               LoggingDescriptor logging =
                 m_creator.createLoggingDescriptor( 
m_config.getChild("logging"), name );
               c_logging = new DefaultLoggerManager( logging, m_baseDirectory );
  @@ -335,8 +343,16 @@
               m_localLogger = m_logger.getChildLogger("kernel");
   
               //
  +            // Create the service management context.
  +            //
  +
  +            m_registry = new DefaultServiceManagementContext( null, "/" );
  +            URL.setURLStreamHandlerFactory( new ServiceURLFactory( domain, 
m_registry ) );
  +
  +            //
               // Set up the ThreadManager that the CommandManager uses
               //
  +
               m_threadManager = new TPCThreadManager();
               m_threadManager.enableLogging( 
getLogger().getChildLogger("threadmanager") );
               Parameters params = new Parameters();
  @@ -349,12 +365,14 @@
               //
               // Set up the CommandManager that the PoolManager uses.
               //
  +
               m_commandManager = new CommandManager();
               m_threadManager.register( m_commandManager );
   
               //
               // Set up the PoolManager that the pooled lifecycle helper needs
               //
  +
               m_poolManager = new DefaultPoolManager( 
m_commandManager.getCommandQueue() );
   
               //
  @@ -438,8 +456,8 @@
               // setup the root container
               //
   
  -            ContainerFactory factory =
  -              new ContainerFactory( m_manager, getLoggingManager(), 
lifestyles );
  +            ContainerHelper factory =
  +              new ContainerHelper( m_manager, lifestyles, m_registry );
               factory.enableLogging( m_logger );
   
               ContainerResource resource = factory.build( config );
  @@ -578,9 +596,15 @@
           {
               ((Disposable)m_container).dispose();
           }
  +        try
  +        {
  +            m_threadManager.dispose();
  +        }
  +        catch( Throwable e )
  +        {
  +            // ignore it
  +        }
           m_manager.dispose();
  -
  -        m_threadManager.dispose();
       }
   
       //=======================================================================
  @@ -597,7 +621,7 @@
       }
   
      /**
  -    * Returns the set of resoruces established within the container hierachy
  +    * Returns the set of resources established within the container hierachy
       * @return the resource collection
       */
       //public Resource[] getResources()
  
  
  
  1.6       +2 -1      
jakarta-avalon-excalibur/assembly/src/java/org/apache/excalibur/merlin/resource/DeploymentHelper.java
  
  Index: DeploymentHelper.java
  ===================================================================
  RCS file: 
/home/cvs/jakarta-avalon-excalibur/assembly/src/java/org/apache/excalibur/merlin/resource/DeploymentHelper.java,v
  retrieving revision 1.5
  retrieving revision 1.6
  diff -u -r1.5 -r1.6
  --- DeploymentHelper.java     31 Aug 2002 14:54:00 -0000      1.5
  +++ DeploymentHelper.java     7 Sep 2002 07:27:11 -0000       1.6
  @@ -278,7 +278,8 @@
           }
           catch( Throwable e )
           {
  -            final String error = "Unexpected error while preparing standard 
context.";
  +            final String error = 
  +              "Unexpected error while preparing standard context for the 
profile: " + profile.getName();
               throw new DeploymentException( error, e );
           }
       }
  
  
  
  1.1                  
jakarta-avalon-excalibur/assembly/src/java/org/apache/excalibur/merlin/resource/DefaultResourceFactory.java
  
  Index: DefaultResourceFactory.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.
   *
   * Original contribution by OSM SARL, http://www.osm.net
   */
  package org.apache.excalibur.merlin.resource;
  
  import org.apache.avalon.framework.context.Context;
  import org.apache.excalibur.merlin.assembly.ContainerManager;
  import org.apache.excalibur.merlin.model.Profile;
  import org.apache.excalibur.merlin.model.Profile;
  import org.apache.excalibur.merlin.model.Resource;
  
  /**
   * The default resource factory.
   *
   * @author <a href="mailto:[EMAIL PROTECTED]">Stephen McConnell</a>
   */
  public class DefaultResourceFactory implements ResourceFactory
  {
      /**
       * Creation of a new resource.
       * 
       * @param manager the type manager
       * @param profile the component profile
       * @param context the deployment context
       * @param handler the lifestyle handler
       * @return the resource instance
       * @exception NullPointerException if any of the supplied arguments are 
null
       */
       public Resource createResource( 
                        ContainerManager manager, 
                        Profile profile, 
                        Context context, 
                        LifestyleHandler handler ) throws NullPointerException
       {
           if( manager == null )
           {
               throw new NullPointerException( "manager" );
           }
           if( profile == null )
           {
               throw new NullPointerException( "profile" );
           }
           if( context == null )
           {
               throw new NullPointerException( "context" );
           }
           if( handler == null )
           {
               throw new NullPointerException( "handler" );
           }
  
           return new DefaultResource( manager, profile, context, handler );
       }
  }
  
  
  
  1.1                  
jakarta-avalon-excalibur/assembly/src/java/org/apache/excalibur/merlin/resource/ResourceFactory.java
  
  Index: ResourceFactory.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.
   *
   * Original contribution by OSM SARL, http://www.osm.net
   */
  package org.apache.excalibur.merlin.resource;
  
  import org.apache.avalon.framework.context.Context;
  import org.apache.excalibur.merlin.assembly.ContainerManager;
  import org.apache.excalibur.merlin.model.Profile;
  import org.apache.excalibur.merlin.model.Profile;
  import org.apache.excalibur.merlin.model.Resource;
  
  
  /**
   * Interface implemented by a classes capable of creating resource instances.
   *
   * @author <a href="mailto:[EMAIL PROTECTED]">Stephen McConnell</a>
   */
  public interface ResourceFactory
  {
      /**
       * Creation of a new resource.
       * 
       * @param manager the type manager
       * @param profile the component profile
       * @param context the deployment context
       * @param handler the lifestyle handler
       * @return the resource instance
       */
       Resource createResource( 
                        ContainerManager manager, 
                        Profile profile, 
                        Context context, 
                        LifestyleHandler handler );
  
  }
  
  
  1.1                  
jakarta-avalon-excalibur/assembly/src/java/org/apache/excalibur/merlin/service/DefaultServiceManagementContext.java
  
  Index: DefaultServiceManagementContext.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.excalibur.merlin.service;
  
  import java.net.URI;
  import java.net.URISyntaxException;
  import java.util.Map;
  import java.util.Hashtable;
  import java.util.Iterator;
  
  import org.apache.excalibur.merlin.model.Resource;
  
  
  /**
   * Default implementation of a service management context.
   *
   * @author <a href="mailto:[EMAIL PROTECTED]">Stephen McConnell</a>
   * @version $Revision: 1.1 $ $Date: 2002/09/07 07:27:12 $
   */
  public class DefaultServiceManagementContext implements 
ServiceManagementContext
  {
      //=============================================================
      // state
      //=============================================================
  
     /**
      * The context name.
      */
      private URI m_base;
  
     /**
      * A parent context.
      */
      private Map m_table = new Hashtable();
  
     /**
      * A hashtable of resources keyed by service name.
      */
      private ServiceManagementContext m_parent;
  
     /**
      * A hashtable of resources keyed by service name.
      */
      private Map m_children = new Hashtable();
  
  
      //=============================================================
      // constructor
      //=============================================================
  
     /**
      * Creation of a new service management context.
      * 
      * @param parent a possibly null parent context
      * @param name the context name
      * @exception NullPointerException if the supplied name is null
      */
      public DefaultServiceManagementContext( final ServiceManagementContext 
parent, final String name ) 
        throws NullPointerException, URISyntaxException
      {
          if( name == null )
          {
              throw new NullPointerException("name");
          }
  
          m_parent = parent;
  
          if( parent == null )
          {
              if( name.endsWith("/") )
              {
                  m_base = new URI( name );
              }
              else
              {
                  m_base = new URI( name + "/" );
              }
          }
          else
          {
              if( name.endsWith("/") )
              {
                  m_base = m_parent.getBase().resolve( name );
              }
              else
              {
                  m_base = m_parent.getBase().resolve( name + "/" );
              }
          }
      }
  
      //=============================================================
      // ServiceManagementContext
      //=============================================================
  
     /**
      * Returns the base context URI.
      *
      * @return the context uri
      */
      public URI getBase()
      {
          return m_base;
      }
  
     /**
      * Creation of a subsidiary service context.
      *
      * @param name the relative name
      * @return the service context object
      * @exception NullPointerException if the supplied name is null
      * @exception URISyntaxException if the name is invalid
      * @exception IllegalArgumentException if the name is already in use
      */
      public ServiceManagementContext createChild( String name ) throws 
URISyntaxException, IllegalArgumentException
      {
          if( name == null )
          {
              throw new NullPointerException("name");
          }
  
          if( m_children.get( name ) != null )
          {
              final String error = "Duplicate name: " + name;
              throw new IllegalArgumentException( error );
          }
  
          ServiceManagementContext context = 
            new DefaultServiceManagementContext( this, name );
  
          m_children.put( name, context );
  
          return context;
      }
  
     /**
      * Bind a resource to the naming context.
      *
      * @exception IllegalArgumentException if the supplied resource 
      *  name already exists within the immediate context
      */
      public void bind( Resource resource )
      {
          final String name = resource.getProfile().getName();
          if( m_table.get( name ) != null )
          {
              final String error = "Duplicate name: " + name;
              throw new IllegalArgumentException( error );
          }
          m_table.put( name, resource );
      }
  
     /**
      * Unbind a resource from the naming context.
      *
      * @exception IllegalArgumentException if the supplied resource is 
      *   unknown within the immediate scope of the context
      */
      public void unbind( Resource resource )
      {
          String name = resource.getProfile().getName();
          Iterator iterator = m_table.entrySet().iterator();
          while( iterator.hasNext() )
          {
               Resource res = (Resource) iterator.next();
               if( res.getProfile().getName().equals( name ) )
               {
                   m_table.remove( name );
                   break;
               }
          }
          final String error = "Unknown resource: " + name;
          throw new IllegalArgumentException( error );
      }
  
     /**
      * Select a set of service based on a supplied filter.  A filter is 
      * supplied in the form of a URI.  Interpritation of URI path, query,
      * and frasgment are protocol dependent.
      *
      * @param uri the service uri
      * @exception Exception is an install error occurs
      */
      public Resource locate( URI uri ) throws UnknownServiceException, 
InvalidPathException
      {
          URI path = m_base.relativize( uri );
          if( path.getPath().indexOf("/") > -1 )
          {
              //
              // its a reference to a nested context
              //
  
              String name = path.getPath().substring( 0, 
path.getPath().indexOf("/") );
              ServiceManagementContext child = (ServiceManagementContext) 
m_children.get( name );
              if( child != null )
              {
                  return child.locate( uri );
              }
              else
              {
                  final String error = "Invalid path element: " + name;
                  throw new InvalidPathException( uri, error );
              }
          }
          else
          {
              //
              // its a reference to an immediate entity
              //
  
              Resource resource = (Resource) m_table.get( path );
              if( resource != null )
              {
                  return resource;
              }
              final String error = "Could not locate the requested service.";
              throw new UnknownServiceException( uri, error );
          }
      }
  }
  
  
  
  
  1.1                  
jakarta-avalon-excalibur/assembly/src/java/org/apache/excalibur/merlin/service/Handler.java
  
  Index: Handler.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.
   *
   * Original contribution OSM SARL 2002, http://www.osm.net
   */
  
  package org.apache.excalibur.merlin.service;
  
  import java.io.IOException;
  import java.net.URL;
  import java.net.URLConnection;
  import java.net.URLStreamHandler;
  
  /**
   * <p>Service URL protocol handler. Creation of a new service URL 
   * requires that the appropriate handler be supplied to the URL
   * constructor.</p>
   * <p>
   * @author <a href="mailto:[EMAIL PROTECTED]">Stephen McConnell</a>
   */
  public class Handler extends URLStreamHandler
  {
  
      /**
       * The default host
       */
       private String m_host;
  
      /**
       * The resource registry.
       */
       private ServiceManagementContext m_registry;
  
      /**
       * The connection object.
       */
       private URLConnection m_connection;
  
      /**
       * Creation of a new handler.
       * @param host the host domain name
       * @param registry the service resource management context
       */
       public Handler( String host, ServiceManagementContext registry )
       {
           m_host = host;
           m_registry = registry;
       }
  
      /**
       * Opens a connection to the specified URL.
       *
       * @param url A URL to open a connection to.
       * @return The established connection.
       * @throws IOException If a connection failure occurs.
       */
      protected URLConnection openConnection( final URL url )
        throws IOException
      {
          if( m_connection == null ) 
          {
              m_connection = new ServiceURLConnection( url, m_registry );
              m_connection.connect();
          }
          return m_connection;
      }
  
      /**
       * Parses the string representation of a <code>URL</code> into a
       * <code>URL</code> object.
       * e.g. service:///root/myService
       * <p>
       * If there is any inherited context, then it has already been
       * copied into the <code>URL</code> argument.
       *
       * @param   url     the <code>URL</code> to receive the result of parsing
       *                  the spec.
       * @param   spec    the <code>String</code> representing the URL that
       *                  must be parsed.
       * @param   start   the character index at which to begin parsing. This is
       *                  just past the '<code>:</code>' (if there is one) that
       *                  specifies the determination of the protocol name.
       * @param   limit   the character position to stop parsing at. This is the
       *                  end of the string or the position of the
       *                  "<code>#</code>" character, if present. All 
information
       *                  after the sharp sign indicates an anchor.
       */
      protected void parseURL( URL url, String spec, int start, int limit )
      {
  
          // 
          // get the ref component
          // (from # to the end of the spec)
          //
  
          String ref = url.getRef();
          String remainder = spec.substring( start, limit );
          int refLoc = spec.indexOf("#", start );
          if( refLoc > -1 ) 
          {
              ref = spec.substring( refLoc + 1 );
              remainder = spec.substring( start, refLoc );
          }
  
          // 
          // get the query component
          // (from ? to the end of the remainder)
          //
  
          String query = url.getQuery();
          int queryLoc = remainder.indexOf("?");
          if( queryLoc > -1 ) 
          {
              query = remainder.substring( queryLoc + 1, remainder.length() );
              remainder = remainder.substring( 0, queryLoc );
          }
  
          // 
          // get the path component
          // (from / to the end of the remainder)
          //
  
          String path = url.getPath();
          int pathLoc = remainder.indexOf("/");
          if( pathLoc > -1 ) 
          {
              path = remainder.substring( pathLoc, remainder.length() );
              remainder = remainder.substring( 0, pathLoc );
          }
  
          //
          // set the URL parameters
          //
  
          String user = url.getUserInfo();
  
          String host = url.getHost();
          if( host == null ) host = m_host;
  
          int port = url.getPort();
          if( port == -1 ) port = getDefaultPort();
  
  
          //
          // create authority string dependending of non-default port reference
          //
  
          String authority = null;
          if( port == getDefaultPort() )
          {
              authority = host;
          }
          else
          {
              authority = host + ":" + port;
          }
  
          setURL( url, "service", host, port, authority, user, path, query, ref 
);
      }
  
     /**
      * Retuns the default port.
      * @return int the default port value of 0
      */
      protected int getDefaultPort()
      {
          return 0;
      }
  
     /**
      * Returns the URL in a string form.
      * @param url to the URL to externalize
      * @return String the external form of the URL
      */
      protected String toExternalForm( URL url )
      {
          StringBuffer result = new StringBuffer( url.getProtocol());
          result.append(":");
          if( url.getUserInfo() != null )
          {
              result.append( "@" );
              result.append( url.getUserInfo() );
          }
          if( url.getHost() == null )
          {
              result.append("localhost");
          }
          else
          {
              result.append( url.getHost() );
          }
          if( url.getPort() != url.getDefaultPort() )
          {
              if( url.getPort() != -1 )
              {
                  result.append( ":" + url.getPort() );
              }
          }
          if (url.getFile() != null) 
          {
              result.append(url.getFile());
          }
          if (url.getRef() != null) 
          {
              result.append("#");
              result.append(url.getRef());
          }
          return result.toString();
      }
  }
        
  
  
  
  1.1                  
jakarta-avalon-excalibur/assembly/src/java/org/apache/excalibur/merlin/service/InvalidPathException.java
  
  Index: InvalidPathException.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.excalibur.merlin.service;
  
  import java.net.URI;
  
  /**
   * Exception to indicate that service URI is invalid.
   *
   * @author <a href="mailto:[EMAIL PROTECTED]">Stephen McConnell</a>
   * @version $Revision: 1.1 $ $Date: 2002/09/07 07:27:12 $
   */
  public final class InvalidPathException
      extends Exception
  {
       private final URI m_path;
  
      /**
       * Construct a new <code>InvalidPathException</code> instance.
       *
       * @param path The supplied URI path.
       * @param message The detail message for this exception.
       */
      public InvalidPathException( final URI path, final String message )
      {
          super( message );
          m_path = path;
      }
  
     /**
      * Return the URI path from which the exception was raised.
      * @return the path URI
      */
      public URI getPath()
      {
          return m_path;
      }
  
     /**
      * Return the exception message.
      * @return the message
      */
      public String getMessage()
      {
          return super.getMessage() + " from uri " + getPath();
      }
  }
  
  
  
  
  1.1                  
jakarta-avalon-excalibur/assembly/src/java/org/apache/excalibur/merlin/service/ServiceManagementContext.java
  
  Index: ServiceManagementContext.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.excalibur.merlin.service;
  
  import java.net.URI;
  import java.net.URISyntaxException;
  
  import org.apache.excalibur.merlin.model.Resource;
  
  /**
   * Interface used to register an established service.
   *
   * @author <a href="mailto:[EMAIL PROTECTED]">Stephen McConnell</a>
   * @version $Revision: 1.1 $ $Date: 2002/09/07 07:27:12 $
   */
  public interface ServiceManagementContext
  {
     /**
      * Returns the base context URI.
      *
      * @return the context uri
      */
      public URI getBase();
  
     /**
      * Creation of a subsidiary service context.
      *
      * @param name the relative name
      * @return the service context object
      * @exception URISyntaxException if the name is invalid
      * @exception IllegalArgumentException if the name is already in use
      */
      public ServiceManagementContext createChild( String name ) throws 
URISyntaxException, IllegalArgumentException;
  
     /**
      * Bind a resource to the naming context.
      * @param resource the resource
      */
      public void bind( Resource resource );
  
     /**
      * Unbind a resource from the naming context.
      * @param resource the resource
      */
      public void unbind( Resource resource );
  
     /**
      * Select a set of service based on a supplied filter.  A filter is 
      * supplied in the form of a URI.  Interpritation of URI path, query,
      * and reference elements are protocol dependent.
      *
      * @param uri the service uri
      * @exception Exception is an install error occurs
      */
      Resource locate( URI uri ) throws UnknownServiceException, 
InvalidPathException;
  
  
  }
  
  
  
  
  1.1                  
jakarta-avalon-excalibur/assembly/src/java/org/apache/excalibur/merlin/service/ServiceURLConnection.java
  
  Index: ServiceURLConnection.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.
   *
   * Original contribution OSM SARL 2002, http://www.osm.net
   */
  
  package org.apache.excalibur.merlin.service;
  
  import java.io.IOException;
  import java.net.URL;
  import java.net.URLConnection;
  
  /**
   * URL connection handler for the service protocol. New instances of 
   * the <code>ServiceURLConnection</code> are created by a service
   * URL <code>Handler</code> class.
   * @see Handler
   * @author <a href="mailto:[EMAIL PROTECTED]">Stephen McConnell</a>
   */
  public class ServiceURLConnection extends URLConnection
  {
  
      /**
       * The resource registry.
       */
       private ServiceManagementContext m_registry;
  
      /**
       * The URL.
       */
       private URL m_url;
  
      /**
       * the primary object resolved during the establishment of a connection.
       */
       private Object m_object;
  
      /**
       * Creation of a new <code>ServiceURLConnection</code> handler.
       * @param url the corbaloc URL
       */
       public ServiceURLConnection( URL url, ServiceManagementContext registry )
       {
           super( url );
           m_url = url;
           m_registry = registry;
       }
  
      /**
       * Establishment of a connection to the object defined by the URL.
       *
       * @exception IOException if an error is raised while attempting to 
       *  establish the connection.
       */
       public void connect() throws IOException
       {
          if( m_url == null )
          {
              throw new IOException("URL has not been initialized.");
          }
  
          //
          // make sure that we are only dealing with the strict corbaloc URL
          // (i.e. no query or ref elements in the URL)
          //
  
          String path = url.toExternalForm();
          int queryIndex = path.indexOf("?");
          if( queryIndex > -1 )
          {
              path = path.substring( 0, queryIndex );
          }
          int refIndex = path.indexOf("#");
          if( refIndex > -1 )
          {
              path = path.substring( 0, refIndex );
          }
  
          //
          // establish the primary object reference using the strict URL
          //
  
          m_object = getObject( path );
       }
  
      /**
       * Return the Object associated with the supplied path or null if 
       * no object exists relative to the path.
       * @param path the path
       * @return the Object reference
       */
       private Object getObject( String path ) throws IOException
       {
           return this;
       }
  
      /**
       * Returns the object referenced by the URL.  If a connection has not 
been 
       * performed, a commection and retrival of the object reference will be 
       * performed.  A client application should narrow the object to the 
       * appropriate CORBA type.
       * @return and instance of org.omg.CORBA.Object
       * @exception IOException if an error occurs whhile attempting to 
retireve 
       *   the object reference.
       */
       public Object getContent() throws IOException
       {
           return getContent( new Class[0] );
       }
  
      /**
       * Retrieves the contents of this URL connection. 
       *
       * @param classes the <code>Class</code> array 
       * indicating the requested types
       * @return     the object fetched that is the first match of the type
       *               specified in the classes array. null if none of 
       *               the requested types are supported.
       *               The <code>instanceOf</code> operation should be used to 
       *               determine the specific kind of object returned.
       * @exception  IOException              if an I/O error occurs while
       *               getting the content.
       */
      public Object getContent( Class[] classes ) throws IOException 
      {
          return m_object;
      }
  }
  
  
  
  1.1                  
jakarta-avalon-excalibur/assembly/src/java/org/apache/excalibur/merlin/service/ServiceURLFactory.java
  
  Index: ServiceURLFactory.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.
   *
   * Original contribution OSM SARL 2002, http://www.osm.net
   */
  
  package org.apache.excalibur.merlin.service;
  
  import java.io.IOException;
  import java.net.URL;
  import java.net.URLConnection;
  import java.net.URLStreamHandlerFactory;
  import java.net.URLStreamHandler;
  
  /**
   * URL protocol handler factory for th eservice protocol.
   * @see Handler
   * @author <a href="mailto:[EMAIL PROTECTED]">Stephen McConnell</a>
   */
  public class ServiceURLFactory implements URLStreamHandlerFactory
  {
      /**
       * The default host name.
       */
       private final String m_host;
  
      /**
       * The resource registry.
       */
       private final ServiceManagementContext m_registry;
  
      /**
       * Creation of a new URL factory for the service protocol.
       *
       * @param host the default host
       * @param registry the service resource registry
       */
       public ServiceURLFactory( String host, ServiceManagementContext registry 
)
       {
           m_host = host;
           m_registry = registry;
       }
  
      /**
       * Returns a stream URL handler for the service protocol.
       * @param protocol the protocol
       * @return a service protocol handler if the supplied protocol is 
"service" else null
       */
       public URLStreamHandler createURLStreamHandler( String protocol )
       {
           if( protocol.equals("service") )
           {
               return new Handler( m_host, m_registry );
           }
           else
           {
               return null;
           }
       }
  }
  
  
  
  1.1                  
jakarta-avalon-excalibur/assembly/src/java/org/apache/excalibur/merlin/service/UnknownServiceException.java
  
  Index: UnknownServiceException.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.excalibur.merlin.service;
  
  import java.net.URI;
  
  /**
   * Exception to indicate that a requested service is unknown.
   *
   * @author <a href="mailto:[EMAIL PROTECTED]">Stephen McConnell</a>
   * @version $Revision: 1.1 $ $Date: 2002/09/07 07:27:12 $
   */
  public final class UnknownServiceException
      extends Exception
  {
       private final URI m_path;
  
      /**
       * Construct a new <code>UnknownServiceException</code> instance.
       *
       * @param path The supplied URI path.
       * @param message The detail message for this exception.
       */
      public UnknownServiceException( final URI path, final String message )
      {
          super( message );
          m_path = path;
      }
  
     /**
      * Return the URI path from which the exception was raised.
      * @return the path URI
      */
      public URI getPath()
      {
          return m_path;
      }
  
     /**
      * Return the exception message.
      * @return the message
      */
      public String getMessage()
      {
          return super.getMessage() + " from uri " + getPath();
      }
  
  }
  
  
  
  
  1.1                  
jakarta-avalon-excalibur/assembly/src/java/org/apache/excalibur/merlin/service/package.html
  
  Index: package.html
  ===================================================================
  <body>
  Experimatal resources dealing with service publication.
  </body>
  
  
  
  1.2       +1 -1      
jakarta-avalon-excalibur/assembly/src/java/org/apache/excalibur/playground/BasicComponent.xinfo
  
  Index: BasicComponent.xinfo
  ===================================================================
  RCS file: 
/home/cvs/jakarta-avalon-excalibur/assembly/src/java/org/apache/excalibur/playground/BasicComponent.xinfo,v
  retrieving revision 1.1
  retrieving revision 1.2
  diff -u -r1.1 -r1.2
  --- BasicComponent.xinfo      20 Aug 2002 23:23:08 -0000      1.1
  +++ BasicComponent.xinfo      7 Sep 2002 07:27:12 -0000       1.2
  @@ -1,7 +1,7 @@
   <?xml version="1.0"?>
   <!DOCTYPE type
         PUBLIC "-//AVALON/Component Type DTD Version 1.0//EN"
  -             "http://jakarta.apache.org/avalon/type_1_0.dtd"; >
  +             "http://jakarta.apache.org/avalon/dtds/type_1_0.dtd"; >
   
   <type>
   
  
  
  
  1.2       +7 -2      
jakarta-avalon-excalibur/assembly/src/java/org/apache/excalibur/playground/CustomContainer.xinfo
  
  Index: CustomContainer.xinfo
  ===================================================================
  RCS file: 
/home/cvs/jakarta-avalon-excalibur/assembly/src/java/org/apache/excalibur/playground/CustomContainer.xinfo,v
  retrieving revision 1.1
  retrieving revision 1.2
  diff -u -r1.1 -r1.2
  --- CustomContainer.xinfo     20 Aug 2002 23:23:08 -0000      1.1
  +++ CustomContainer.xinfo     7 Sep 2002 07:27:12 -0000       1.2
  @@ -7,6 +7,11 @@
   
     <component>
       <name>custom</name>
  +    <!--
  +    <attributes>
  +      <attribute key="merlin:resource-factory" 
value="org.apache.excalibur.merlin.container.ContainerFactory"/>
  +    </attributes>
  +    -->
     </component>
   
     <context>
  @@ -21,8 +26,8 @@
       <entry key="merlin:container.container-listener" 
         type="org.apache.excalibur.merlin.container.ContainerListener" 
         optional="true"/>
  -    <entry key="merlin:container.logging" 
  -      type="org.apache.excalibur.merlin.assembly.DefaultLoggerManager"/>
  +    <entry key="merlin:container.registry" 
  +      type="org.apache.excalibur.merlin.service.ServiceManagementContext"/>
     </context>
   
     <services>
  
  
  
  1.2       +0 -1      
jakarta-avalon-excalibur/assembly/src/java/org/apache/excalibur/playground/CustomContainer.xprofile
  
  Index: CustomContainer.xprofile
  ===================================================================
  RCS file: 
/home/cvs/jakarta-avalon-excalibur/assembly/src/java/org/apache/excalibur/playground/CustomContainer.xprofile,v
  retrieving revision 1.1
  retrieving revision 1.2
  diff -u -r1.1 -r1.2
  --- CustomContainer.xprofile  20 Aug 2002 23:23:08 -0000      1.1
  +++ CustomContainer.xprofile  7 Sep 2002 07:27:12 -0000       1.2
  @@ -21,7 +21,6 @@
        <context>
          <import key="merlin:container.manager"/>
          <import key="merlin:container.descriptor"/>
  -       <import key="merlin:container.logging"/>
        </context>
   
      </component>
  
  
  
  1.1                  
jakarta-avalon-excalibur/assembly/src/java/org/apache/excalibur/playground/activation/ActivationClient.java
  
  Index: ActivationClient.java
  ===================================================================
  
  package org.apache.excalibur.playground.activation;
  
  import java.net.URL;
  import java.net.URLConnection;
  import java.util.Properties;
  
  import org.apache.avalon.framework.logger.AbstractLogEnabled;
  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.service.Serviceable;
  import org.apache.avalon.framework.service.ServiceException;
  import org.apache.avalon.framework.service.ServiceManager;
  import org.apache.avalon.framework.activity.Initializable;
  
  import org.omg.CORBA.ORB;
  import org.apache.orb.corbaloc.Handler;
  import org.apache.orb.corbaloc.ServiceResolver;
  import org.apache.orb.corbaloc.ServiceResolverHelper;
  
  
  /**
   * Implementation of a container based servant manager.
   * @author <a href="mailto:[EMAIL PROTECTED]">Stephen McConnell</a>
   */
  
  public class ActivationClient extends AbstractLogEnabled
  implements Serviceable, Configurable, Initializable
  {
  
      private Configuration m_config;
  
      private ORB m_orb;
      private ServiceResolver m_resolver;
      private String m_path;
      private URL m_url;
      
      //=======================================================================
      // Configurable
      //=======================================================================
      
     /**
      * Method invoked by the ORB initializer to declare the static 
configuration.
      * @param config application static configuration
      * @exception ConfigurationException if a error in configuration occurs
      */
      public void configure( final Configuration config )
          throws ConfigurationException
      {
          m_config = config;
          String url = "corbaloc:iiop:[EMAIL PROTECTED]:2056/activator";
          m_path = config.getChild("connection").getAttribute("url", url );
      }
  
      //=======================================================================
      // Serviceable
      //=======================================================================
      
     /**
      * Method invoked by the container to provide dependent services.
      * @param manager the service manager
      * @exception ServiceException if the supplied manager does not provide an 
ORB
      */
      public void service( final ServiceManager manager )
          throws ServiceException
      {
          //m_orb = (ORB) manager.lookup( "orb" );
      }
  
      //=======================================================================
      // Initializable
      //=======================================================================
  
     /**
      * Initialization of the server.  The initialization validates that a 
      * logging channel is available, that configuration exists, and that 
      * context is not null.  Following validation, the implementation 
      * creates an ORB based on a child configuration named 'orb' supplied
      * during Initializer establishment.  Once the ORB is obtained, the 
      * implementation handles the establishment of the POA and servant.
      *
      * @exception Exception if initialization fails
      */
      public void initialize()
      throws Exception
      {
          m_orb = ORB.init( new String[0], new Properties() );
          m_url = new URL( null, m_path, new Handler( m_orb ) );
  
          try
          {
              URLConnection connection = m_url.openConnection();
  
              getLogger().debug("url: " + m_url );
              org.omg.CORBA.Object object = (org.omg.CORBA.Object) 
connection.getContent();
              getLogger().info("got an object: " + object.getClass().getName() 
);
              m_resolver = ServiceResolverHelper.narrow( object );
              getLogger().debug("object: " + m_resolver.getClass().getName() );
          }
          catch( Throwable e )
          {
              final String error = "Initialization failure.";
              getLogger().error( error, e );
          }
      }
  }
  
  
  
  1.1                  
jakarta-avalon-excalibur/assembly/src/java/org/apache/excalibur/playground/activation/ActivationClient.xinfo
  
  Index: ActivationClient.xinfo
  ===================================================================
  <?xml version="1.0"?>
  
  <type>
  
    <component>
      <name>activator-client</name>
    </component>
  
  </type>
  
  
  
  

--
To unsubscribe, e-mail:   <mailto:[EMAIL PROTECTED]>
For additional commands, e-mail: <mailto:[EMAIL PROTECTED]>

Reply via email to