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 * 009 *****************************************************************************/ 010 package org.picocontainer.adapters; 011 012 import org.picocontainer.ComponentMonitor; 013 import org.picocontainer.PicoVisitor; 014 import org.picocontainer.ComponentAdapter; 015 import org.picocontainer.ComponentMonitorStrategy; 016 import org.picocontainer.PicoContainer; 017 import org.picocontainer.PicoCompositionException; 018 import org.picocontainer.monitors.AbstractComponentMonitor; 019 import org.picocontainer.monitors.NullComponentMonitor; 020 021 import java.io.Serializable; 022 023 /** 024 * Base class for a ComponentAdapter with general functionality. 025 * This implementation provides basic checks for a healthy implementation of a ComponentAdapter. 026 * It does not allow to use <code>null</code> for the component key or the implementation, 027 * ensures that the implementation is a concrete class and that the key is assignable from the 028 * implementation if the key represents a type. 029 * 030 * @author Paul Hammant 031 * @author Aslak Hellesøy 032 * @author Jon Tirsén 033 */ 034 public abstract class AbstractAdapter<T> implements ComponentAdapter<T>, ComponentMonitorStrategy, Serializable { 035 private Object componentKey; 036 private Class<T> componentImplementation; 037 private ComponentMonitor componentMonitor; 038 039 040 /** 041 * Constructs a new ComponentAdapter for the given key and implementation. 042 * @param componentKey the search key for this implementation 043 * @param componentImplementation the concrete implementation 044 */ 045 public AbstractAdapter(Object componentKey, Class componentImplementation) { 046 this(componentKey, componentImplementation, new AbstractComponentMonitor()); 047 this.componentMonitor = new NullComponentMonitor(); 048 } 049 050 /** 051 * Constructs a new ComponentAdapter for the given key and implementation. 052 * @param componentKey the search key for this implementation 053 * @param componentImplementation the concrete implementation 054 * @param monitor the component monitor used by this ComponentAdapter 055 */ 056 public AbstractAdapter(Object componentKey, Class componentImplementation, ComponentMonitor monitor) { 057 if (monitor == null) { 058 throw new NullPointerException("ComponentMonitor==null"); 059 } 060 this.componentMonitor = monitor; 061 if (componentImplementation == null) { 062 throw new NullPointerException("componentImplementation"); 063 } 064 this.componentKey = componentKey; 065 this.componentImplementation = componentImplementation; 066 checkTypeCompatibility(); 067 } 068 069 /** 070 * {@inheritDoc} 071 * @see org.picocontainer.ComponentAdapter#getComponentKey() 072 */ 073 public Object getComponentKey() { 074 if (componentKey == null) { 075 throw new NullPointerException("componentKey"); 076 } 077 return componentKey; 078 } 079 080 /** 081 * {@inheritDoc} 082 * @see org.picocontainer.ComponentAdapter#getComponentImplementation() 083 */ 084 public Class<T> getComponentImplementation() { 085 return componentImplementation; 086 } 087 088 protected void checkTypeCompatibility() { 089 if (componentKey instanceof Class) { 090 Class<?> componentType = (Class) componentKey; 091 if (!componentType.isAssignableFrom(componentImplementation)) { 092 throw new ClassCastException(componentImplementation.getName() + " is not a " + componentType.getName()); 093 } 094 } 095 } 096 097 public T getComponentInstance(PicoContainer container) throws PicoCompositionException { 098 return getComponentInstance(container, null); 099 } 100 101 /** 102 * @return Returns the ComponentAdapter's class name and the component's key. 103 * @see java.lang.Object#toString() 104 */ 105 public String toString() { 106 return getDescriptor() + getComponentKey(); 107 } 108 109 public void accept(PicoVisitor visitor) { 110 visitor.visitComponentAdapter(this); 111 } 112 113 public void changeMonitor(ComponentMonitor monitor) { 114 this.componentMonitor = monitor; 115 } 116 117 /** 118 * Returns the monitor currently used 119 * @return The ComponentMonitor currently used 120 */ 121 public ComponentMonitor currentMonitor(){ 122 return componentMonitor; 123 } 124 125 public final ComponentAdapter<T> getDelegate() { 126 return null; 127 } 128 129 public final <U extends ComponentAdapter> U findAdapterOfType(Class<U> componentAdapterType) { 130 return null; 131 } 132 133 134 }