[jsr-314-open] getting behind CDI

Dan Allen dan.j.allen at gmail.com
Wed Dec 23 14:38:16 EST 2009


On Wed, Dec 23, 2009 at 10:24 AM, Cay Horstmann <cay at horstmann.com> wrote:

> On 12/19/2009 08:25 AM, Dan Allen wrote:
>
>> If the developer wants to target a native Java EE technology stack, we
>> should consider recommending platform managed beans
>> (@javax.annotation.ManagedBean) with CDI services. If the developer's
>> scope is broader, then we could suggest for them to consider alternative
>> bean containers such as Spring. It's even possible to recommend the use
>> of @javax.annotation.ManagedBean with @javax.inject.Inject to have a
>> bean which is portable to both Java EE and Spring, likely the ideal
>> recommendation for setting a common ground.
>>
>> Hopefully we can all agree that it's time to look past the rudimentary
>> JSF managed bean facility. I don't think we do anyone a service by
>> showing them the @javax.faces.ManagedBean in examples because it's just
>> not going to stand up to the long-term challenges the developer is going
>> to face.
>>
>
> I am sorry to be so dense here, but how does @javax.annotation.ManagedBean
> work with JSF 2.0? I just tried out
>
> @javax.annotation.ManagedBean("user")
> public class UserBean implements Serializable { ... }
>
> The JSF EL does not pick this up, even in an EE6 container (GlassFish v3).
> This isn't really surprising. The JSR316 spec mandates that the name is
> turned into a JNDI name, but it specifies no interaction with an EL.
>
> I tried adding an empty beans.xml to check whether that would trigger a
> lookup by the CDI implementation, but it didn't, and reading the JSR 299
> spec, I don't think it should. Is there some other straightforward way of
> making @javax.annotation.ManagedBean work with the JSF EL?
>
> If not, it would seem to me that we need to use @javax.inject.Named if we
> want to avoid @javax.faces.bean.ManagedBean.
>

Shoot, I made the false assumption that the name in
@javax.annotation.ManagedBean was the EL name. On the one hand it makes some
sense that it is the JNDI name to make it consistent with how the container
treats EJBs. But on the other hand, what developers expect in all but a few
cases is that it would the EL name.

It's possible to put together an EL resolver the bridge the gap. Below is a
hacked together EL resolver that finds @javax.annotation.ManagedBean
references in the same module as the web app.

public class ManagedBeanELResolver extends ELResolver {

   public Object getValue(ELContext context, Object base, Object property) {
      if (property == null) {
         return null;
      }

      String propertyAsString = property.toString();

      if (base == null) {
         try {
            InitialContext ic = new InitialContext();
            // we assume the managed bean is in the war
            Object result = ic.lookup("java:module/" + propertyAsString);
            context.setPropertyResolved(true);
            return result;
         } catch (NamingException ex) {
         }
      }

      // delegate up the chain
      return null;
   }

   public Class<?> getType(ELContext context, Object base, Object property)
{
      return null;
   }

   public void setValue(ELContext context, Object base, Object property,
Object value) {
   }

   public boolean isReadOnly(ELContext context, Object base, Object
property) {
      return false;
   }

   public Iterator<FeatureDescriptor> getFeatureDescriptors(ELContext
context, Object base) {
      return null;
   }

   public Class<?> getCommonPropertyType(ELContext context, Object base) {
      return null;
   }
}

Register in faces-config.xml

<application>
    <el-resolver>com.acme.ManagedBeanELResolver</el-resolver>
</application>

I guess the question is, does Spring intend on use the
@javax.annotation.ManagedBean name as an EL name? If that is the case, then
it's inconsistent between Spring and the platform. If Spring doesn't,
perhaps they would consider using @javax.inject.Named (the most logical
choice at this point) and we can align on that annotation.

So, as Cay points out, we are back to @javax.inject.Named as the
recommendation (unless you want to use that hacked up EL resolver).

-Dan

-- 
Dan Allen
Senior Software Engineer, Red Hat | Author of Seam in Action
Registered Linux User #231597

http://mojavelinux.com
http://mojavelinux.com/seaminaction
http://www.google.com/profiles/dan.j.allen
-------------- next part --------------
An HTML attachment was scrubbed...
URL: http://lists.jboss.org/pipermail/jsr-314-open-mirror/attachments/20091223/9400c880/attachment.html 


More information about the jsr-314-open-mirror mailing list