views:

37

answers:

2

Which is a better design approach: Having separate link/association tables for each type of data within a database or incorporating a general identity into a common link/association table?

Since this question really doesn't make sense without an example...

Suppose I have a database which contains data for authors and books (to use an example people can readily grasp and identify with). For the sake of simplicity, the tables for each look like:

Authors

Id
Name

Books

Id
AuthorId
Title
ISBN

I've decided I want to include links for these two sets of data into other systems (Amazon, Barnes & Noble, Books-A-Million, etc.). I've created tables for the LinkTypes, LinkSources, and LinkBases:

LinkTypes

Id
Name (e.g., Book, Author)

LinkSources

Id
Name (e.g., Amazon, B&N, etc.)

LinkBases

Id
LinkTypeId
LinkSourceId
UrlBase (e.g., http://www.amazon.com/book.html?id={0})

And a table for the actual links:

Links

Id
LinkTypeId
LinkSourceId
ReferenceValue (this value is substituted into the associated UrlBase to create the actual link)

Up to now, I've been thinking of creating separate tables for the links related to Authors and Books. The tables would look something like:

AuthorLinks

AuthorId
LinkId

This is probably fine for two different types of data, but what happens when I decide to expand the database to include Publishers, Discussion Groups, Genres, and any number of other types of data which I could have links available? Is this still good design (or was it good design to begin with)?

An option I'm considering is modifying the Links table to include a column for AssociationId which is not tied to a specific type of data, but would be used to establish the necessary link. This approach eliminates the separate association tables, but it could introduce a level of confusion to the design long-term.

Any thoughts on which is the better design? If I need to provide further detail, please let me know.

A: 

That looks an awful lot like an RDF store, i.e., a graph database. If it is, consider using an existing implementation. If not, rethink what relations you really want to have in your database and write your tables to capture those instead.

Donal Fellows
It's not a graph database (at least as I understand it). I'm not sure what you're suggesting I rethink here. I thought I was pretty plain about the relationships. I presented two differing designs for the relationships and asked for feedback on which was a better approach.
Ron O'Rourke
+1  A: 

I asked a similar question and got some intersting responses: http://stackoverflow.com/questions/2862918/common-one-to-many-table-for-multiple-entities

I think the best solution is to use inheritance. Create an abstract entity (I called it Item but I'm sure there's a better name) that represents an Author, Book, or anything else that could have a link. You'd end up with something like this:

Item      Author    Book       LinkBase        Link
=======   =======   =========  ==========      ========
ItemID    ItemID    ItemID     LinkBaseID      LinkBaseID
          Name      AuthorID   LinkTypeId      ItemID
                    Title      LinkSourceId    ReferenceValue
                               ReferenceValue

I don't think you need LinkSourceID on the Link table because you already have a link back to the LinkBase which contains the LinkSourceID.

One additional thought I had is that if referential integrity is important then you might want to avoid your second option because you can't maintain a foreign key on your Links table with a generic AssociationID.

BenV