    001    /*****************************************************************************
    002     * Copyright (C) PicoContainer Organization. All rights reserved.            *
    003     * ------------------------------------------------------------------------- *
    004     * The software in this package is published under the terms of the BSD      *
    005     * style license a copy of which has been included with this distribution in *
    006     * the LICENSE.txt file.                                                     *
    007     *                                                                           *
    008     * Original code by Mauro Talevi                                             *
    009     *****************************************************************************/
    010
    011    package org.picocontainer.monitors;
    012
    013    import java.io.Serializable;
    014    import java.lang.reflect.Constructor;
    015    import java.lang.reflect.Member;
    016    import java.lang.reflect.Method;
    017
    018    import org.picocontainer.ComponentAdapter;
    019    import org.picocontainer.ComponentMonitor;
    020    import org.picocontainer.ComponentMonitorStrategy;
    021    import org.picocontainer.MutablePicoContainer;
    022    import org.picocontainer.PicoContainer;
    023    import org.picocontainer.Injector;
    024    import org.picocontainer.Behavior;
    025
    026    /**
    027     * <p>
    028     * A {@link ComponentMonitor monitor} which delegates to another monitor.
    029     * It provides a {@link NullComponentMonitor default ComponentMonitor},
    030     * but does not allow to use <code>null</code> for the delegate.
    031     * </p>
    032     * <p>
    033     * It also supports a {@link org.picocontainer.ComponentMonitorStrategy monitor strategy}
    034     * that allows to change the delegate.
    035     * </p>
    036     *
    037     * @author Mauro Talevi
    038     */
    039    @SuppressWarnings("serial")
    040    public class AbstractComponentMonitor implements ComponentMonitor, ComponentMonitorStrategy, Serializable {
    041
    042
    043            /**
    044             * Delegate monitor to allow for component monitor chaining.
    045             */
    046            private  ComponentMonitor delegate;
    047
    048        /**
    049         * Creates a AbstractComponentMonitor with a given delegate
    050         * @param delegate the ComponentMonitor to which this monitor delegates
    051         */
    052        public AbstractComponentMonitor(ComponentMonitor delegate) {
    053            checkMonitor(delegate);
    054            this.delegate = delegate;
    055        }
    056
    057        /**
    058         * Creates a AbstractComponentMonitor with an instance of
    059         * {@link NullComponentMonitor}.
    060         */
    061        public AbstractComponentMonitor() {
    062            this(new NullComponentMonitor());
    063        }
    064
    065        public <T> Constructor<T> instantiating(PicoContainer container, ComponentAdapter<T> componentAdapter,
    066                                         Constructor<T> constructor
    067        ) {
    068            return delegate.instantiating(container, componentAdapter, constructor);
    069        }
    070
    071        public <T> void instantiated(PicoContainer container, ComponentAdapter<T> componentAdapter,
    072                                 Constructor<T> constructor,
    073                                 Object instantiated,
    074                                 Object[] injected,
    075                                 long duration) {
    076            delegate.instantiated(container, componentAdapter, constructor, instantiated, injected, duration);
    077        }
    078
    079        public <T> void instantiationFailed(PicoContainer container,
    080                                        ComponentAdapter<T> componentAdapter,
    081                                        Constructor<T> constructor,
    082                                        Exception e) {
    083            delegate.instantiationFailed(container, componentAdapter, constructor, e);
    084        }
    085
    086        public Object invoking(PicoContainer container,
    087                               ComponentAdapter<?> componentAdapter,
    088                               Member member,
    089                               Object instance, Object[] args) {
    090            return delegate.invoking(container, componentAdapter, member, instance, args);
    091        }
    092
    093        public void invoked(PicoContainer container,
    094                            ComponentAdapter<?> componentAdapter,
    095                            Member member,
    096                            Object instance,
    097                            long duration, Object[] args, Object retVal) {
    098            delegate.invoked(container, componentAdapter, member, instance, duration, args, retVal);
    099        }
    100
    101        public void invocationFailed(Member member, Object instance, Exception e) {
    102            delegate.invocationFailed(member, instance, e);
    103        }
    104
    105        public void lifecycleInvocationFailed(MutablePicoContainer container,
    106                                              ComponentAdapter<?> componentAdapter, Method method,
    107                                              Object instance,
    108                                              RuntimeException cause) {
    109            delegate.lifecycleInvocationFailed(container, componentAdapter, method,instance, cause);
    110        }
    111
    112        public Object noComponentFound(MutablePicoContainer container, Object componentKey) {
    113            return delegate.noComponentFound(container, componentKey);
    114        }
    115
    116        public Injector newInjector(Injector injector) {
    117            return injector;
    118        }
    119
    120        public Behavior newBehavior(Behavior behavior) {
    121            return behavior;
    122        }
    123
    124        /**
    125         * If the delegate supports a {@link ComponentMonitorStrategy monitor strategy},
    126         * this is used to changed the monitor while keeping the same delegate.
    127         * Else the delegate is replaced by the new monitor.
    128         * {@inheritDoc}
    129         */
    130        public void changeMonitor(ComponentMonitor monitor) {
    131            checkMonitor(monitor);
    132            if ( delegate instanceof ComponentMonitorStrategy ){
    133                ((ComponentMonitorStrategy)delegate).changeMonitor(monitor);
    134            } else {
    135                delegate = monitor;
    136            }
    137        }
    138
    139        public ComponentMonitor currentMonitor() {
    140            if ( delegate instanceof ComponentMonitorStrategy ){
    141                return ((ComponentMonitorStrategy)delegate).currentMonitor();
    142            } else {
    143                return delegate;
    144            }
    145        }
    146
    147        private void checkMonitor(ComponentMonitor monitor) {
    148            if ( monitor == null ){
    149                throw new NullPointerException("monitor");
    150            }
    151        }
    152
    153    }