EJB 3 annotations to the max.

Until now I haven't come around using EJB3 in a real project, we already have Spring and Hibernate so I don't see the point. Of course also the whole EJB1 and EJB2 thing is still stuck in the back of my head. At QCon London I attended the EJB 3.0 session with LindaDeMichel and that looked like a good moment to see if I need to change my point of view on EJB's. As you would probably know already by now, the good things about EJB3 are that you can now test your EJB's without a running container and don't need to extend or implement obscure interfaces and classes anymore. But this blog is not about the features of EJB3, this blog is about the use of annotations, or should I say misuse....

First that comes around is: @PersistenceContext (well many came around, but it's impossible to remember all of them)

For instance you can say in an EJB:

@PersistenceContext EntityManager entityManager

So it is actually the EntityManager.... and not a PersistenceContext. Then why is it called @PersistenceContext? The javadoc of PersistenceContext says: "Expresses a dependency on an EntityManager persistence context." That doesn't shed much light does it?
Okay continue to the next annotation: @EJB. Let's say you have a class AccountService that needs a reference to the CustomerBean which happens to be an EJB. The CustomerBean is declared as follows:

@Stateless public class CustomerBean implements Customer.

Fair enough, I want it to be an EJB and when using annotations this is the way to do it. So @Stateless is for an EJB, but what is @EJB used for one might think? To answer this question let's have a look in the AccountService:

public class AccountService {
	@EJB Customer customer.
}

@EJB??? There it is! But why there? I don't care that the customer is an EJB, I just want it to be injected. Now one of the main reasons for using interfaces is gone: my AcccountServive knows implementation details about the CustomerBean, namely that it is an EJB. A more general problem with using these annotations is that my classes are now dependent on JEE to compile, since the annotations are in the JEE API and not the JSE. This is also one the points Vincent talked about when mixing annotations and POJO's.

Next annotation (or actually a property of an annotation) that makes my eyebrows frown is the mappedBy property of the @OneToMany. Have a look at this:

@Entity public class Order {
	@OneToMany(mappedBy="order")
	protected Set items = new HashSet();
}

The "mappedBy = order" feels so unnatural. At first I thought: "Of course it's mapped by Order, I am in the frickin' Order class". But then, after reading the javadoc, I came to the conclusion that this actually indicates that the order property in the Item class owns this relationship. But why do I have to declare this in the Order class? Is this relevant for the Order to know? I think not, I would say that this belongs in the Item class and in particular somewhere around the order property.

I can go on with the rest of the annotations, but I have had enough. Yes EJB3 is much better then the previous versions, but who came up with the annotations? Is it really so difficult to create sensible annotations?

Comments (1)

  1. Peter Veentjer - Reply

    April 3, 2007 at 10:52 am

    The following blogpost also is fun to read:

    http://uri.jteam.nl/?p=15

    It is about annotations making your domain objects unreadable.

Add a Comment