? patch.diff
? org/apache/avalon/phoenix/components/embeddor/.nbattrs
? org/apache/avalon/phoenix/components/manager/.nbattrs
? org/apache/avalon/phoenix/components/manager/SubContext.java
Index: org/apache/avalon/phoenix/components/embeddor/DefaultEmbeddor.java
===================================================================
RCS file: /home/cvspublic/jakarta-avalon-phoenix/src/java/org/apache/avalon/phoenix/components/embeddor/DefaultEmbeddor.java,v
retrieving revision 1.70
diff -u -r1.70 DefaultEmbeddor.java
--- org/apache/avalon/phoenix/components/embeddor/DefaultEmbeddor.java	20 Jun 2002 11:39:31 -0000	1.70
+++ org/apache/avalon/phoenix/components/embeddor/DefaultEmbeddor.java	13 Jul 2002 06:13:30 -0000
@@ -604,7 +604,10 @@
     {
         final SystemManager systemManager =
             (SystemManager)getServiceManager().lookup( SystemManager.ROLE );
-        systemManager.register( ManagementRegistration.EMBEDDOR.getName(),
+
+        SystemManager componentManager = systemManager.getSubContext( "phoenix", "component" );
+        
+        componentManager.register( ManagementRegistration.EMBEDDOR.getName(),
                                 this, ManagementRegistration.EMBEDDOR.getInterfaces() );
 
         for( int i = 0; i < m_entries.length; i++ )
@@ -613,7 +616,7 @@
                 ManagementRegistration.getManagementInfoForRole( m_entries[ i ].getRole() );
             if ( null != registration )
             {
-                systemManager.register( registration.getName(),
+                componentManager.register( registration.getName(),
                                         m_entries[ i ].getObject(), registration.getInterfaces() );
             }
         }
@@ -627,7 +630,10 @@
     {
         final SystemManager systemManager =
             (SystemManager)getServiceManager().lookup( SystemManager.ROLE );
-        systemManager.unregister( ManagementRegistration.EMBEDDOR.getName() );
+
+        SystemManager componentManager = systemManager.getSubContext( "phoenix", "component" );
+        
+        componentManager.unregister( ManagementRegistration.EMBEDDOR.getName() );
 
         for( int i = 0; i < m_entries.length; i++ )
         {
@@ -635,7 +641,7 @@
                 ManagementRegistration.getManagementInfoForRole( m_entries[ i ].getRole() );
             if ( null != registration )
             {
-                systemManager.unregister( registration.getName() );
+                componentManager.unregister( registration.getName() );
             }
         }
     }
Index: org/apache/avalon/phoenix/components/kernel/DefaultApplicationContext.java
===================================================================
RCS file: /home/cvspublic/jakarta-avalon-phoenix/src/java/org/apache/avalon/phoenix/components/kernel/DefaultApplicationContext.java,v
retrieving revision 1.19
diff -u -r1.19 DefaultApplicationContext.java
--- org/apache/avalon/phoenix/components/kernel/DefaultApplicationContext.java	2 Jul 2002 01:02:12 -0000	1.19
+++ org/apache/avalon/phoenix/components/kernel/DefaultApplicationContext.java	13 Jul 2002 06:13:30 -0000
@@ -8,6 +8,7 @@
 package org.apache.avalon.phoenix.components.kernel;
 
 import java.util.HashMap;
+import org.apache.avalon.framework.activity.Initializable;
 import org.apache.avalon.framework.configuration.Configuration;
 import org.apache.avalon.framework.configuration.ConfigurationException;
 import org.apache.avalon.framework.logger.AbstractLogEnabled;
@@ -16,6 +17,7 @@
 import org.apache.avalon.framework.service.Serviceable;
 import org.apache.avalon.phoenix.interfaces.ApplicationContext;
 import org.apache.avalon.phoenix.interfaces.ConfigurationRepository;
+import org.apache.avalon.phoenix.interfaces.ManagerException;
 import org.apache.avalon.phoenix.interfaces.SystemManager;
 import org.apache.avalon.phoenix.interfaces.ConfigurationValidator;
 import org.apache.avalon.phoenix.metadata.SarMetaData;
@@ -31,7 +33,7 @@
  */
 class DefaultApplicationContext
     extends AbstractLogEnabled
-    implements ApplicationContext, Serviceable
+    implements ApplicationContext, Serviceable, Initializable
 {
     //Log Hierarchy for application
     private final Hierarchy m_hierarchy;
@@ -50,6 +52,7 @@
 
     ///Place to expose Management beans
     private SystemManager m_systemManager;
+    private SystemManager m_blockManager;
 
     private final SarMetaData m_metaData;
 
@@ -78,6 +81,12 @@
             lookup( ConfigurationValidator.ROLE );
     }
 
+    public void initialize()
+        throws Exception
+    {
+        m_blockManager = getManagementContext();
+    }
+        
     public SarMetaData getMetaData()
     {
         return m_metaData;
@@ -124,8 +133,7 @@
                               final Object object )
         throws Exception
     {
-        final String longName = getServiceName( name, service );
-        m_systemManager.register( longName, object, new Class[]{service} );
+        m_blockManager.register( name, object, new Class[]{service} );
     }
 
     /**
@@ -137,17 +145,7 @@
     public void unexportObject( final String name, final Class service )
         throws Exception
     {
-        final String longName = getServiceName( name, service );
-        m_systemManager.unregister( longName );
-    }
-
-    /**
-     * Utility method to get the JMX-ized name of service to export
-     */
-    private String getServiceName( final String name, final Class service )
-    {
-        return name + ",application=" + getMetaData().getName() +
-            ",role=" + service.getName();
+        m_blockManager.unregister( name );
     }
 
     /**
@@ -165,4 +163,20 @@
 
         return configuration;
     }
+    
+    /**
+     *  Returns the local SystemManager where the blocks should be registered
+     *  for management.
+     *
+     *  TODO: context should probably be passed in by reference from the kernel
+     */
+    private SystemManager getManagementContext() 
+        throws ManagerException
+    {
+        SystemManager appContext = m_systemManager.getSubContext( "phoenix", "application" );
+        SystemManager blockContext = appContext.getSubContext( m_metaData.getName(), "block" );
+        
+        return blockContext;
+    }
+    
 }
Index: org/apache/avalon/phoenix/components/kernel/DefaultKernel.java
===================================================================
RCS file: /home/cvspublic/jakarta-avalon-phoenix/src/java/org/apache/avalon/phoenix/components/kernel/DefaultKernel.java,v
retrieving revision 1.70
diff -u -r1.70 DefaultKernel.java
--- org/apache/avalon/phoenix/components/kernel/DefaultKernel.java	28 Jun 2002 05:11:52 -0000	1.70
+++ org/apache/avalon/phoenix/components/kernel/DefaultKernel.java	13 Jul 2002 06:13:31 -0000
@@ -55,7 +55,8 @@
 
     ///SystemManager provided by Embeddor
     private SystemManager m_systemManager;
-
+    private SystemManager m_applicationManager;
+    
     ///Configuration Repository
     private ConfigurationRepository m_repository;
 
@@ -76,6 +77,7 @@
     public void initialize()
         throws Exception
     {
+        m_applicationManager = m_systemManager.getSubContext( "phoenix", "application" );
     }
 
     public void dispose()
@@ -158,10 +160,9 @@
             // manage application
             try
             {
-                final String managementName = name + ",type=Application";
-                m_systemManager.register( managementName,
-                                          application,
-                                          new Class[]{ApplicationMBean.class} );
+                m_applicationManager.register( name,
+                                               application,
+                                               new Class[]{ApplicationMBean.class} );
             }
             catch( final Throwable t )
             {
@@ -225,6 +226,7 @@
 
         ContainerUtil.enableLogging( context, createContextLogger( name ) );
         ContainerUtil.service( context, createServiceManager() );
+        ContainerUtil.initialize( context );
         return context;
     }
 
@@ -267,7 +269,7 @@
             // un-manage application
             try
             {
-                m_systemManager.unregister( name + ",type=Application" );
+                m_applicationManager.unregister( name );
             }
             catch( final Throwable t )
             {
Index: org/apache/avalon/phoenix/components/manager/AbstractSystemManager.java
===================================================================
RCS file: /home/cvspublic/jakarta-avalon-phoenix/src/java/org/apache/avalon/phoenix/components/manager/AbstractSystemManager.java,v
retrieving revision 1.14
diff -u -r1.14 AbstractSystemManager.java
--- org/apache/avalon/phoenix/components/manager/AbstractSystemManager.java	20 Jun 2002 11:39:31 -0000	1.14
+++ org/apache/avalon/phoenix/components/manager/AbstractSystemManager.java	13 Jul 2002 06:13:32 -0000
@@ -32,6 +32,9 @@
 
     private HashMap m_entries = new HashMap();
 
+    private final HashMap m_subcontexts = new HashMap();    
+    private static final String EMPTY_STRING = "";
+    
     /**
      * Register an object for management.
      * The object is exported through some management scheme
@@ -51,10 +54,12 @@
                                        final Class[] interfaces )
         throws ManagerException, IllegalArgumentException
     {
-        checkRegister( name, object );
+        String jmxName = jmxName( name );
+        
+        checkRegister( jmxName, object );
         if( null == interfaces )
         {
-            final String message = REZ.getString( "manager.error.interfaces.null", name );
+            final String message = REZ.getString( "manager.error.interfaces.null", jmxName );
             throw new IllegalArgumentException( message );
         }
 
@@ -62,9 +67,9 @@
 
         final ManagedEntry entry =
             new ManagedEntry( object, interfaces );
-        entry.setExportedObject( export( name, entry.getObject(), interfaces ) );
+        entry.setExportedObject( export( jmxName, entry.getObject(), interfaces ) );
 
-        m_entries.put( name, entry );
+        m_entries.put( jmxName, entry );
     }
 
     /**
@@ -80,12 +85,14 @@
     public synchronized void register( final String name, final Object object )
         throws ManagerException, IllegalArgumentException
     {
-        checkRegister( name, object );
+        String jmxName = jmxName( name );
+        
+        checkRegister( jmxName, object );
 
         final ManagedEntry entry =
             new ManagedEntry( object, null );
-        entry.setExportedObject( export( name, entry.getObject(), null ) );
-        m_entries.put( name, entry );
+        entry.setExportedObject( export( jmxName, entry.getObject(), null ) );
+        m_entries.put( jmxName, entry );
     }
 
     /**
@@ -97,18 +104,50 @@
     public synchronized void unregister( final String name )
         throws ManagerException
     {
-        final ManagedEntry entry = (ManagedEntry)m_entries.remove( name );
+        String jmxName = jmxName( name );
+        
+        final ManagedEntry entry = (ManagedEntry)m_entries.remove( jmxName );
 
         if( null == entry )
         {
-            final String message = REZ.getString( "manager.error.unregister.noentry", name );
+            final String message = REZ.getString( "manager.error.unregister.noentry", jmxName );
             throw new ManagerException( message );
         }
 
-        unexport( name, entry.getExportedObject() );
+        unexport( jmxName, entry.getExportedObject() );
     }
 
     /**
+     * Returns the subcontext of the specified name.  If it does not exist it
+     * is created.
+     *
+     * @param name name of the subcontext
+     * @throws ManagerException if context cannot be created or retrieved
+     * @return  the subcontext with the specified name
+     */ 
+    public SystemManager getSubContext( String parent, String type ) 
+        throws ManagerException
+    {
+        if (type==null || EMPTY_STRING.equals(type) )
+        {
+            throw new ManagerException( "context type cannot be null or empty" );
+        }
+
+        // get from list if possible
+        SystemManager subcontext = 
+            (SystemManager) m_subcontexts.get( contextKey( parent, type ) );
+        
+        // otherwise create and add to list
+        if (subcontext == null)
+        {
+            subcontext = new SubContext( this, parent, type );
+            m_subcontexts.put( contextKey( parent, type ), subcontext );
+        }
+        
+        return subcontext;
+    }
+    
+    /**
      * Export the object to the particular management medium using
      * the supplied object and interfaces.
      * This needs to be implemented by subclasses.
@@ -202,4 +241,157 @@
             throw new ManagerException( message );
         }
     }
+    
+    /**
+     *  Adds this part of the context in constructing the jmx name
+     */
+    private String jmxName( String name )
+    {
+        return "instance=" + name;
+    }    
+    
+    /**
+     *  Helper method to get key used to store subcontexts in m_subcontexts
+     */
+    private static final String contextKey( String parent, String type ) 
+    {
+        return parent + "|" + type;
+    }    
+    
+    /**
+     * Implements a management context local to a particular process with which
+     * it can register its managed object.  The naming scheme that results is 
+     * meant to be compatible with jmx.
+     */
+    class SubContext implements SystemManager 
+    {
+        private final SystemManager m_parent;
+        private final String m_name;
+        private final String m_type;
+        private final HashMap m_subcontexts;
+
+        /** 
+         * Creates new SubContext to the specified context.  Objects registered 
+         * under the subcontext will be typed with the name of the context so the
+         * jmx name becomes 'contextName' + 'objectNameSoFar'
+         *
+         * @param parent the parent context
+         * @param name the subcontext name
+         */
+        public SubContext( SystemManager parent, String name, String type)
+        {
+            m_parent = parent;
+            m_name = name;
+            m_type = type;
+            m_subcontexts = new HashMap();
+        }
+
+        /**
+         * @return  the type of objects managed in the context
+         */    
+        public String getType()
+        {
+            return m_type;
+        }
+
+        /**
+         * 
+         * @return  the context name
+         */    
+        public String getName()
+        {
+            return m_name;
+        }
+
+        /**
+         * Register an object for management.
+         * The object is exported through some management scheme
+         * (typically JMX) and the management is restricted
+         * to the interfaces passed in as a parameter to method.
+         *
+         * @param name the name to register object under
+         * @param object the object
+         * @param interfaces the interfaces to register the component under
+         * @throws ManagerException if an error occurs. An error could occur if the object doesn't
+         *            implement the interfaces, the interfaces parameter contain non-instance
+         *            classes, the name is already registered etc.
+         * @throws IllegalArgumentException if object or interfaces is null
+         */
+        public void register( String name, Object object, Class[] interfaces )
+            throws ManagerException, IllegalArgumentException
+        {
+            m_parent.register( jmxName(name), object, interfaces );
+        }
+
+        /**
+         * Register an object for management.
+         * The object is exported through some management scheme
+         * (typically JMX). Note that the particular management scheme
+         * will most likely use reflection to extract manageable information.
+         *
+         * @param name the name to register object under
+         * @param object the object
+         * @throws ManagerException if an error occurs such as name already registered.
+         * @throws IllegalArgumentException if object is null
+         */
+        public void register( String name, Object object )
+            throws ManagerException, IllegalArgumentException
+        {
+            m_parent.register( jmxName(name), object );
+        }
+
+        /**
+         * Unregister named object.
+         *
+         * @param name the name of object to unregister
+         * @throws ManagerException if an error occurs such as when no such object registered.
+         */
+        public void unregister( String name )
+            throws ManagerException
+        {
+            m_parent.unregister( jmxName(name) );
+        }
+
+        /**
+         * Returns the subcontext of the specified name.  If it does not exist it
+         * is created.
+         *
+         * @return the subcontext with the specified name
+         * @param contextName
+         * @throws ManagerException if context cannot be created or retrieved 
+         */ 
+        public SystemManager getSubContext( String parent, String type ) 
+            throws ManagerException
+        {
+            if (type==null || EMPTY_STRING.equals(type) )
+            {
+                throw new ManagerException( "type cannot be null or empty" );
+            }
+            if (parent==null || EMPTY_STRING.equals(parent) )
+            {
+                throw new ManagerException( "type cannot be null or empty" );
+            }
+
+            // get from list if possible
+            SystemManager subcontext = (SystemManager) m_subcontexts.get( contextKey(parent, type) );
+
+            // otherwise create and add to list
+            if (subcontext == null)
+            {
+                subcontext = new SubContext( this, parent, type );
+                m_subcontexts.put( contextKey(parent, type), subcontext );
+            }
+
+            return subcontext;
+        }
+
+        /**
+         *  Helper method used to generate the jmx name by appending the current name
+         *  and passing up the chain to the root context
+         */
+        private String jmxName( String name )
+        {
+            return getName() + ',' + getType() + '=' + name;
+        }
+    }    
 }
Index: org/apache/avalon/phoenix/components/manager/MX4JSystemManager.java
===================================================================
RCS file: /home/cvspublic/jakarta-avalon-phoenix/src/java/org/apache/avalon/phoenix/components/manager/MX4JSystemManager.java,v
retrieving revision 1.8
diff -u -r1.8 MX4JSystemManager.java
--- org/apache/avalon/phoenix/components/manager/MX4JSystemManager.java	20 Jun 2002 14:13:29 -0000	1.8
+++ org/apache/avalon/phoenix/components/manager/MX4JSystemManager.java	13 Jul 2002 06:13:33 -0000
@@ -139,7 +139,7 @@
 
     private ObjectName createObjectName( final String name ) throws MalformedObjectNameException
     {
-        return new ObjectName( m_domain + ":name=" + name );
+        return new ObjectName( m_domain + ":" + name );
     }
 
     /**
Index: org/apache/avalon/phoenix/components/manager/NoopSystemManager.java
===================================================================
RCS file: /home/cvspublic/jakarta-avalon-phoenix/src/java/org/apache/avalon/phoenix/components/manager/NoopSystemManager.java,v
retrieving revision 1.3
diff -u -r1.3 NoopSystemManager.java
--- org/apache/avalon/phoenix/components/manager/NoopSystemManager.java	11 Dec 2001 10:13:34 -0000	1.3
+++ org/apache/avalon/phoenix/components/manager/NoopSystemManager.java	13 Jul 2002 06:13:33 -0000
@@ -52,4 +52,5 @@
         throws ManagerException
     {
     }
+    
 }
Index: org/apache/avalon/phoenix/interfaces/SystemManager.java
===================================================================
RCS file: /home/cvspublic/jakarta-avalon-phoenix/src/java/org/apache/avalon/phoenix/interfaces/SystemManager.java,v
retrieving revision 1.7
diff -u -r1.7 SystemManager.java
--- org/apache/avalon/phoenix/interfaces/SystemManager.java	10 May 2002 11:08:57 -0000	1.7
+++ org/apache/avalon/phoenix/interfaces/SystemManager.java	13 Jul 2002 06:13:34 -0000
@@ -57,4 +57,17 @@
      */
     void unregister( String name )
         throws ManagerException;
+    
+    /**
+     * Returns the subcontext of the specified name.  If it does not exist it
+     * is created.
+     *
+     * @param parent name of the object in the parent context that will own this one
+     * @param name type of objects that will be managed in the new subcontext
+     * @throws ManagerException if context cannot be created or retrieved
+     * @return  the subcontext with the specified name
+     */ 
+    SystemManager getSubContext( String parent, String type )
+        throws ManagerException;
+    
 }

