adam bien's blog

Fallacy 8: It is very easy to implement everything you want in a web container 📎

I find in the past some interesting, but wrong, assumptions about Java EE and grouped them together to the "Java EE Fallacies".
I hear frequently from developers, that they are only allowed to develop servlet based webapplications, without EJBs. There are also still developers out there, who are afraid of EJBs.
They prefer to reinvent the EJB-container inside the WebContainer, instead of using it :-). The funny story is: WebContainers do not provide any support for transactions, consistency, or service contracts, so you need either a supporting framework (e.g. a DecoratingFilter, which initiates transactions and put the context into the current thread, which is accessible in the whole synchronous invocation), or you have to build it every time in your project.
To store a simple entity without EJBs you have to deal with multithreading (servlets are not threadsafe), and transactions. So what is simpler,
a servlet (web-only implementation):

@PersistenceContext(name="foo", unitName="myPuName")
public class MyServlet extends HttpServelet {

@Resource UserTransaction utx;

  public void doGet(HttpServletRequest req,
                    HttpServletResponse resp) throws throws ServletException, IOException {

    EntityManager em = (EntityManager) ic.lookup("java:comp/env/foo");

    //get data from request
    String name = request.getParameter("item_name");
    ...
    //create new Item entity
    Item item = new Item();
    //set values of Item entity
    item.setName(name);
    ...
    utx.begin();
    em.persist(item); //persist and add new Item to database
    utx.commit();
    ...
}
[sample taken from Sun's
blueprints]

or an EJB 3 implementation of the same logic:

@TransactionAttribute(TransactionAttributeType.REQUIRES_NEW)
public class ItemMgrBean {

    @PersistenceContext
    protected EntityManager em;

    public void storeItem(Item item){
    em.persist(item);
    }
}

In the EJB container, you do not have to care about conccurrency etc. this solves the container for you. Things become even more interesting in the ancient (:-)) J2EE world. In J2EE 1.3/1.4 web-container developers have to decorate a servlet with a filter and inject the java.sql.Connection in the current thread (using e.g. the ThreadLocal). The DAO classes, which access the database, should then reuse the connection.
Even with EJB 2.0, you do not have to do this. You only fetch a new connection from a datasource, and the container assures the consistency for you (you will receive ALWAYS the same instance from the pool). Having at least one Session Bean (as SessionFacade) gives you not only transactional behavior out off the box, but also gives you services like JSR-77 (management and monitoring), which allows you to track the performance and load of your application.
So sometimes EJBs are easier to use, understand and maintain, than a web application :-). The opposite is also true: you can easily overengineer your applications with EJBs. The truth, is as often, in the middle...