]
Sven Linstaedt updated CDI-493:
-------------------------------
Summary: Allow firing of parameterized event types from BeanManager (was: Allow
firing of generic events from BeanManager)
Allow firing of parameterized event types from BeanManager
----------------------------------------------------------
Key: CDI-493
URL:
https://issues.jboss.org/browse/CDI-493
Project: CDI Specification Issues
Issue Type: Feature Request
Components: Events
Affects Versions: 1.2.Final
Reporter: Sven Linstaedt
Currently we are allowed firing generic events from
{{javax.enterprise.event.Event<X>#fire}} as long as it's type parameter X does
not contain a TypeVariable.
When it comes to {{javax.enterprise.inject.spi.BeanManager#fireEvent}} and
{{javax.enterprise.inject.spi.BeanManager#resolveObserverMethods}} this is unfortunately
not possible due to type erasure. Because we lack the relevant generic information that
are otherwise explicit stated via {{Event#select}}, we are not able to fire a generic
event from {{BeanManager#fireEvent}}.
This proposal is about enhancing the API of BeanManager in order to supply the relevant
type information, that are otherwise discarded by type erasure. A possible solution would
look like adding two new methods to BeanManager
{code}
BeanManager#fireEvent(Type, Object, Annotation...)
BeanManager#resolveObserverMethods(Type, T, Annotation...)
{code}
which receive the selected event type as 1st parameter, validate that the actual event
instance (2nd parameter) is assignable to the selected event type (the selected event type
has to resolve all type variables; throwing an IllegalArgumentException otherwise) and
fires the event afterwards.
The original two methods can delegate their calls to the new ones, having
{{java.lang.Object}} as event type.
Additionally {{javax.enterprise.inject.spi.EventMetadata#getType()}} will return the
resolved parameterized type.
With this proposal it would be possible to provide meta-extensions, that enable other
extension to handle custom extension lifecycle events like
{code}
<X> void on(@Observes @BoundWith(InterceptorBinding.class)
ProcessBoundedType<X> pbt) {
if (pbt.getBoundedType().isAnnotationPresent(Interceptor.class)) {
// register interceptor type
} else {
// register intercepted type
}
}
{code}