cocoon-cvs mailing list archives

Site index · List index
Message view « Date » · « Thread »
Top « Date » · « Thread »
From jheym...@apache.org
Subject svn commit: r330548 [39/132] - in /cocoon/whiteboard/maven2/cocoon-flat-layout: ./ cocoon-ajax-block/ cocoon-ajax-block/api/ cocoon-ajax-block/api/src/ cocoon-ajax-block/api/src/main/ cocoon-ajax-block/api/src/main/java/ cocoon-ajax-block/api/src/main/...
Date Thu, 03 Nov 2005 14:00:48 GMT
Added: cocoon/whiteboard/maven2/cocoon-flat-layout/cocoon-core/src/main/java/org/apache/cocoon/core/container/SingleComponentServiceManager.java
URL: http://svn.apache.org/viewcvs/cocoon/whiteboard/maven2/cocoon-flat-layout/cocoon-core/src/main/java/org/apache/cocoon/core/container/SingleComponentServiceManager.java?rev=330548&view=auto
==============================================================================
--- cocoon/whiteboard/maven2/cocoon-flat-layout/cocoon-core/src/main/java/org/apache/cocoon/core/container/SingleComponentServiceManager.java (added)
+++ cocoon/whiteboard/maven2/cocoon-flat-layout/cocoon-core/src/main/java/org/apache/cocoon/core/container/SingleComponentServiceManager.java Thu Nov  3 05:41:06 2005
@@ -0,0 +1,86 @@
+/* 
+ * Copyright 2005 The Apache Software Foundation
+ * Licensed  under the  Apache License,  Version 2.0  (the "License");
+ * you may not use  this file  except in  compliance with the License.
+ * You may obtain a copy of the License at 
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed  under the  License is distributed on an "AS IS" BASIS,
+ * WITHOUT  WARRANTIES OR CONDITIONS  OF ANY KIND, either  express  or
+ * implied.
+ * 
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.cocoon.core.container;
+
+import org.apache.avalon.framework.activity.Disposable;
+import org.apache.avalon.framework.container.ContainerUtil;
+import org.apache.avalon.framework.service.ServiceException;
+import org.apache.avalon.framework.service.ServiceManager;
+
+/**
+ * This is a simple service manager implementation that just serves one
+ * single component.
+ * @since 2.2
+ * @version $Id: SingleComponentServiceManager.java 312637 2005-10-10 13:00:42Z cziegeler $
+ */
+public final class SingleComponentServiceManager
+implements ServiceManager, Disposable {
+
+    protected final ServiceManager parent;
+    protected final Object component;
+    protected final String role;
+
+    public SingleComponentServiceManager(ServiceManager parent,
+                                         Object         component,
+                                         String         role) {
+        this.parent = parent;
+        this.component = component;
+        this.role = role;
+    }
+
+    /**
+     * @see org.apache.avalon.framework.service.ServiceManager#hasService(java.lang.String)
+     */
+    public boolean hasService(String key) {
+        if ( this.role.equals(key) ) {
+            return true;
+        }
+        if ( this.parent != null ) {
+            return this.parent.hasService(key);
+        }
+        return false;
+    }
+
+    /**
+     * @see org.apache.avalon.framework.service.ServiceManager#lookup(java.lang.String)
+     */
+    public Object lookup(String key) throws ServiceException {
+        if ( this.role.equals(key) ) {
+            return this.component;
+        }
+        if ( this.parent != null ) {
+            return this.parent.lookup(key);
+        }
+        throw new ServiceException("Cocoon", "Component for key '" + key + "' not found.");
+    }
+
+    /**
+     * @see org.apache.avalon.framework.service.ServiceManager#release(java.lang.Object)
+     */
+    public void release(Object component) {
+        if ( component != this.component && parent != null ) {
+            this.parent.release(component);
+        }
+    }
+
+    /**
+     * @see org.apache.avalon.framework.activity.Disposable#dispose()
+     */
+    public void dispose() {
+        ContainerUtil.dispose(this.parent);
+    }
+}
\ No newline at end of file

Propchange: cocoon/whiteboard/maven2/cocoon-flat-layout/cocoon-core/src/main/java/org/apache/cocoon/core/container/SingleComponentServiceManager.java
------------------------------------------------------------------------------
    svn:eol-style = native

Added: cocoon/whiteboard/maven2/cocoon-flat-layout/cocoon-core/src/main/java/org/apache/cocoon/core/container/StandaloneServiceSelector.java
URL: http://svn.apache.org/viewcvs/cocoon/whiteboard/maven2/cocoon-flat-layout/cocoon-core/src/main/java/org/apache/cocoon/core/container/StandaloneServiceSelector.java?rev=330548&view=auto
==============================================================================
--- cocoon/whiteboard/maven2/cocoon-flat-layout/cocoon-core/src/main/java/org/apache/cocoon/core/container/StandaloneServiceSelector.java (added)
+++ cocoon/whiteboard/maven2/cocoon-flat-layout/cocoon-core/src/main/java/org/apache/cocoon/core/container/StandaloneServiceSelector.java Thu Nov  3 05:41:06 2005
@@ -0,0 +1,497 @@
+/* 
+ * Copyright 2002-2005 The Apache Software Foundation
+ * Licensed  under the  Apache License,  Version 2.0  (the "License");
+ * you may not use  this file  except in  compliance with the License.
+ * You may obtain a copy of the License at 
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed  under the  License is distributed on an "AS IS" BASIS,
+ * WITHOUT  WARRANTIES OR CONDITIONS  OF ANY KIND, either  express  or
+ * implied.
+ * 
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.cocoon.core.container;
+
+import java.util.ArrayList;
+import java.util.Iterator;
+import java.util.List;
+
+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.container.ContainerUtil;
+import org.apache.avalon.framework.service.ServiceException;
+import org.apache.avalon.framework.service.ServiceManager;
+import org.apache.avalon.framework.service.ServiceSelector;
+import org.apache.avalon.framework.service.Serviceable;
+import org.apache.cocoon.components.ComponentInfo;
+import org.apache.cocoon.components.Preloadable;
+import org.apache.cocoon.core.container.handler.ComponentHandler;
+
+/**
+ * Default component selector for Cocoon's components.
+ *
+ * @version $Id: StandaloneServiceSelector.java 326062 2005-10-18 09:31:53Z sylvain $
+ * @since 2.2
+ */
+public class StandaloneServiceSelector
+extends AbstractServiceManager
+implements Preloadable, ServiceSelector, Serviceable, Configurable {
+    
+    /** The application context for components
+     */
+    protected ServiceManager serviceManager;
+
+    /** The parent selector, if any */
+    protected StandaloneServiceSelector parentSelector;
+
+    /** The parent locator, if any */
+    protected ServiceManager parentLocator;
+
+    /** The role of this selector. Set in <code>configure()</code>. */
+    protected String roleName;
+
+    /** The default key */
+    protected String defaultKey;
+
+    /* (non-Javadoc)
+     * @see org.apache.avalon.framework.service.ServiceSelector#select(java.lang.Object)
+     */
+    public Object select( Object hint )
+    throws ServiceException {
+        final String key;
+        if (hint == null) {
+            key = this.defaultKey;
+        } else {
+            key = hint.toString();
+        }
+
+        if( !this.initialized ) {
+            if( this.getLogger().isWarnEnabled() ) {
+                this.getLogger().warn( "Selecting a component on an uninitialized service selector "
+                    + "with key [" + key + "]" );
+            }
+        }
+
+        if( this.disposed ) {
+            throw new IllegalStateException(
+                "You cannot select a component from a disposed service selector." );
+        }
+
+        ComponentHandler handler = (ComponentHandler)this.componentHandlers.get( key );
+
+        // Retrieve the instance of the requested component
+        if( null == handler ) {
+            // Doesn't exist here : try in parent selector
+            if ( this.parentSelector != null ) {
+                return this.parentSelector.select(key);                
+            }
+            final String message = this.roleName
+                + ": service selector could not find the component for key [" + key + "]";
+            if( this.getLogger().isDebugEnabled() ) {
+                this.getLogger().debug( message );
+            }
+            throw new ServiceException( key, message );
+        }
+
+        Object component = null;
+
+        try {
+            component = handler.get();
+        } catch( final ServiceException ce ) {
+            //rethrow
+            throw ce;
+        } catch( final Exception e ) {
+            final String message = this.roleName
+                + ": service selector could not access the component for key [" + key + "]";
+
+            if( this.getLogger().isDebugEnabled() ) {
+                this.getLogger().debug( message, e );
+            }
+            throw new ServiceException( key, message, e );
+        }
+
+        if( null == component ) {
+            // Doesn't exist here : try in parent selector
+            if ( this.parentSelector != null ) {
+                component = this.parentSelector.select(key);
+            } else {
+                final String message = this.roleName
+                    + ": service selector could not find the component for key [" + key + "]";
+                if( this.getLogger().isDebugEnabled() ) {
+                    this.getLogger().debug( message );
+                }
+                throw new ServiceException( key, message );
+            }
+        }
+
+        this.componentMapping.put( component, handler );
+        return component;
+
+    }
+
+    /* (non-Javadoc)
+     * @see org.apache.avalon.framework.service.ServiceSelector#isSelectable(java.lang.Object)
+     */
+    public boolean isSelectable( Object hint ) {
+        final String key;
+        if (hint == null) {
+            key = this.defaultKey;
+        } else {
+            key = hint.toString();
+        }
+
+        if( !this.initialized ) return false;
+        if( this.disposed ) return false;
+
+        boolean exists = false;
+
+        try {
+            ComponentHandler handler = (ComponentHandler)this.componentHandlers.get( key );
+            exists = (handler != null);
+        } catch( Throwable t ) {
+            // We can safely ignore all exceptions
+        }
+
+        if ( !exists && this.parentSelector != null ) {
+            exists = this.parentSelector.isSelectable( key );
+        }
+        return exists;
+    }
+
+    /* (non-Javadoc)
+     * @see org.apache.avalon.framework.service.ServiceSelector#release(java.lang.Object)
+     */
+    public void release( final Object component ) {
+        if( null == component ) {
+            return;
+        }
+
+        // Was it selected on the parent ?
+        if ( this.parentSelector != null &&
+             this.parentSelector.canRelease(component) ) {
+            this.parentSelector.release(component);
+
+        } else {
+            final ComponentHandler handler =
+                (ComponentHandler)this.componentMapping.get( component );
+    
+            if( null == handler ) {
+                this.getLogger().warn( "Attempted to release a " + component.getClass().getName()
+                    + " but its handler could not be located." );
+                return;
+            }
+    
+            // ThreadSafe components will always be using a ThreadSafeComponentHandler,
+            //  they will only have a single entry in the m_componentMapping map which
+            //  should not be removed until the ComponentLocator is disposed.  All
+            //  other components have an entry for each instance which should be
+            //  removed.
+            if( !handler.isSingleton() ) {
+                // Remove the component before calling put.  This is critical to avoid the
+                //  problem where another thread calls put on the same component before
+                //  remove can be called.
+                this.componentMapping.remove( component );
+            }
+    
+            try {
+                handler.put( component );
+            } catch( Exception e ) {
+                if( this.getLogger().isDebugEnabled() ) {
+                    this.getLogger().debug( "Error trying to release component", e );
+                }
+            }
+        }
+    }
+
+    /* (non-Javadoc)
+     * @see org.apache.avalon.framework.service.Serviceable#service(org.apache.avalon.framework.service.ServiceManager)
+     */
+    public void service( final ServiceManager componentManager )
+    throws ServiceException {
+        this.serviceManager = componentManager;
+    }
+
+    /* (non-Javadoc)
+     * @see org.apache.avalon.framework.configuration.Configurable#configure(org.apache.avalon.framework.configuration.Configuration)
+     */
+    public void configure( final Configuration config )
+    throws ConfigurationException {
+        this.roleName = getRoleName(config);
+
+        // Get default key
+        this.defaultKey = config.getAttribute(this.getDefaultKeyAttributeName(), null);
+
+        // Add components
+        String compInstanceName = getComponentInstanceName();
+
+        Configuration[] instances = config.getChildren();
+
+        for (int i = 0; i < instances.length; i++) {
+
+            Configuration instance = instances[i];
+            ComponentInfo info = null;
+            
+            String key = instance.getAttribute("name").trim();
+
+            String classAttr = instance.getAttribute(getClassAttributeName(), null);
+            String className;
+
+            if (compInstanceName == null) {
+                // component-instance implicitly defined by the presence of the 'class' attribute
+                if (classAttr == null) {
+                    info = this.roleManager.getDefaultServiceInfoForKey(roleName, instance.getName());
+                    className = info.getServiceClassName();
+                } else {
+                    className = classAttr.trim();
+                }
+
+            } else {
+                // component-instances names explicitly defined
+                if (compInstanceName.equals(instance.getName())) {
+                    className = (classAttr == null) ? null : classAttr.trim();
+                } else {
+                    info = this.roleManager.getDefaultServiceInfoForKey(roleName, instance.getName());
+                    className = info.getServiceClassName();
+                }
+            }
+
+            if (className == null) {
+                String message = "Unable to determine class name for component named '" + key +
+                    "' at " + instance.getLocation();
+
+                getLogger().error(message);
+                throw new ConfigurationException(message);
+            }
+            
+            this.addComponent( className, key, instance, info );
+        }
+    }
+
+    /* (non-Javadoc)
+     * @see org.apache.avalon.framework.activity.Initializable#initialize()
+     */
+    public void initialize() 
+    throws Exception {
+        super.initialize();
+
+        List keys = new ArrayList( this.componentHandlers.keySet() );
+
+        for( int i = 0; i < keys.size(); i++ ) {
+            final Object key = keys.get( i );
+            final ComponentHandler handler =
+                (ComponentHandler)this.componentHandlers.get( key );
+
+            try {
+                handler.initialize();
+            } catch( Exception e ) {
+                if( this.getLogger().isDebugEnabled() ) {
+                    this.getLogger().debug( "Caught an exception trying to initialize "
+                        + "of the component handler.", e );
+                }
+            }
+
+        }
+    }
+
+    /* (non-Javadoc)
+     * @see org.apache.avalon.framework.activity.Disposable#dispose()
+     */
+    public void dispose() {
+        Iterator keys = this.componentHandlers.keySet().iterator();
+        List keyList = new ArrayList();
+
+        while( keys.hasNext() ) {
+            Object key = keys.next();
+            ComponentHandler handler =
+                (ComponentHandler)this.componentHandlers.get( key );
+
+            handler.dispose();
+
+            keyList.add( key );
+        }
+
+        keys = keyList.iterator();
+
+        while( keys.hasNext() ) {
+            this.componentHandlers.remove( keys.next() );
+        }
+
+        keyList.clear();
+
+        if ( this.parentLocator != null ) {
+            this.parentLocator.release( this.parentSelector );
+            this.parentLocator = null;
+            this.parentSelector = null;
+        }
+        
+        super.dispose();
+    }
+
+    /** Add a new component to the manager.
+     * @param key the key for the new component.
+     * @param component the class of this component.
+     * @param configuration the configuration for this component.
+     */
+    public void addComponent( final String key,
+                              final Class component,
+                              final Configuration configuration,
+                              final ComponentInfo info)
+    throws ServiceException {
+        if( this.initialized ) {
+            throw new ServiceException( key,
+                "Cannot add components to an initialized service selector" );
+        }
+
+        try {
+            final ComponentHandler handler = getComponentHandler( null,
+                                                                  component,
+                                                                  configuration,
+                                                                  this.serviceManager,
+                                                                  info);
+
+            handler.initialize();
+            this.componentHandlers.put( key, handler );
+
+            if( this.getLogger().isDebugEnabled() ) {
+                this.getLogger().debug(
+                    "Adding " + component.getName() + " for key [" + key + "]" );
+            }
+        } catch (ServiceException se) {
+            throw se;
+        } catch( final Exception e ) {
+            final String message =
+                "Could not set up component for key [ " + key + "]";
+            if( this.getLogger().isErrorEnabled() ) {
+                this.getLogger().error( message, e );
+            }
+
+            throw new ServiceException(key, message, e );
+        }
+    }
+
+    /**
+     * Get the name for component-instance elements (i.e. components not defined
+     * by their role shortcut. If <code>null</code>, any element having a 'class'
+     * attribute will be considered as a component instance.
+     * <p>
+     * The default here is to return <code>null</code>, and subclasses can redefine
+     * this method to return particular values.
+     *
+     * @return <code>null</code>, but can be changed by subclasses
+     */
+    protected String getComponentInstanceName() {
+        return null;
+    }
+
+    /**
+     * Get the name of the attribute giving the class name of a component.
+     * The default here is "class", but this can be overriden in subclasses.
+     *
+     * @return "<code>class</code>", but can be changed by subclasses
+     */
+    protected String getClassAttributeName() {
+        return "class";
+    }
+
+    /**
+     * Get the name of the attribute giving the default key to use if
+     * none is given. The default here is "default", but this can be
+     * overriden in subclasses. If this method returns <code>null</code>,
+     * no default key can be specified.
+     *
+     * @return "<code>default</code>", but can be changed by subclasses
+     */
+    protected String getDefaultKeyAttributeName() {
+        return "default";
+    }
+    
+    /**
+     * Get the role name for this selector. This is called by <code>configure()</code>
+     * to set the value of <code>this.roleName</code>.
+     *
+     * @return the role name, or <code>null<code> if it couldn't be determined.
+     */
+    protected String getRoleName(Configuration config) {
+        // Get the role for this selector
+        String name = config.getAttribute("role", null);
+        if (name == null && this.roleManager != null) {
+            name = this.roleManager.getRoleForName(config.getName());
+        }
+
+        return name;
+    }
+
+    /**
+     * Set the ComponentLocatorImpl that allows access to a possible
+     * parent of this selector
+     * @param locator
+     * @throws ServiceException
+     */
+    void setParentLocator(ServiceManager locator, String role)
+    throws ServiceException {
+        if (this.parentSelector != null) {
+            throw new ServiceException(null, "Parent selector is already set");
+        }
+        this.parentLocator = locator;
+        
+        if (locator != null && locator.hasService(role)) {
+            // Get the parent, unwrapping it as far as needed
+            Object parent = locator.lookup(role);
+            
+            if (parent instanceof StandaloneServiceSelector) {
+                this.parentSelector = (StandaloneServiceSelector)parent;
+            } else {
+                throw new IllegalArgumentException("Parent selector is not an extended component selector (" + parent + ")");
+            }
+        }
+    }
+
+    protected boolean canRelease(Object component) {
+        if ( this.parentSelector != null &&
+             this.parentSelector.canRelease(component) ) {
+            return true;
+        }
+        return this.componentMapping.containsKey( component );
+    }
+    
+    /**
+     * A special factory that sets the RoleManager and LoggerManager after service()
+     */
+    public static class Factory extends ComponentFactory {
+        
+        private final String role;
+        
+        public Factory(ComponentEnvironment env, ComponentInfo info, String role) 
+        throws Exception {
+            super(env, info);
+            this.role = role;
+        }
+        
+        protected void setupObject(Object obj)
+        throws Exception {
+            final StandaloneServiceSelector component = (StandaloneServiceSelector)obj;
+
+            ContainerUtil.enableLogging(component, this.environment.logger);
+            ContainerUtil.contextualize(component, this.environment.context);
+            ContainerUtil.service(component, this.environment.serviceManager);
+            
+            component.setLoggerManager(this.environment.loggerManager);
+            component.setRoleManager(this.environment.roleManager);
+
+            ServiceManager manager = this.environment.serviceManager;
+            if (manager instanceof CoreServiceManager) {
+                // Can it be something else?
+                component.setParentLocator( ((CoreServiceManager)manager).parentManager, this.role);
+            }
+            
+            ContainerUtil.configure(component, this.serviceInfo.getConfiguration());
+            ContainerUtil.initialize(component);
+            ContainerUtil.start(component);
+        }
+    }
+}

Propchange: cocoon/whiteboard/maven2/cocoon-flat-layout/cocoon-core/src/main/java/org/apache/cocoon/core/container/StandaloneServiceSelector.java
------------------------------------------------------------------------------
    svn:eol-style = native

Added: cocoon/whiteboard/maven2/cocoon-flat-layout/cocoon-core/src/main/java/org/apache/cocoon/core/container/handler/AbstractComponentHandler.java
URL: http://svn.apache.org/viewcvs/cocoon/whiteboard/maven2/cocoon-flat-layout/cocoon-core/src/main/java/org/apache/cocoon/core/container/handler/AbstractComponentHandler.java?rev=330548&view=auto
==============================================================================
--- cocoon/whiteboard/maven2/cocoon-flat-layout/cocoon-core/src/main/java/org/apache/cocoon/core/container/handler/AbstractComponentHandler.java (added)
+++ cocoon/whiteboard/maven2/cocoon-flat-layout/cocoon-core/src/main/java/org/apache/cocoon/core/container/handler/AbstractComponentHandler.java Thu Nov  3 05:41:06 2005
@@ -0,0 +1,292 @@
+/* 
+ * Copyright 2002-2005 The Apache Software Foundation
+ * Licensed  under the  Apache License,  Version 2.0  (the "License");
+ * you may not use  this file  except in  compliance with the License.
+ * You may obtain a copy of the License at 
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed  under the  License is distributed on an "AS IS" BASIS,
+ * WITHOUT  WARRANTIES OR CONDITIONS  OF ANY KIND, either  express  or
+ * implied.
+ * 
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.cocoon.core.container.handler;
+
+import org.apache.avalon.excalibur.pool.Poolable;
+import org.apache.avalon.framework.component.Composable;
+import org.apache.avalon.framework.configuration.Configuration;
+import org.apache.avalon.framework.context.Context;
+import org.apache.avalon.framework.logger.Logger;
+import org.apache.avalon.framework.service.ServiceManager;
+import org.apache.avalon.framework.thread.SingleThreaded;
+import org.apache.avalon.framework.thread.ThreadSafe;
+import org.apache.cocoon.components.ComponentInfo;
+import org.apache.cocoon.core.container.ComponentEnvironment;
+import org.apache.cocoon.core.container.ComponentFactory;
+import org.apache.cocoon.core.container.DefaultServiceSelector;
+import org.apache.cocoon.core.container.StandaloneServiceSelector;
+
+/**
+ * This class acts like a Factory to instantiate the correct version
+ * of the component handler that you need.
+ *
+ * @version $Id: AbstractComponentHandler.java 312637 2005-10-10 13:00:42Z cziegeler $
+ * @since 2.2
+ */
+public abstract class AbstractComponentHandler 
+implements ComponentHandler {
+    
+    private final Object referenceSemaphore = new Object();
+    private int references = 0;
+
+    protected final Logger logger;
+    
+    /** State management boolean stating whether the Handler is disposed or not */
+    protected boolean disposed = false;
+
+    /** State management boolean stating whether the Handler is initialized or not */
+    private boolean initialized = false;
+    
+    /** Information about the component */
+    private ComponentInfo info;
+    
+    /**
+     * Looks up and returns a component handler for a given component class.
+     *
+     * @param role the component's role. Can be <code>null</code> if the role isn't known.
+     * @param componentEnv The component's creation environment.
+     * @param info          The description of the component (configuration, lifecycle etc.)
+     *
+     * @throws Exception If there were any problems obtaining a ComponentHandler
+     */
+    public static ComponentHandler getComponentHandler(String role, 
+                                                       ComponentEnvironment componentEnv,
+                                                       ComponentInfo info) 
+    throws Exception {
+        
+       // Load the class
+        Class componentClass;
+        
+        try {
+            componentClass = componentEnv.loadClass(info.getServiceClassName());
+        } catch (ClassNotFoundException cnfe) {
+            throw new Exception("Cannot find class " + info.getServiceClassName() + " for component at " +
+                    info.getConfiguration().getLocation(), cnfe);
+        }
+
+        int numInterfaces = 0;
+
+        // Early check for Composable
+        if ( Composable.class.isAssignableFrom( componentClass ) ) {
+            throw new Exception("Interface Composable is not supported anymore. Please change class "
+                                + componentClass.getName() + " to use Serviceable instead.");
+        }
+
+        if( SingleThreaded.class.isAssignableFrom( componentClass ) ) {
+            numInterfaces++;
+            info.setModel(ComponentInfo.MODEL_PRIMITIVE);
+        }
+
+        if( ThreadSafe.class.isAssignableFrom( componentClass ) ) {
+            numInterfaces++;
+            info.setModel(ComponentInfo.MODEL_SINGLETON);
+        }
+
+        if( Poolable.class.isAssignableFrom( componentClass ) ) {
+            numInterfaces++;
+            if ( info.getModel() != ComponentInfo.MODEL_NON_THREAD_SAFE_POOLED ) {
+                info.setModel(ComponentInfo.MODEL_POOLED);
+                if ( ComponentInfo.TYPE_NON_THREAD_SAFE_POOLED.equals(info.getConfiguration().getAttribute("model", null))) {
+                    info.setModel(ComponentInfo.MODEL_NON_THREAD_SAFE_POOLED);
+                }
+            }
+        }
+
+        if( numInterfaces > 1 ) {
+            throw new Exception( "[CONFLICT] More than one lifecycle interface in "
+                                 + componentClass.getName() + "  May implement no more than one of "
+                                 + "SingleThreaded, ThreadSafe, or Poolable" );
+        }
+
+        if ( numInterfaces == 0 ) {
+            // this component does not use avalon interfaces, so get the info from the configuration
+            info.fill(info.getConfiguration());
+        }
+        
+        // Create the factory to use to create the instances of the Component.
+        ComponentFactory factory;
+        ComponentHandler handler;
+                
+        if (DefaultServiceSelector.class.isAssignableFrom(componentClass)) {
+            // Special factory for DefaultServiceSelector
+            factory = new DefaultServiceSelector.Factory(componentEnv, info, role);
+            handler = new ThreadSafeComponentHandler(info, componentEnv.logger, factory);
+            handler.initialize();
+            return handler;
+            
+        } else if (StandaloneServiceSelector.class.isAssignableFrom(componentClass)) {
+            // Special factory for StandaloneServiceSelector
+            factory = new StandaloneServiceSelector.Factory(componentEnv, info, role);
+                
+        } else {
+            factory = new ComponentFactory(componentEnv, info);
+        }
+
+        if( info.getModel() == ComponentInfo.MODEL_NON_THREAD_SAFE_POOLED)  {
+            handler = new NonThreadSafePoolableComponentHandler( info, componentEnv.logger, factory, info.getConfiguration() );
+        } else if( info.getModel() == ComponentInfo.MODEL_POOLED ) {
+            handler = new PoolableComponentHandler( info, componentEnv.logger, factory, info.getConfiguration() );
+        } else if( info.getModel() == ComponentInfo.MODEL_SINGLETON ) {
+            handler = new ThreadSafeComponentHandler( info, componentEnv.logger, factory );
+        } else {
+            // This is a SingleThreaded component
+            handler = new SingleThreadedComponentHandler( info, componentEnv.logger, factory );
+        }
+
+        return handler;
+    }
+
+    /**
+     * Creates a new ComponentHandler.
+     */
+    public AbstractComponentHandler(ComponentInfo info, Logger logger) {
+        this.logger = logger;
+        this.info = info;
+    }
+    
+    public ComponentInfo getInfo() {
+        return this.info;
+    }
+
+    /**
+     * Get an instance of the type of component handled by this handler.
+     * <p>
+     * Subclasses should not extend this method but rather the doGet method below otherwise
+     *  reference counts will not be supported.
+     * <p>
+     *
+     * @return an instance
+     * @exception Exception if an error occurs
+     */
+    public final Object get() throws Exception {
+        initialize();
+        if( this.disposed ) {
+            throw new IllegalStateException( "You cannot get a component from a disposed handler." );
+        }
+        
+        final Object component = this.doGet();
+
+        synchronized( this.referenceSemaphore ) {
+            this.references++;
+        }
+
+        return component;
+    }
+
+    /**
+     * Put back an instance of the type of component handled by this handler.
+     * <p>
+     * Subclasses should not extend this method but rather the doPut method below otherwise
+     *  reference counts will not be supported.
+     * <p>
+     *
+     * @param component a service
+     * @exception Exception if an error occurs
+     */
+    public final void put( Object component ) 
+    throws Exception {
+        if( !this.initialized ) {
+            throw new IllegalStateException(
+                "You cannot put a component to an uninitialized handler." );
+        }
+        //  The reference count must be decremented before any calls to doPut.
+        //  If there is another thread blocking, then this thread could stay deep inside
+        //  doPut for an undetermined amount of time until the thread scheduler gives it
+        //  some cycles again.  (It happened).  All ComponentHandler state must therefor
+        //  reflect the thread having left this method before the call to doPut to avoid
+        //  warning messages from the dispose() cycle if that takes place before this
+        //  thread has a chance to continue.
+        synchronized( this.referenceSemaphore ) {
+            this.references--;
+        }
+
+        try {
+            this.doPut( component );
+        } catch( Throwable t ) {
+            this.logger.error("Exception during putting back a component.", t);
+        }
+    }
+
+    /**
+     * Concrete implementation of getting a component.
+     *
+     * @return a service
+     * @exception Exception if an error occurs
+     */
+    protected abstract Object doGet() throws Exception;
+
+    /**
+     * Concrete implementation of putting back a component.
+     *
+     * @param component a <code>Component</code> value
+     * @exception Exception if an error occurs
+     */
+    protected abstract void doPut( Object component ) throws Exception;
+
+    /**
+     * Default here is to return <code>false</code>
+     */
+    public boolean isSingleton() {
+        return false;
+    }
+    
+    /**
+     * Returns <code>true</code> if this component handler can safely be
+     * disposed (i.e. none of the components it is handling are still
+     * being used).
+     *
+     * @return <code>true</code> if this component handler can safely be
+     *         disposed; <code>false</code> otherwise
+     */
+    public final boolean canBeDisposed() {
+        return ( this.references == 0 );
+    }
+    
+    /* (non-Javadoc)
+     * @see org.apache.cocoon.core.container.ComponentHandler#dispose()
+     */
+    public void dispose() {
+        this.disposed = true;
+    }
+    
+    /* (non-Javadoc)
+     * @see org.apache.cocoon.core.container.ComponentHandler#initialize()
+     */
+    public final void initialize() throws Exception {
+        if( this.initialized ) {
+            return;
+        }
+
+        doInitialize();
+        this.initialized = true;
+    }
+    
+    protected abstract void doInitialize() throws Exception;
+
+    /**
+     * Create a component handler (version used by XSP)
+     * TODO - perhaps we can remove this later?
+     */
+    public static ComponentHandler getComponentHandler(Class clazz, Logger logger, Context context, ServiceManager manager, Configuration config) throws Exception {
+        ComponentEnvironment env = new ComponentEnvironment(clazz.getClassLoader(), logger, null, null, context, manager);
+        ComponentInfo info = new ComponentInfo();
+        info.setServiceClassName(clazz.getName());
+        info.setConfiguration(config);
+        return getComponentHandler(null, env, info);
+
+    }
+}

Propchange: cocoon/whiteboard/maven2/cocoon-flat-layout/cocoon-core/src/main/java/org/apache/cocoon/core/container/handler/AbstractComponentHandler.java
------------------------------------------------------------------------------
    svn:eol-style = native

Added: cocoon/whiteboard/maven2/cocoon-flat-layout/cocoon-core/src/main/java/org/apache/cocoon/core/container/handler/AbstractFactoryHandler.java
URL: http://svn.apache.org/viewcvs/cocoon/whiteboard/maven2/cocoon-flat-layout/cocoon-core/src/main/java/org/apache/cocoon/core/container/handler/AbstractFactoryHandler.java?rev=330548&view=auto
==============================================================================
--- cocoon/whiteboard/maven2/cocoon-flat-layout/cocoon-core/src/main/java/org/apache/cocoon/core/container/handler/AbstractFactoryHandler.java (added)
+++ cocoon/whiteboard/maven2/cocoon-flat-layout/cocoon-core/src/main/java/org/apache/cocoon/core/container/handler/AbstractFactoryHandler.java Thu Nov  3 05:41:06 2005
@@ -0,0 +1,58 @@
+/* 
+ * Copyright 2002-2005 The Apache Software Foundation
+ * Licensed  under the  Apache License,  Version 2.0  (the "License");
+ * you may not use  this file  except in  compliance with the License.
+ * You may obtain a copy of the License at 
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed  under the  License is distributed on an "AS IS" BASIS,
+ * WITHOUT  WARRANTIES OR CONDITIONS  OF ANY KIND, either  express  or
+ * implied.
+ * 
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.cocoon.core.container.handler;
+
+import org.apache.avalon.framework.logger.Logger;
+import org.apache.cocoon.components.ComponentInfo;
+import org.apache.cocoon.core.container.ComponentFactory;
+
+/**
+ * This class acts like a Factory to instantiate the correct version
+ * of the component handler that you need.
+ *
+ * @version $Id: AbstractFactoryHandler.java 312637 2005-10-10 13:00:42Z cziegeler $
+ * @since 2.2
+ */
+public abstract class AbstractFactoryHandler extends AbstractComponentHandler {
+    
+    /** This factory is used to created new objects */
+    protected final ComponentFactory factory;
+    
+    /**
+     * Creates a new ComponentHandler.
+     */
+    public AbstractFactoryHandler(ComponentInfo info, Logger logger, ComponentFactory factory) {
+        super(info, logger);
+        this.factory = factory;
+    }
+
+    /**
+     * Decommission a component
+     * @param component Object to be decommissioned
+     */
+    protected void decommission( final Object component ) {
+        try {
+            this.factory.decommission( component );
+        } catch( final Exception e ) {
+            if( this.logger.isWarnEnabled() ) {
+                this.logger.warn( "Error decommissioning component: "
+                    + this.factory.getCreatedClass().getName(), e );
+            }
+        }
+    }
+    
+}

Propchange: cocoon/whiteboard/maven2/cocoon-flat-layout/cocoon-core/src/main/java/org/apache/cocoon/core/container/handler/AbstractFactoryHandler.java
------------------------------------------------------------------------------
    svn:eol-style = native

Added: cocoon/whiteboard/maven2/cocoon-flat-layout/cocoon-core/src/main/java/org/apache/cocoon/core/container/handler/AliasComponentHandler.java
URL: http://svn.apache.org/viewcvs/cocoon/whiteboard/maven2/cocoon-flat-layout/cocoon-core/src/main/java/org/apache/cocoon/core/container/handler/AliasComponentHandler.java?rev=330548&view=auto
==============================================================================
--- cocoon/whiteboard/maven2/cocoon-flat-layout/cocoon-core/src/main/java/org/apache/cocoon/core/container/handler/AliasComponentHandler.java (added)
+++ cocoon/whiteboard/maven2/cocoon-flat-layout/cocoon-core/src/main/java/org/apache/cocoon/core/container/handler/AliasComponentHandler.java Thu Nov  3 05:41:06 2005
@@ -0,0 +1,55 @@
+/* 
+ * Copyright 2002-2005 The Apache Software Foundation
+ * Licensed  under the  Apache License,  Version 2.0  (the "License");
+ * you may not use  this file  except in  compliance with the License.
+ * You may obtain a copy of the License at 
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed  under the  License is distributed on an "AS IS" BASIS,
+ * WITHOUT  WARRANTIES OR CONDITIONS  OF ANY KIND, either  express  or
+ * implied.
+ * 
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.cocoon.core.container.handler;
+
+import org.apache.avalon.framework.logger.Logger;
+import org.apache.cocoon.components.ComponentInfo;
+import org.apache.cocoon.core.container.CoreServiceManager;
+
+/**
+ * A component handler used to alias roles: it delegates all its calls to another
+ * handler.
+ * 
+ * @version $Id: AliasComponentHandler.java 312637 2005-10-10 13:00:42Z cziegeler $
+ * @since 2.2
+ */
+public class AliasComponentHandler extends AbstractComponentHandler {
+
+    ComponentHandler aliasedHandler;
+    
+    public AliasComponentHandler(Logger logger, ComponentHandler aliasedHandler) {
+        super(new ComponentInfo(), logger);
+        getInfo().setConfiguration(CoreServiceManager.EMPTY_CONFIGURATION);
+        this.aliasedHandler = aliasedHandler;
+    }
+
+    protected Object doGet() throws Exception {
+        return this.aliasedHandler.get();
+    }
+
+    protected void doPut(Object component) throws Exception {
+        this.aliasedHandler.put(component);
+    }
+    
+    protected void doInitialize() {
+        // nothing to do here
+    }
+    
+    public boolean isSingleton() {
+        return this.aliasedHandler.isSingleton();
+    }
+}

Propchange: cocoon/whiteboard/maven2/cocoon-flat-layout/cocoon-core/src/main/java/org/apache/cocoon/core/container/handler/AliasComponentHandler.java
------------------------------------------------------------------------------
    svn:eol-style = native

Added: cocoon/whiteboard/maven2/cocoon-flat-layout/cocoon-core/src/main/java/org/apache/cocoon/core/container/handler/ComponentHandler.java
URL: http://svn.apache.org/viewcvs/cocoon/whiteboard/maven2/cocoon-flat-layout/cocoon-core/src/main/java/org/apache/cocoon/core/container/handler/ComponentHandler.java?rev=330548&view=auto
==============================================================================
--- cocoon/whiteboard/maven2/cocoon-flat-layout/cocoon-core/src/main/java/org/apache/cocoon/core/container/handler/ComponentHandler.java (added)
+++ cocoon/whiteboard/maven2/cocoon-flat-layout/cocoon-core/src/main/java/org/apache/cocoon/core/container/handler/ComponentHandler.java Thu Nov  3 05:41:06 2005
@@ -0,0 +1,80 @@
+/* 
+ * Copyright 2002-2005 The Apache Software Foundation
+ * Licensed  under the  Apache License,  Version 2.0  (the "License");
+ * you may not use  this file  except in  compliance with the License.
+ * You may obtain a copy of the License at 
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed  under the  License is distributed on an "AS IS" BASIS,
+ * WITHOUT  WARRANTIES OR CONDITIONS  OF ANY KIND, either  express  or
+ * implied.
+ * 
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.cocoon.core.container.handler;
+
+import org.apache.cocoon.components.ComponentInfo;
+
+/**
+ * This class acts like a Factory to instantiate the correct version
+ * of the component handler that you need.
+ *
+ * @version $Id: ComponentHandler.java 312637 2005-10-10 13:00:42Z cziegeler $
+ * @since 2.2
+ */
+public interface ComponentHandler {
+
+    /**
+     * Get an instance of the type of component handled by this handler.
+     * 
+     * @return an instance
+     * @exception Exception if an error occurs
+     */
+    Object get() throws Exception;
+
+    /**
+     * Put back an instance of the type of component handled by this handler.
+     *
+     * @param component a service
+     * @exception Exception if an error occurs
+     */
+    void put( Object component ) 
+    throws Exception;
+    
+    /**
+     * Indicates if this handler manages a single object, i.e. all calls to {@link #get()}
+     * will return the same object.
+     * 
+     * @return <code>true</code> if managed object is a singleton
+     */
+    boolean isSingleton();
+
+    /**
+     * Returns <code>true</code> if this component handler can safely be
+     * disposed (i.e. none of the components it is handling are still
+     * being used).
+     *
+     * @return <code>true</code> if this component handler can safely be
+     *         disposed; <code>false</code> otherwise
+     */
+    boolean canBeDisposed();
+
+    /**
+     * Dispose of the component handler and any associated Pools and Factories.
+     */
+    public void dispose();
+    
+    /**
+     * Initialize this handler
+     */
+    void initialize() throws Exception;
+    
+    /**
+     * Get the service metadata for this handler
+     */
+    ComponentInfo getInfo();
+
+}

Propchange: cocoon/whiteboard/maven2/cocoon-flat-layout/cocoon-core/src/main/java/org/apache/cocoon/core/container/handler/ComponentHandler.java
------------------------------------------------------------------------------
    svn:eol-style = native

Added: cocoon/whiteboard/maven2/cocoon-flat-layout/cocoon-core/src/main/java/org/apache/cocoon/core/container/handler/InstanceComponentHandler.java
URL: http://svn.apache.org/viewcvs/cocoon/whiteboard/maven2/cocoon-flat-layout/cocoon-core/src/main/java/org/apache/cocoon/core/container/handler/InstanceComponentHandler.java?rev=330548&view=auto
==============================================================================
--- cocoon/whiteboard/maven2/cocoon-flat-layout/cocoon-core/src/main/java/org/apache/cocoon/core/container/handler/InstanceComponentHandler.java (added)
+++ cocoon/whiteboard/maven2/cocoon-flat-layout/cocoon-core/src/main/java/org/apache/cocoon/core/container/handler/InstanceComponentHandler.java Thu Nov  3 05:41:06 2005
@@ -0,0 +1,74 @@
+/* 
+ * Copyright 2002-2005 The Apache Software Foundation
+ * Licensed  under the  Apache License,  Version 2.0  (the "License");
+ * you may not use  this file  except in  compliance with the License.
+ * You may obtain a copy of the License at 
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed  under the  License is distributed on an "AS IS" BASIS,
+ * WITHOUT  WARRANTIES OR CONDITIONS  OF ANY KIND, either  express  or
+ * implied.
+ * 
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.cocoon.core.container.handler;
+
+import org.apache.avalon.framework.activity.Disposable;
+import org.apache.avalon.framework.logger.Logger;
+import org.apache.cocoon.components.ComponentInfo;
+import org.apache.cocoon.core.container.CoreServiceManager;
+
+/**
+ * A component handler for instances created outside the container.
+ * 
+ * @version $Id: InstanceComponentHandler.java 312637 2005-10-10 13:00:42Z cziegeler $
+ * @since 2.2
+ */
+public class InstanceComponentHandler extends AbstractComponentHandler {
+
+    private Object obj;
+
+    /**
+     * Creates a new ComponentHandler.
+     */
+    public InstanceComponentHandler(Logger logger, Object obj) {
+        super(new ComponentInfo(), logger);
+        // For info.getLocation() to work properly
+        this.getInfo().setConfiguration(CoreServiceManager.EMPTY_CONFIGURATION);
+        this.obj = obj;
+    }
+
+    public boolean isSingleton() {
+        return true;
+    }
+
+    /* (non-Javadoc)
+     * @see org.apache.cocoon.core.container.AbstractComponentHandler#doGet()
+     */
+    protected Object doGet() throws Exception {
+        return this.obj;
+    }
+
+    /* (non-Javadoc)
+     * @see org.apache.cocoon.core.container.AbstractComponentHandler#doPut(java.lang.Object)
+     */
+    protected void doPut(Object component) throws Exception {
+        // nothing
+    }
+    
+    protected void doInitialize() {
+        // nothing to do here
+    }
+
+    /* (non-Javadoc)
+     * @see org.apache.cocoon.core.container.ComponentHandler#dispose()
+     */
+    public void dispose() {
+        if (this.obj instanceof Disposable) {
+            ((Disposable)this.obj).dispose();
+        }
+    }
+}

Propchange: cocoon/whiteboard/maven2/cocoon-flat-layout/cocoon-core/src/main/java/org/apache/cocoon/core/container/handler/InstanceComponentHandler.java
------------------------------------------------------------------------------
    svn:eol-style = native

Added: cocoon/whiteboard/maven2/cocoon-flat-layout/cocoon-core/src/main/java/org/apache/cocoon/core/container/handler/LazyHandler.java
URL: http://svn.apache.org/viewcvs/cocoon/whiteboard/maven2/cocoon-flat-layout/cocoon-core/src/main/java/org/apache/cocoon/core/container/handler/LazyHandler.java?rev=330548&view=auto
==============================================================================
--- cocoon/whiteboard/maven2/cocoon-flat-layout/cocoon-core/src/main/java/org/apache/cocoon/core/container/handler/LazyHandler.java (added)
+++ cocoon/whiteboard/maven2/cocoon-flat-layout/cocoon-core/src/main/java/org/apache/cocoon/core/container/handler/LazyHandler.java Thu Nov  3 05:41:06 2005
@@ -0,0 +1,128 @@
+/* 
+ * Copyright 2002-2005 The Apache Software Foundation
+ * Licensed  under the  Apache License,  Version 2.0  (the "License");
+ * you may not use  this file  except in  compliance with the License.
+ * You may obtain a copy of the License at 
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed  under the  License is distributed on an "AS IS" BASIS,
+ * WITHOUT  WARRANTIES OR CONDITIONS  OF ANY KIND, either  express  or
+ * implied.
+ * 
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.cocoon.core.container.handler;
+
+import org.apache.avalon.framework.configuration.Configuration;
+import org.apache.cocoon.components.ComponentInfo;
+import org.apache.cocoon.core.CoreResourceNotFoundException;
+import org.apache.cocoon.core.container.ComponentEnvironment;
+
+/**
+ * 
+ * @version $Id: LazyHandler.java 312637 2005-10-10 13:00:42Z cziegeler $
+ * @since 2.2
+ */
+public class LazyHandler implements ComponentHandler {
+    
+    private String role;
+    private String className;
+    private Configuration config;
+    private ComponentEnvironment compEnv;
+    
+    private ComponentHandler delegate;
+    
+    public LazyHandler(String role, String className, Configuration configuration, ComponentEnvironment environment) {
+        this.role = role;
+        this.className = className;
+        this.config = configuration;
+        this.compEnv = environment;
+    }
+    
+    private ComponentHandler getDelegate() throws Exception {
+        if (this.delegate == null) {
+//            System.err.println("######## " + System.identityHashCode(compEnv.serviceManager) + " creating handler for " + this.role);
+            ComponentInfo info = new ComponentInfo();
+            info.setConfiguration(config);
+            info.setServiceClassName(className);
+
+            this.delegate = AbstractComponentHandler.getComponentHandler(role, compEnv, info);
+            this.delegate.initialize();
+        }
+        
+        return this.delegate;
+    }
+    
+    private ComponentHandler getDelegateRE() {
+        try {
+            return getDelegate();
+        } catch (Exception e) {
+            throw new CoreResourceNotFoundException("Cannot get delegate handler", e);
+        }
+    }
+
+    /* (non-Javadoc)
+     * @see org.apache.cocoon.core.container.ComponentHandler#get()
+     */
+    public Object get() throws Exception {
+        return getDelegate().get();
+    }
+
+    /* (non-Javadoc)
+     * @see org.apache.cocoon.core.container.ComponentHandler#put(java.lang.Object)
+     */
+    public void put(Object component) throws Exception {
+        getDelegate().put(component);
+    }
+
+    /* (non-Javadoc)
+     * @see org.apache.cocoon.core.container.ComponentHandler#isSingleton()
+     */
+    public boolean isSingleton() {
+        return getDelegateRE().isSingleton();
+    }
+
+    /* (non-Javadoc)
+     * @see org.apache.cocoon.core.container.ComponentHandler#canBeDisposed()
+     */
+    public boolean canBeDisposed() {
+        // We can always be disposed if handler was never used
+        if (this.delegate == null) {
+            return true;
+        } 
+        return getDelegateRE().canBeDisposed();
+    }
+
+    /* (non-Javadoc)
+     * @see org.apache.cocoon.core.container.ComponentHandler#dispose()
+     */
+    public void dispose() {
+        // Dispose only if handler was actually used
+        if (this.delegate != null) {
+            this.delegate.dispose();
+        }
+    }
+
+    /* (non-Javadoc)
+     * @see org.apache.cocoon.core.container.ComponentHandler#initialize()
+     */
+    public void initialize() throws Exception {
+        // nothing (delegate is initialized when created)
+    }
+
+    /* (non-Javadoc)
+     * @see org.apache.cocoon.core.container.ComponentHandler#getInfo()
+     */
+    public ComponentInfo getInfo() {
+        if (this.delegate == null) {
+            final ComponentInfo info = new ComponentInfo();
+            info.setServiceClassName(className);
+            info.setConfiguration(config);
+            return info;
+        } 
+        return this.delegate.getInfo();
+    }
+}

Propchange: cocoon/whiteboard/maven2/cocoon-flat-layout/cocoon-core/src/main/java/org/apache/cocoon/core/container/handler/LazyHandler.java
------------------------------------------------------------------------------
    svn:eol-style = native

Added: cocoon/whiteboard/maven2/cocoon-flat-layout/cocoon-core/src/main/java/org/apache/cocoon/core/container/handler/NonThreadSafePoolableComponentHandler.java
URL: http://svn.apache.org/viewcvs/cocoon/whiteboard/maven2/cocoon-flat-layout/cocoon-core/src/main/java/org/apache/cocoon/core/container/handler/NonThreadSafePoolableComponentHandler.java?rev=330548&view=auto
==============================================================================
--- cocoon/whiteboard/maven2/cocoon-flat-layout/cocoon-core/src/main/java/org/apache/cocoon/core/container/handler/NonThreadSafePoolableComponentHandler.java (added)
+++ cocoon/whiteboard/maven2/cocoon-flat-layout/cocoon-core/src/main/java/org/apache/cocoon/core/container/handler/NonThreadSafePoolableComponentHandler.java Thu Nov  3 05:41:06 2005
@@ -0,0 +1,247 @@
+/* 
+ * Copyright 2002-2005 The Apache Software Foundation
+ * Licensed  under the  Apache License,  Version 2.0  (the "License");
+ * you may not use  this file  except in  compliance with the License.
+ * You may obtain a copy of the License at 
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed  under the  License is distributed on an "AS IS" BASIS,
+ * WITHOUT  WARRANTIES OR CONDITIONS  OF ANY KIND, either  express  or
+ * implied.
+ * 
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.cocoon.core.container.handler;
+
+import java.util.Iterator;
+import java.util.LinkedList;
+
+import org.apache.avalon.framework.configuration.Configuration;
+import org.apache.avalon.framework.logger.Logger;
+import org.apache.cocoon.components.ComponentInfo;
+import org.apache.cocoon.core.container.ComponentFactory;
+
+/**
+ * The PoolableComponentHandler to make sure that poolable components are initialized
+ * destroyed and pooled correctly.
+ * <p>
+ * Components which implement Poolable may be configured to be pooled using the following
+ *  example configuration.  This example assumes that the user component class MyComp
+ *  implements Poolable.
+ * <p>
+ * Configuration Example:
+ * <pre>
+ *   &lt;my-comp pool-max="8"/&gt;
+ * </pre>
+ * <p>
+ * Roles Example:
+ * <pre>
+ *   &lt;role name="com.mypkg.MyComponent"
+ *         shorthand="my-comp"
+ *         default-class="com.mypkg.DefaultMyComponent"/&gt;
+ * </pre>
+ * <p>
+ * Configuration Attributes:
+ * <ul>
+ * <li>The <code>pool-max</code> attribute is used to set the maximum number of components which
+ *  will be pooled. (Defaults to "8") If additional instances are required, they're created,
+ *  but not pooled.</li>
+ * </ul>
+ *
+ * @version $Id: NonThreadSafePoolableComponentHandler.java 312637 2005-10-10 13:00:42Z cziegeler $
+ * @since 2.2
+ */
+public class NonThreadSafePoolableComponentHandler
+extends AbstractFactoryHandler {
+    
+    /** The default max size of the pool */
+    public static final int DEFAULT_MAX_POOL_SIZE = 8;
+
+    /**
+     * Object used to synchronize access to the get and put methods
+     */
+    protected final Object semaphore = new Object();
+
+    /**
+     * The maximum size of the pool.
+     */
+    private final int max;
+
+    /**
+     * List of the Poolable instances which are available for use.
+     */
+    private LinkedList ready;
+
+    /**
+     * Store the size of the ready list to optimize operations which require this value.
+     */
+    private int readySize;
+
+    /**
+     * Total number of Poolable instances in the pool
+     */
+    private int size;
+    
+    /**
+     * Create a PoolableComponentHandler which manages a pool of Components
+     *  created by the specified factory object.
+     *
+     * @param factory The factory object which is responsible for creating the components
+     *                managed by the ComponentHandler.
+     * @param config The configuration to use to configure the pool.
+     */
+    public NonThreadSafePoolableComponentHandler( final ComponentInfo info,
+                                     final Logger logger,
+                                     final ComponentFactory factory,
+                                     final Configuration config )
+    throws Exception {
+        super(info, logger, factory);
+
+        final int poolMax = config.getAttributeAsInteger( "pool-max", DEFAULT_MAX_POOL_SIZE );
+        this.max = ( poolMax <= 0 ? Integer.MAX_VALUE : poolMax );
+
+        // Create the pool lists.
+        this.ready = new LinkedList();
+    }
+
+    /**
+     * Dispose of the ComponentHandler and any associated Pools and Factories.
+     */
+    public void dispose() {
+        super.dispose();
+
+        // Any Poolables in the m_ready list need to be disposed of
+        synchronized( this.semaphore ) {
+            // Remove objects in the ready list.
+            for( Iterator iter = this.ready.iterator(); iter.hasNext(); ) {
+                Object poolable = iter.next();
+                iter.remove();
+                this.readySize--;
+                this.permanentlyRemovePoolable( poolable );
+            }
+
+            if( this.size > 0 && this.logger.isDebugEnabled() ) {
+                this.logger.debug( "There were " + this.size
+                                   + " outstanding objects when the pool was disposed." );
+            }
+        }
+    }
+    
+    /**
+     * Permanently removes a poolable from the pool's active list and
+     *  destroys it so that it will not ever be reused.
+     * <p>
+     * This method is only called by threads that have m_semaphore locked.
+     */
+    protected void permanentlyRemovePoolable( Object poolable ) {
+        this.size--;
+        this.decommission( poolable );
+    }
+
+    /**
+     * Gets a Poolable from the pool.  If there is room in the pool, a new Poolable will be
+     *  created.  Depending on the parameters to the constructor, the method may block or throw
+     *  an exception if a Poolable is not available on the pool.
+     *
+     * @return Always returns a Poolable.  Contract requires that put must always be called with
+     *  the Poolable returned.
+     * @throws Exception An exception may be thrown as described above or if there is an exception
+     *  thrown by the ObjectFactory's newInstance() method.
+     */
+    protected Object getFromPool() throws Exception {
+        Object poolable;
+        synchronized( this.semaphore ) {
+            // Look for a Poolable at the end of the m_ready list
+            if ( this.readySize > 0 ){
+                // A poolable is ready and waiting in the pool
+                poolable = this.ready.removeLast();
+                this.readySize--;
+            } else {
+                // Create a new poolable.  May throw an exception if the poolable can not be
+                //  instantiated.
+                poolable = this.factory.newInstance();
+                this.size++;
+
+                if ( this.logger.isDebugEnabled() ) {
+                    this.logger.debug( "Created a new " + poolable.getClass().getName()
+                                       + " from the object factory." );
+                }
+            }
+        }
+
+        this.factory.exitingPool(poolable);
+        
+        if( this.logger.isDebugEnabled() ) {
+            this.logger.debug( "Got a " + poolable.getClass().getName() + " from the pool." );
+        }
+
+        return poolable;
+    }
+
+    /**
+     * Returns a poolable to the pool 
+     *
+     * @param poolable Poolable to return to the pool.
+     */
+    protected void putIntoPool( final Object poolable ) {
+        try {
+            this.factory.enteringPool(poolable);
+        } catch (Exception ignore) {
+            this.logger.warn("Exception during putting component back into the pool.", ignore);
+        }
+
+        synchronized( this.semaphore ) {
+            if( this.size <= this.max ) {
+                if( this.disposed ) {
+                    // The pool has already been disposed.
+                    if( this.logger.isDebugEnabled() ) {
+                        this.logger.debug( "Put called for a " + poolable.getClass().getName()
+                                           + " after the pool was disposed." );
+                    }
+
+                    this.permanentlyRemovePoolable( poolable );
+                } else {
+                    // There is room in the pool to keep this poolable.
+                    if( this.logger.isDebugEnabled() ) {
+                        this.logger.debug( "Put a " + poolable.getClass().getName()
+                                           + " back into the pool." );
+                    }
+
+                    this.ready.addLast( poolable );
+                    this.readySize++;
+
+                }
+            } else {
+                // More Poolables were created than can be held in the pool, so remove.
+                if( this.logger.isDebugEnabled() ) {
+                    this.logger.debug( "No room to put a " + poolable.getClass().getName()
+                                       + " back into the pool, so remove it." );
+                }
+
+                this.permanentlyRemovePoolable( poolable );
+            }
+        }
+    }
+    
+    protected void doInitialize() {
+        // nothing to do here
+    }
+    
+    
+    /* (non-Javadoc)
+     * @see org.apache.cocoon.core.container.handler.AbstractComponentHandler#doGet()
+     */
+    protected Object doGet() throws Exception {
+        return this.getFromPool();
+    }
+
+    /* (non-Javadoc)
+     * @see org.apache.cocoon.core.container.handler.AbstractComponentHandler#doPut(java.lang.Object)
+     */
+    protected void doPut(Object component) throws Exception {
+        this.putIntoPool(component);
+    }
+}

Propchange: cocoon/whiteboard/maven2/cocoon-flat-layout/cocoon-core/src/main/java/org/apache/cocoon/core/container/handler/NonThreadSafePoolableComponentHandler.java
------------------------------------------------------------------------------
    svn:eol-style = native

Added: cocoon/whiteboard/maven2/cocoon-flat-layout/cocoon-core/src/main/java/org/apache/cocoon/core/container/handler/PoolableComponentHandler.java
URL: http://svn.apache.org/viewcvs/cocoon/whiteboard/maven2/cocoon-flat-layout/cocoon-core/src/main/java/org/apache/cocoon/core/container/handler/PoolableComponentHandler.java?rev=330548&view=auto
==============================================================================
--- cocoon/whiteboard/maven2/cocoon-flat-layout/cocoon-core/src/main/java/org/apache/cocoon/core/container/handler/PoolableComponentHandler.java (added)
+++ cocoon/whiteboard/maven2/cocoon-flat-layout/cocoon-core/src/main/java/org/apache/cocoon/core/container/handler/PoolableComponentHandler.java Thu Nov  3 05:41:06 2005
@@ -0,0 +1,169 @@
+/* 
+ * Copyright 2002-2005 The Apache Software Foundation
+ * Licensed  under the  Apache License,  Version 2.0  (the "License");
+ * you may not use  this file  except in  compliance with the License.
+ * You may obtain a copy of the License at 
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed  under the  License is distributed on an "AS IS" BASIS,
+ * WITHOUT  WARRANTIES OR CONDITIONS  OF ANY KIND, either  express  or
+ * implied.
+ * 
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.cocoon.core.container.handler;
+
+import java.lang.reflect.InvocationHandler;
+import java.lang.reflect.InvocationTargetException;
+import java.lang.reflect.Method;
+import java.lang.reflect.Proxy;
+import java.util.HashSet;
+import java.util.Set;
+
+import org.apache.avalon.framework.configuration.Configuration;
+import org.apache.avalon.framework.logger.Logger;
+import org.apache.cocoon.components.ComponentInfo;
+import org.apache.cocoon.core.Core;
+import org.apache.cocoon.core.container.ComponentFactory;
+
+/**
+ * This is an extension to the {@link org.apache.cocoon.core.container.handler.NonThreadSafePoolableComponentHandler}
+ * that uses proxies to make the poolable components thread safe.
+ *
+ * @version $Id: PoolableComponentHandler.java 312637 2005-10-10 13:00:42Z cziegeler $
+ * @since 2.2
+ */
+public class PoolableComponentHandler
+extends NonThreadSafePoolableComponentHandler {
+    
+    /** All the interfaces for the proxy */
+    protected final Class[] interfaces;
+    
+    /**
+     * Create a PoolableComponentHandler which manages a pool of Components
+     *  created by the specified factory object.
+     *
+     * @param factory The factory object which is responsible for creating the components
+     *                managed by the ComponentHandler.
+     * @param config The configuration to use to configure the pool.
+     */
+    public PoolableComponentHandler( final ComponentInfo info,
+                                     final Logger logger,
+                                     final ComponentFactory factory,
+                                     final Configuration config )
+    throws Exception {
+        super(info, logger, factory, config);
+        final HashSet workInterfaces = new HashSet();
+
+        // Get *all* interfaces
+        this.guessWorkInterfaces( factory.getCreatedClass(), workInterfaces );
+
+        this.interfaces = (Class[]) workInterfaces.toArray( new Class[workInterfaces.size()] );
+    }
+    
+    /* (non-Javadoc)
+     * @see org.apache.cocoon.core.container.handler.AbstractComponentHandler#doGet()
+     */
+    protected Object doGet() throws Exception {
+        return this.createProxy();
+    }
+
+    /* (non-Javadoc)
+     * @see org.apache.cocoon.core.container.handler.AbstractComponentHandler#doPut(java.lang.Object)
+     */
+    protected void doPut(Object component) throws Exception {
+        // nothing to do
+    }
+
+    /* (non-Javadoc)
+     * @see org.apache.cocoon.core.container.handler.AbstractComponentHandler#doInitialize()
+     */
+    protected void doInitialize() {
+        // nothing to do here
+    }
+    
+    protected Object createProxy() {
+        return Proxy.newProxyInstance(this.factory.getCreatedClass().getClassLoader(), 
+                                      this.interfaces, 
+                                      new ProxyHandler(this));
+    }
+
+    /**
+     * Get a list of interfaces to proxy by scanning through
+     * all interfaces a class implements.
+     *
+     * @param clazz           the class
+     * @param workInterfaces  the set of current work interfaces
+     */
+    private void guessWorkInterfaces( final Class clazz,
+                                      final Set workInterfaces ) {
+        if ( null != clazz ) {
+            this.addInterfaces( clazz.getInterfaces(), workInterfaces );
+
+            this.guessWorkInterfaces( clazz.getSuperclass(), workInterfaces );
+        }
+    }
+
+    /**
+     * Get a list of interfaces to proxy by scanning through
+     * all interfaces a class implements.
+     *
+     * @param interfaces      the array of interfaces
+     * @param workInterfaces  the set of current work interfaces
+     */
+    private void addInterfaces( final Class[] interfaces,
+                                final Set workInterfaces ) {
+        for ( int i = 0; i < interfaces.length; i++ ) {
+            workInterfaces.add( interfaces[i] );
+            this.addInterfaces(interfaces[i].getInterfaces(), workInterfaces);
+        }
+    }
+
+    protected static final class ProxyHandler implements InvocationHandler, Core.CleanupTask {
+        
+        private final ThreadLocal componentHolder = new ThreadLocal();
+        private final PoolableComponentHandler handler;
+        
+        public ProxyHandler(PoolableComponentHandler handler) {
+            this.handler = handler;
+        }
+        
+        /* (non-Javadoc)
+         * @see java.lang.reflect.InvocationHandler#invoke(java.lang.Object, java.lang.reflect.Method, java.lang.Object[])
+         */
+        public Object invoke(Object proxy, Method method, Object[] args)
+        throws Throwable {
+            if ( method.getName().equals("hashCode") && args == null ) {
+                return new Integer(this.hashCode());
+            }
+            if ( this.componentHolder.get() == null ) {
+                this.componentHolder.set(this.handler.getFromPool());
+                Core.addCleanupTask(this);
+            }
+            try {
+                return method.invoke(this.componentHolder.get(), args);
+            } catch (InvocationTargetException ite) {
+                throw ite.getTargetException();
+            }
+        }
+        
+        
+        /* (non-Javadoc)
+         * @see org.apache.cocoon.core.Core.CleanupTask#invoke()
+         */
+        public void invoke() {
+            try {
+                final Object o = this.componentHolder.get();
+                this.handler.putIntoPool(o);
+            } catch (Exception ignore) {
+                // we ignore this
+            }
+            this.componentHolder.set(null);
+        }
+    }
+    
+    
+}

Propchange: cocoon/whiteboard/maven2/cocoon-flat-layout/cocoon-core/src/main/java/org/apache/cocoon/core/container/handler/PoolableComponentHandler.java
------------------------------------------------------------------------------
    svn:eol-style = native

Added: cocoon/whiteboard/maven2/cocoon-flat-layout/cocoon-core/src/main/java/org/apache/cocoon/core/container/handler/SingleThreadedComponentHandler.java
URL: http://svn.apache.org/viewcvs/cocoon/whiteboard/maven2/cocoon-flat-layout/cocoon-core/src/main/java/org/apache/cocoon/core/container/handler/SingleThreadedComponentHandler.java?rev=330548&view=auto
==============================================================================
--- cocoon/whiteboard/maven2/cocoon-flat-layout/cocoon-core/src/main/java/org/apache/cocoon/core/container/handler/SingleThreadedComponentHandler.java (added)
+++ cocoon/whiteboard/maven2/cocoon-flat-layout/cocoon-core/src/main/java/org/apache/cocoon/core/container/handler/SingleThreadedComponentHandler.java Thu Nov  3 05:41:06 2005
@@ -0,0 +1,73 @@
+/* 
+ * Copyright 2002-2005 The Apache Software Foundation
+ * Licensed  under the  Apache License,  Version 2.0  (the "License");
+ * you may not use  this file  except in  compliance with the License.
+ * You may obtain a copy of the License at 
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed  under the  License is distributed on an "AS IS" BASIS,
+ * WITHOUT  WARRANTIES OR CONDITIONS  OF ANY KIND, either  express  or
+ * implied.
+ * 
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.cocoon.core.container.handler;
+
+import org.apache.avalon.framework.logger.Logger;
+import org.apache.cocoon.components.ComponentInfo;
+import org.apache.cocoon.core.container.ComponentFactory;
+
+/**
+ * The DefaultComponentHandler to make sure components are initialized
+ * and destroyed correctly.
+ *
+ * @version $Id: SingleThreadedComponentHandler.java 312637 2005-10-10 13:00:42Z cziegeler $
+ * @since 2.2
+ */
+public class SingleThreadedComponentHandler
+extends AbstractFactoryHandler {
+
+    /**
+     * Create a SingleThreadedComponentHandler which manages a pool of Components
+     *  created by the specified factory object.
+     *
+     * @param logger The logger to use
+     * @param factory The factory object which is responsible for creating the components
+     *                managed by the handler.
+     */
+    public SingleThreadedComponentHandler( final ComponentInfo info,
+                                    final Logger logger,
+                                    final ComponentFactory factory ) {
+        super(info, logger, factory);
+    }
+
+    /**
+     * Get a reference of the desired Component
+     *
+     * @return A component instance.
+     *
+     * @throws Exception If there are any problems encountered acquiring a
+     *                   component instance.
+     */
+    protected Object doGet()
+    throws Exception {
+        return this.factory.newInstance();
+    }
+
+    /**
+     * Return a reference of the desired Component
+     *
+     * @param component Component to be be put/released back to the handler.
+     */
+    protected void doPut( final Object component ) {
+        this.decommission( component );
+    }
+    
+    protected void doInitialize() {
+        // nothing to do here
+    }
+
+}

Propchange: cocoon/whiteboard/maven2/cocoon-flat-layout/cocoon-core/src/main/java/org/apache/cocoon/core/container/handler/SingleThreadedComponentHandler.java
------------------------------------------------------------------------------
    svn:eol-style = native

Added: cocoon/whiteboard/maven2/cocoon-flat-layout/cocoon-core/src/main/java/org/apache/cocoon/core/container/handler/ThreadSafeComponentHandler.java
URL: http://svn.apache.org/viewcvs/cocoon/whiteboard/maven2/cocoon-flat-layout/cocoon-core/src/main/java/org/apache/cocoon/core/container/handler/ThreadSafeComponentHandler.java?rev=330548&view=auto
==============================================================================
--- cocoon/whiteboard/maven2/cocoon-flat-layout/cocoon-core/src/main/java/org/apache/cocoon/core/container/handler/ThreadSafeComponentHandler.java (added)
+++ cocoon/whiteboard/maven2/cocoon-flat-layout/cocoon-core/src/main/java/org/apache/cocoon/core/container/handler/ThreadSafeComponentHandler.java Thu Nov  3 05:41:06 2005
@@ -0,0 +1,82 @@
+/* 
+ * Copyright 2002-2005 The Apache Software Foundation
+ * Licensed  under the  Apache License,  Version 2.0  (the "License");
+ * you may not use  this file  except in  compliance with the License.
+ * You may obtain a copy of the License at 
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed  under the  License is distributed on an "AS IS" BASIS,
+ * WITHOUT  WARRANTIES OR CONDITIONS  OF ANY KIND, either  express  or
+ * implied.
+ * 
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.cocoon.core.container.handler;
+
+import org.apache.avalon.framework.logger.Logger;
+import org.apache.cocoon.components.ComponentInfo;
+import org.apache.cocoon.core.container.ComponentFactory;
+
+/**
+ * The ThreadSafeComponentHandler to make sure components are initialized
+ * and destroyed correctly.
+ *
+ * @version $Id: ThreadSafeComponentHandler.java 312637 2005-10-10 13:00:42Z cziegeler $
+ * @since 2.2
+ */
+public class ThreadSafeComponentHandler
+extends AbstractFactoryHandler {
+    
+    private Object instance;
+
+    /**
+     * Create a ThreadSafeComponentHandler which manages a single instance
+     * of an object return by the component factory.
+     * @param logger The logger to use
+     * @param factory The factory object which is responsible for creating the components
+     *                managed by the handler.
+     */
+    public ThreadSafeComponentHandler( final ComponentInfo info,
+                                       final Logger logger,
+                                       final ComponentFactory factory ) {
+        super(info, logger, factory);
+    }
+    
+    public boolean isSingleton() {
+        return true;
+    }
+
+    public void doInitialize() throws Exception {
+        if( this.instance == null ) {
+            this.instance = this.factory.newInstance();
+        }
+    }
+
+    /**
+     * Get a reference of the desired Component
+     */
+    protected Object doGet()
+    throws Exception {
+        return this.instance;
+    }
+
+    /**
+     * Return a reference of the desired Component
+     */
+    protected void doPut( final Object component ) {
+        // nothing to do
+    }
+
+    /**
+     * Dispose of the ComponentHandler and any associated Pools and Factories.
+     */
+    public void dispose() {
+        this.decommission( this.instance );
+        this.instance = null;
+
+        super.dispose();
+    }
+}

Propchange: cocoon/whiteboard/maven2/cocoon-flat-layout/cocoon-core/src/main/java/org/apache/cocoon/core/container/handler/ThreadSafeComponentHandler.java
------------------------------------------------------------------------------
    svn:eol-style = native

Added: cocoon/whiteboard/maven2/cocoon-flat-layout/cocoon-core/src/main/java/org/apache/cocoon/core/container/util/PropertyHelper.java
URL: http://svn.apache.org/viewcvs/cocoon/whiteboard/maven2/cocoon-flat-layout/cocoon-core/src/main/java/org/apache/cocoon/core/container/util/PropertyHelper.java?rev=330548&view=auto
==============================================================================
--- cocoon/whiteboard/maven2/cocoon-flat-layout/cocoon-core/src/main/java/org/apache/cocoon/core/container/util/PropertyHelper.java (added)
+++ cocoon/whiteboard/maven2/cocoon-flat-layout/cocoon-core/src/main/java/org/apache/cocoon/core/container/util/PropertyHelper.java Thu Nov  3 05:41:06 2005
@@ -0,0 +1,101 @@
+/* 
+ * Copyright 2002-2005 The Apache Software Foundation
+ * Licensed  under the  Apache License,  Version 2.0  (the "License");
+ * you may not use  this file  except in  compliance with the License.
+ * You may obtain a copy of the License at 
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed  under the  License is distributed on an "AS IS" BASIS,
+ * WITHOUT  WARRANTIES OR CONDITIONS  OF ANY KIND, either  express  or
+ * implied.
+ * 
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.cocoon.core.container.util;
+
+import org.apache.cocoon.core.Settings;
+
+/**
+ * Helper class for replacing property references with the value of the
+ * property
+ *
+ * @version $Id: PropertyHelper.java 312637 2005-10-10 13:00:42Z cziegeler $
+ * @since 2.2
+ */
+public class PropertyHelper {
+
+        /**
+     * Replace all property references in the string with the current value
+     * and return it.
+     */
+    public static String replace(String value, Settings settings) {
+        // quick test for null or no references
+        if ( value == null || value.indexOf("${") == -1 ) {
+            return value;
+        }
+        final StringBuffer buffer = new StringBuffer();
+        int prev = 0;
+        int pos;
+        
+        // search for the next instance of $ from the 'prev' position
+        while ((pos = value.indexOf("$", prev)) >= 0) {
+
+            // if there was any text before this, add it
+            if (pos > prev) {
+                buffer.append(value.substring(prev, pos));
+            }
+            
+            // if we are at the end of the string, end
+            if (pos == (value.length() - 1)) {
+                buffer.append("$");
+                prev = pos + 1;
+            } else if (value.charAt(pos + 1) != '{') {
+                // peek ahead to see if the next char is a property or not
+                // not a property: insert the char as a literal
+                buffer.append(value.substring(pos, pos + 2));
+                prev = pos + 2;
+
+            } else {
+                // start token found, check for end token
+                int endName = value.indexOf('}', pos);
+                if (endName == -1) {
+                    // no end token found, just append the rest
+                    buffer.append(value.substring(pos));
+                    prev = value.length();
+                } else {
+                    final String propertyName = value.substring(pos + 2, endName);
+                    String propertyValue = getProperty(propertyName, settings);
+                    // compatibility fallback - if the value is null, just readd token
+                    if (propertyValue == null) {
+                        buffer.append("${");
+                        buffer.append(propertyName);
+                        buffer.append('}');
+                    } else {
+                        buffer.append(propertyValue);
+                    }
+                    prev = endName + 1;
+                }
+            }
+        }
+        // no more tokens found
+        // append the rest
+        if (prev < value.length()) {
+             buffer.append(value.substring(prev));
+        }
+        return buffer.toString();
+    }
+
+    static String getProperty(String name, Settings settings) {
+        String value = null;
+        if ( settings != null ) {
+            value = settings.getProperty(name);
+        }
+        if ( value == null ) {
+            value = System.getProperty(name);
+        }
+        return value;
+    }
+}

Propchange: cocoon/whiteboard/maven2/cocoon-flat-layout/cocoon-core/src/main/java/org/apache/cocoon/core/container/util/PropertyHelper.java
------------------------------------------------------------------------------
    svn:eol-style = native

Added: cocoon/whiteboard/maven2/cocoon-flat-layout/cocoon-core/src/main/java/org/apache/cocoon/core/logging/CocoonLogKitLoggerManager.java
URL: http://svn.apache.org/viewcvs/cocoon/whiteboard/maven2/cocoon-flat-layout/cocoon-core/src/main/java/org/apache/cocoon/core/logging/CocoonLogKitLoggerManager.java?rev=330548&view=auto
==============================================================================
--- cocoon/whiteboard/maven2/cocoon-flat-layout/cocoon-core/src/main/java/org/apache/cocoon/core/logging/CocoonLogKitLoggerManager.java (added)
+++ cocoon/whiteboard/maven2/cocoon-flat-layout/cocoon-core/src/main/java/org/apache/cocoon/core/logging/CocoonLogKitLoggerManager.java Thu Nov  3 05:41:06 2005
@@ -0,0 +1,70 @@
+/*
+ * Copyright 2005 The Apache Software Foundation.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.cocoon.core.logging;
+
+import org.apache.avalon.excalibur.logger.LogKitLoggerManager;
+import org.apache.avalon.excalibur.logger.LoggerManager;
+import org.apache.cocoon.environment.Environment;
+import org.apache.log.ContextMap;
+import org.apache.log.Hierarchy;
+
+/**
+ * This is an extension of the {@link LoggerManager}. It can be used to
+ * initialize a logging context on a per thread basis. This allows the
+ * logging implementation to access and log information about the current
+ * request.
+ * 
+ * @version $Id: CocoonLogKitLoggerManager.java 312962 2005-10-11 21:39:38Z sylvain $
+ * @since 2.2
+ */
+public class CocoonLogKitLoggerManager 
+    extends LogKitLoggerManager
+    implements PerRequestLoggerManager {
+    
+    public CocoonLogKitLoggerManager() {
+        // Use the default hierarchy, which is also used by commons-logging
+        super(Hierarchy.getDefaultHierarchy());
+    }
+
+    /**
+     * @see org.apache.cocoon.core.logging.PerRequestLoggerManager#initializePerRequestLoggingContext(org.apache.cocoon.environment.Environment)
+     */
+    public Object initializePerRequestLoggingContext(Environment env) {
+        ContextMap ctxMap;
+        // Initialize a fresh log context containing the object model: it
+        // will be used by the CocoonLogFormatter
+        ctxMap = ContextMap.getCurrentContext();
+        // Add thread name (default content for empty context)
+        String threadName = Thread.currentThread().getName();
+        ctxMap.set("threadName", threadName);
+        // Add the object model
+        ctxMap.set("objectModel", env.getObjectModel());
+        // Add a unique request id (threadName + currentTime
+        ctxMap.set("request-id", threadName + System.currentTimeMillis());
+        
+        return ctxMap;
+    }
+
+    /**
+     * @see org.apache.cocoon.core.logging.PerRequestLoggerManager#cleanPerRequestLoggingContext(java.lang.Object)
+     */
+    public void cleanPerRequestLoggingContext(Object ctxMap) {
+        if ( ctxMap != null ) {
+            ((ContextMap)ctxMap).clear();
+        }
+    }
+
+}

Propchange: cocoon/whiteboard/maven2/cocoon-flat-layout/cocoon-core/src/main/java/org/apache/cocoon/core/logging/CocoonLogKitLoggerManager.java
------------------------------------------------------------------------------
    svn:eol-style = native

Added: cocoon/whiteboard/maven2/cocoon-flat-layout/cocoon-core/src/main/java/org/apache/cocoon/core/logging/PerRequestLoggerManager.java
URL: http://svn.apache.org/viewcvs/cocoon/whiteboard/maven2/cocoon-flat-layout/cocoon-core/src/main/java/org/apache/cocoon/core/logging/PerRequestLoggerManager.java?rev=330548&view=auto
==============================================================================
--- cocoon/whiteboard/maven2/cocoon-flat-layout/cocoon-core/src/main/java/org/apache/cocoon/core/logging/PerRequestLoggerManager.java (added)
+++ cocoon/whiteboard/maven2/cocoon-flat-layout/cocoon-core/src/main/java/org/apache/cocoon/core/logging/PerRequestLoggerManager.java Thu Nov  3 05:41:06 2005
@@ -0,0 +1,41 @@
+/*
+ * Copyright 2005 The Apache Software Foundation.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.cocoon.core.logging;
+
+import org.apache.avalon.excalibur.logger.LoggerManager;
+import org.apache.cocoon.environment.Environment;
+
+/**
+ * This is an extension of the {@link LoggerManager}. It can be used to
+ * initialize a logging context on a per thread basis. This allows the
+ * logging implementation to access and log information about the current
+ * request.
+ * 
+ * @version $Id: PerRequestLoggerManager.java 225167 2005-07-25 19:24:01Z cziegeler $
+ * @since 2.2
+ */
+public interface PerRequestLoggerManager extends LoggerManager {
+
+    /**
+     * Initialize the context for logging.
+     */
+    Object initializePerRequestLoggingContext(Environment env);
+
+    /**
+     * Clean up the logging context.
+     */
+    void cleanPerRequestLoggingContext(Object ctxMap);
+}

Propchange: cocoon/whiteboard/maven2/cocoon-flat-layout/cocoon-core/src/main/java/org/apache/cocoon/core/logging/PerRequestLoggerManager.java
------------------------------------------------------------------------------
    svn:eol-style = native



Mime
View raw message