public class CommonAnnotationBeanPostProcessor extends InitDestroyAnnotationBeanPostProcessor implements InstantiationAwareBeanPostProcessor, BeanFactoryAware, Serializable
BeanPostProcessor
implementation
that supports common Java annotations out of the box, in particular the JSR-250
annotations in the javax.annotation
package. These common Java
annotations are supported in many Java EE 5 technologies (e.g. JSF 1.2),
as well as in Java 6's JAX-WS.
This post-processor includes support for the PostConstruct
and PreDestroy
annotations - as init annotation
and destroy annotation, respectively - through inheriting from
InitDestroyAnnotationBeanPostProcessor
with pre-configured annotation types.
The central element is the Resource
annotation
for annotation-driven injection of named beans, by default from the containing
Spring BeanFactory, with only mappedName
references resolved in JNDI.
The "alwaysUseJndiLookup" flag
enforces JNDI lookups
equivalent to standard Java EE 5 resource injection for name
references
and default names as well. The target beans can be simple POJOs, with no special
requirements other than the type having to match.
The JAX-WS WebServiceRef
annotation is supported too,
analogous to Resource
but with the capability of creating
specific JAX-WS service endpoints. This may either point to an explicitly defined
resource by name or operate on a locally specified JAX-WS service class. Finally,
this post-processor also supports the EJB 3 EJB
annotation,
analogous to Resource
as well, with the capability to
specify both a local bean name and a global JNDI name for fallback retrieval.
The target beans can be plain POJOs as well as EJB 3 Session Beans in this case.
The common annotations supported by this post-processor are available in Java 6 (JDK 1.6) as well as in Java EE 5/6 (which provides a standalone jar for its common annotations as well, allowing for use in any Java 5 based application).
For default usage, resolving resource names as Spring bean names, simply define the following in your application context:
<bean class="org.springframework.context.annotation.CommonAnnotationBeanPostProcessor"/>For direct JNDI access, resolving resource names as JNDI resource references within the Java EE application's "java:comp/env/" namespace, use the following:
<bean class="org.springframework.context.annotation.CommonAnnotationBeanPostProcessor"> <property name="alwaysUseJndiLookup" value="true"/> </bean>
mappedName
references will always be resolved in JNDI,
allowing for global JNDI names (including "java:" prefix) as well. The
"alwaysUseJndiLookup" flag just affects name
references and
default names (inferred from the field name / property name).
NOTE: A default CommonAnnotationBeanPostProcessor will be registered by the "context:annotation-config" and "context:component-scan" XML tags. Remove or turn off the default annotation configuration there if you intend to specify a custom CommonAnnotationBeanPostProcessor bean definition!
NOTE: Annotation injection will be performed before XML injection; thus the latter configuration will override the former for properties wired through both approaches.
setAlwaysUseJndiLookup(boolean)
,
setResourceFactory(org.springframework.beans.factory.BeanFactory)
,
InitDestroyAnnotationBeanPostProcessor
,
AutowiredAnnotationBeanPostProcessor
,
Serialized FormModifier and Type | Class and Description |
---|---|
protected class |
CommonAnnotationBeanPostProcessor.LookupElement
Class representing generic injection information about an annotated field
or setter method, supporting @Resource and related annotations.
|
logger
HIGHEST_PRECEDENCE, LOWEST_PRECEDENCE
Constructor and Description |
---|
CommonAnnotationBeanPostProcessor()
Create a new CommonAnnotationBeanPostProcessor,
with the init and destroy annotation types set to
PostConstruct and PreDestroy ,
respectively. |
Modifier and Type | Method and Description |
---|---|
protected Object |
autowireResource(BeanFactory factory,
CommonAnnotationBeanPostProcessor.LookupElement element,
String requestingBeanName)
Obtain a resource object for the given name and type through autowiring
based on the given factory.
|
protected Object |
buildLazyResourceProxy(CommonAnnotationBeanPostProcessor.LookupElement element,
String requestingBeanName)
Obtain a lazily resolving resource proxy for the given name and type,
delegating to
getResource(org.springframework.context.annotation.CommonAnnotationBeanPostProcessor.LookupElement, java.lang.String) on demand once a method call comes in. |
protected Object |
getResource(CommonAnnotationBeanPostProcessor.LookupElement element,
String requestingBeanName)
Obtain the resource object for the given name and type.
|
void |
ignoreResourceType(String resourceType)
Ignore the given resource type when resolving
@Resource
annotations. |
boolean |
postProcessAfterInstantiation(Object bean,
String beanName)
Perform operations after the bean has been instantiated, via a constructor or factory method,
but before Spring property population (from explicit properties or autowiring) occurs.
|
Object |
postProcessBeforeInstantiation(Class<?> beanClass,
String beanName)
Apply this BeanPostProcessor before the target bean gets instantiated.
|
void |
postProcessMergedBeanDefinition(RootBeanDefinition beanDefinition,
Class<?> beanType,
String beanName)
Post-process the given merged bean definition for the specified bean.
|
PropertyValues |
postProcessPropertyValues(PropertyValues pvs,
PropertyDescriptor[] pds,
Object bean,
String beanName)
Post-process the given property values before the factory applies them
to the given bean.
|
void |
setAlwaysUseJndiLookup(boolean alwaysUseJndiLookup)
Set whether to always use JNDI lookups equivalent to standard Java EE 5 resource
injection, even for
name attributes and default names. |
void |
setBeanFactory(BeanFactory beanFactory)
Callback that supplies the owning factory to a bean instance.
|
void |
setFallbackToDefaultTypeMatch(boolean fallbackToDefaultTypeMatch)
Set whether to allow a fallback to a type match if no explicit name has been
specified.
|
void |
setJndiFactory(BeanFactory jndiFactory)
Specify the factory for objects to be injected into
@Resource /
@WebServiceRef / @EJB annotated fields and setter methods,
for mappedName attributes that point directly into JNDI. |
void |
setResourceFactory(BeanFactory resourceFactory)
Specify the factory for objects to be injected into
@Resource /
@WebServiceRef / @EJB annotated fields and setter methods,
for name attributes and default names. |
getOrder, postProcessAfterInitialization, postProcessBeforeDestruction, postProcessBeforeInitialization, requiresDestruction, setDestroyAnnotationType, setInitAnnotationType, setOrder
clone, equals, finalize, getClass, hashCode, notify, notifyAll, toString, wait, wait, wait
postProcessAfterInitialization, postProcessBeforeInitialization
public CommonAnnotationBeanPostProcessor()
PostConstruct
and PreDestroy
,
respectively.public void ignoreResourceType(String resourceType)
@Resource
annotations.
By default, the javax.xml.ws.WebServiceContext
interface
will be ignored, since it will be resolved by the JAX-WS runtime.
resourceType
- the resource type to ignorepublic void setFallbackToDefaultTypeMatch(boolean fallbackToDefaultTypeMatch)
Default is "true". Switch this flag to "false" in order to enforce a by-name lookup in all cases, throwing an exception in case of no name match.
public void setAlwaysUseJndiLookup(boolean alwaysUseJndiLookup)
name
attributes and default names.
Default is "false": Resource names are used for Spring bean lookups in the
containing BeanFactory; only mappedName
attributes point directly
into JNDI. Switch this flag to "true" for enforcing Java EE style JNDI lookups
in any case, even for name
attributes and default names.
public void setJndiFactory(BeanFactory jndiFactory)
@Resource
/
@WebServiceRef
/ @EJB
annotated fields and setter methods,
for mappedName
attributes that point directly into JNDI.
This factory will also be used if "alwaysUseJndiLookup" is set to "true" in order
to enforce JNDI lookups even for name
attributes and default names.
The default is a SimpleJndiBeanFactory
for JNDI lookup behavior equivalent to standard Java EE 5 resource injection.
public void setResourceFactory(BeanFactory resourceFactory)
@Resource
/
@WebServiceRef
/ @EJB
annotated fields and setter methods,
for name
attributes and default names.
The default is the BeanFactory that this post-processor is defined in, if any, looking up resource names as Spring bean names. Specify the resource factory explicitly for programmatic usage of this post-processor.
Specifying Spring's SimpleJndiBeanFactory
leads to JNDI lookup behavior equivalent to standard Java EE 5 resource injection,
even for name
attributes and default names. This is the same behavior
that the "alwaysUseJndiLookup" flag enables.
setAlwaysUseJndiLookup(boolean)
public void setBeanFactory(BeanFactory beanFactory)
BeanFactoryAware
Invoked after the population of normal bean properties
but before an initialization callback such as
InitializingBean.afterPropertiesSet()
or a custom init-method.
setBeanFactory
in interface BeanFactoryAware
beanFactory
- owning BeanFactory (never null
).
The bean can immediately call methods on the factory.BeanInitializationException
public void postProcessMergedBeanDefinition(RootBeanDefinition beanDefinition, Class<?> beanType, String beanName)
MergedBeanDefinitionPostProcessor
postProcessMergedBeanDefinition
in interface MergedBeanDefinitionPostProcessor
postProcessMergedBeanDefinition
in class InitDestroyAnnotationBeanPostProcessor
beanDefinition
- the merged bean definition for the beanbeanType
- the actual type of the managed bean instancebeanName
- the name of the beanpublic Object postProcessBeforeInstantiation(Class<?> beanClass, String beanName)
InstantiationAwareBeanPostProcessor
If a non-null object is returned by this method, the bean creation process
will be short-circuited. The only further processing applied is the
BeanPostProcessor.postProcessAfterInitialization(java.lang.Object, java.lang.String)
callback from the configured
BeanPostProcessors
.
This callback will be applied to bean definitions with their bean class, as well as to factory-method definitions in which case the returned bean type will be passed in here.
Post-processors may implement the extended
SmartInstantiationAwareBeanPostProcessor
interface in order
to predict the type of the bean object that they are going to return here.
The default implementation returns null
.
postProcessBeforeInstantiation
in interface InstantiationAwareBeanPostProcessor
beanClass
- the class of the bean to be instantiatedbeanName
- the name of the beannull
to proceed with default instantiationInstantiationAwareBeanPostProcessor.postProcessAfterInstantiation(java.lang.Object, java.lang.String)
,
AbstractBeanDefinition.getBeanClass()
,
AbstractBeanDefinition.getFactoryMethodName()
public boolean postProcessAfterInstantiation(Object bean, String beanName)
InstantiationAwareBeanPostProcessor
This is the ideal callback for performing custom field injection on the given bean instance, right before Spring's autowiring kicks in.
The default implementation returns true
.
postProcessAfterInstantiation
in interface InstantiationAwareBeanPostProcessor
bean
- the bean instance created, with properties not having been set yetbeanName
- the name of the beantrue
if properties should be set on the bean; false
if property population should be skipped. Normal implementations should return true
.
Returning false
will also prevent any subsequent InstantiationAwareBeanPostProcessor
instances being invoked on this bean instance.InstantiationAwareBeanPostProcessor.postProcessBeforeInstantiation(java.lang.Class<?>, java.lang.String)
public PropertyValues postProcessPropertyValues(PropertyValues pvs, PropertyDescriptor[] pds, Object bean, String beanName)
InstantiationAwareBeanPostProcessor
Also allows for replacing the property values to apply, typically through creating a new MutablePropertyValues instance based on the original PropertyValues, adding or removing specific values.
The default implementation returns the given pvs
as-is.
postProcessPropertyValues
in interface InstantiationAwareBeanPostProcessor
pvs
- the property values that the factory is about to apply (never null
)pds
- the relevant property descriptors for the target bean (with ignored
dependency types - which the factory handles specifically - already filtered out)bean
- the bean instance created, but whose properties have not yet been setbeanName
- the name of the beannull
to skip property populationMutablePropertyValues
protected Object buildLazyResourceProxy(CommonAnnotationBeanPostProcessor.LookupElement element, @Nullable String requestingBeanName)
getResource(org.springframework.context.annotation.CommonAnnotationBeanPostProcessor.LookupElement, java.lang.String)
on demand once a method call comes in.element
- the descriptor for the annotated field/methodrequestingBeanName
- the name of the requesting beannull
)getResource(org.springframework.context.annotation.CommonAnnotationBeanPostProcessor.LookupElement, java.lang.String)
,
Lazy
protected Object getResource(CommonAnnotationBeanPostProcessor.LookupElement element, @Nullable String requestingBeanName) throws NoSuchBeanDefinitionException
element
- the descriptor for the annotated field/methodrequestingBeanName
- the name of the requesting beannull
)NoSuchBeanDefinitionException
- if no corresponding target resource foundprotected Object autowireResource(BeanFactory factory, CommonAnnotationBeanPostProcessor.LookupElement element, @Nullable String requestingBeanName) throws NoSuchBeanDefinitionException
factory
- the factory to autowire againstelement
- the descriptor for the annotated field/methodrequestingBeanName
- the name of the requesting beannull
)NoSuchBeanDefinitionException
- if no corresponding target resource found