tags:

views:

268

answers:

3

If I have to save an object to the database which has a relationships, do I have that dao do all the saving itself, or to delegate to other DAO's. If it should delegate to other DAOs, should that be done in the DAO itself, or in a layer above (like a service layer)? I would use an ORM for this, except that in PHP, nothing good exists yet.

+2  A: 

I think the answer depends on ownership.

If the Parent owns the Children, and there's no possibility of creating a Child without a Parent, then it should be just ParentDao and no ChildDao at all.

If you can create a Child without a Parent, you'll need a ChildDao for its CRUD operations. In that case, you could have the ParentDao own a reference to a ChildDao and defer Child CRUD operations to it.

duffymo
A: 

I agree with duffymo's answer - but am interested as to your statement

I would use an ORM for this, except that in PHP, nothing good exists yet

I've used both Doctrine and Propel and have found them both to be very capable. My personal preference is Doctrine although a significant amount of improvements have been made in Propel 1.3

Macros
I'm actually really looking forward to Doctrine 2.0, but I really need transparent persistence, which neither Doctrine < 2.0 or Propel offer.I basically need something more like Hibernate.
blockhead
A: 

I'd like to ask a follow-up question based on this part of duffymo's answer:

If you can create a Child without a Parent, you'll need a ChildDao for its CRUD operations. In that case, you could have the ParentDao own a reference to a ChildDao and defer Child CRUD operations to it.

Let's discuss a slight variation of this particular case: the Child entity cannot exist without the Parent entity, but the Child entity can also be associated to a different Parent entity.

Example (---> means associated with; a "has a" relationship):

  • User ---> Address
  • Organization ---> Address

So in our data model, we have an address table, a user table, and an organization table.

(If we used JPA, we could take advantage of the @SecondaryTable annotation, right?)

But lets say we want to have a DAO layer.

So for maximum code reuse I think I agree with duffymo's answer, so for this case: Have three DAOs: AddressDao, UserDao, and OrganizationDao, and make both UserDao and OrganizationDao delegate to AddressDao (as opposed to having only two DAOs and putting identical address table CRUD logic in both UserDao and OrganizationDao).

My Question:

What about referential integrity -- how do we handle transactions? My initial thought was to manage the transaction in the parent DAO.

However, according to some of the DAO patterns I have read, it seems that the recommendation is never to manage transactions within DAOs.

So what do we do? Does anyone have ideas for how to compose DAOs for complex Entity relationships?

Should we inject a TransactionManager into the DAO layer so that we only start a transaction if the higher layer hasn't already started one yet?

lsaenz