This is a simplified version of the database design I have so far, for a ‘Stack Overflow’ style voting system.
The question is: if the user has a score for the total number of votes they got for a response, should that score be worked out ‘on the fly’ or should there be a field in the users table referring to their score. Also if the case is the the later, what would the recommended method be for keeping it up to date?
Users Table
-id
-name
-email
Question Table
-id
-text
-poster (user id)
Responses Table
-id
-text
-question (question id)
-poster (user id)
Votes Table
-id
-response (response id)
-voter (user id)
De-normalizing the database model so a few critical scenarios can have better performance is justified, as long as you do it in a careful and deliberate fashion.
So after you have benchmarked the realistic amount of data and determined that counting votes on the fly causes performance problems, go right ahead and cache the vote count.
Probably the most robust way to keep the cached value up-to-date is to implement a database trigger that increments the cached value whenever a row is inserted into
Votesand decrements it when a row is deleted.(NOTE: Having a
SELECT COUNT(*)...trigger can introduce subtle concurrency issues.)