Skip to content

Does JPA kill the DAO Pattern?

Oliver Gierke definitely thinks not. And I concur with him.

A couple of years ago I got into an running battle with a developer at my old workplace as to whether the JPA architecture abstracted away enough of the persistence to justify eliminating the database layer. My answer was, and still is, certainly not!

The simple answer to this question is another question – What if you wanted to replace JPA? The users of the data layer, lets call these objects the SessionLayer, need not, and should not know what sort of persistence layer you’re using. JPA does manage to abstract away some annoyances with choosing a specific transactional persistence technology just as Hibernate or Toplink. But what if you need to replace database access with a call to a web service? Convert the entire application to use Spring transactions? Send a non-transactional JMS message? Or just write the data in a flat file

If you have an entirely separate data access layer, which encapsulates your data persistence methods from its users, there’s only one place to change. It’s clients need not ever know you made that change. You have isolated the responsibility. JPA, unencapsulated, encourages users of the data layer to consider the method of persistence. Use JPA underneath your data layer.

2 Comments

  1. Gavin wrote:

    Hrm, it would be nice if that were true, but in practice, I very much doubt that a simple DAO interface is sufficient to really abstract the very different data access patterns you are using with JPA and calling a web service. Seriously … they’re just not the same thing at all…

    Plus, so far, I have never seen anyone actually try to do this (i.e. replace database access with something else) across their whole application. Everybody *talks* about doing it, but it (almost) never actually seems to happen in practice. So YAGNI applies.

    Friday, January 16, 2009 at 23:31 | Permalink
  2. Scot Mcphee wrote:

    I certainly take that as far it is. I personally have been in the situation where you’re replacing database access with service calls, in that case because we were reading some critical data straight out of a database that didn’t “belong” to the development group I was part of. We did that for speed in early iterations. Come phase 2, and we were told to replace the direct database access with calls to the “proper” service layer. The rationale being that the database we were reading out of was part of a system about to be made obsolete “in the near future” (for some value of “near”) and the “switch” would be made under the service layer.

    However if you consider a simple design – and here let’s say some sort of services layer over a database – I think it’s a really fatal mistake to pollute the services layer with of JPA or Hibernate (etc) query constructions and manipulations. The service layer’s job is to marshal the service input, ask the data layer to do it’s work, and marshal the result back to the requestor. In my view it’s never bad form to do something like this;

    public class ServiceLayer implements Service {
        public DataOut myService(DataIn in) {
            // unmarshal and check DataIn if neccessary
            someData someData = someDataLayer
             .findSomeDataUsingAStoredProcedureAlreadyInTheDB(in.getName());
            MoreData moreData = moreDataLayer
             .createMoreDataRelationshipUsingAFancyHSQLQueryOperations(in, someData);
            return new DataOut(someData, moreData);
        }
    }

    For a start, as a design, that communicates effective intention. At this level of abstraction, it isn’t really material exactly what the two data layer methods do. And when you do need to know what either methods do, you’re not forced to consider the service layer at the same time.

    Obviously, I chose method names there to reflect what might be happening “under the hood” of the data layer. Which isn’t something you’d actually do in practice. But the end result is, you’ve encapsulated the access in sensibly named methods in a convenient abstraction. I don’t see the problem.

    Saturday, January 17, 2009 at 07:53 | Permalink