Let's say, I have the following tables in MS-SQL Database:
Please note: This database composition is just fictional, because I'am not allowed to share sensitive business data.
Category
- Id (int, pk)
- Name (varchar(50))
Game
- Id (int, pk)
- Name (varchar(50))
- CategoryId (int, fk: Category->Id)
- etc…
Participant
- Id (int, pk)
- Name (varchar(100))
- etc…
Composition
- Id (int, pk)
- ParticipantId (int, fk: Participant->Id)
- GameId (int, fk: Game->Id)
- Date (date)
- Time (time)
The problem is that, only one Game per Category per Participant is allowed for a given Date and Time.
So for example:
Tim can participate only in one game from one category at a time.
Valid composition:
- Tim -> Football (Ball games) -> 2017/02/02 -> 12:00
- Tim -> DOOM (Video games) -> 2017/02/02 -> 12:00
- Tim -> Football (Ball games) -> 2017/02/02 -> 13:00
- Tim -> DOOM (Video games) -> 2017/02/02 -> 13:00
Invalid composition:
- Tim -> Football (Ball games) -> 2017/02/02 -> 12:00
- Tim -> Baseball (Ball games) -> 2017/02/02 -> 12:00
My first idea was to set a unique index to Composition table ParticipantId + GameId + Date + Time, but it still allows me to add two or more games from the same Category.
Finally the question is, is it a design problem, or I just have to add a check constraint to maintain data consistency?
Best Answer
One way to enforce this is to add
CategoryID
inComposition
. Then you can add aUNIQUE
constraint on(ParticipantID, CategoryID, Date, Time)
.This requires to modify the foreign key to
Game
and to add aUNIQUE
constraint onGame
(or modify the existing one). The tables that need changes: