Reputation: 778
Initially I was importing foods from an excel document from Food Source 1 and it had VARCHAR type primary*(PK example #FOOD0001)* (Because there was only 1 source at the time I just imported directly into the foods table with auto incrementing int ID)
But I have a need to import food from another source Food Source 2 which has completely primary key type (INT) (PK example #25928747)
I currently have:
Foods table
INT
FoodId<PK>
, Name
Servings table
INT
ServingId<PK>
,FoodId<FK>
, Name, Size
What is the best database design so that any food source could be imported that won't affect the current ids or at least has a mapping so that foods can easily be updated, deleted etc? I don't want to change the ID to a VARCHAR for performance reasons
One idea I have is to introduce a FoodSourceFoodId in my foods table that has the original id from the food source, that way if a food gets changed/updated from the food source then it can easily be updated in the foods table?
Foods table
INT FoodId<PK>, *VARCHAR FoodSourceFoodId*, Name
1 #FOOD0001 Food 1
2 #FOOD0002 Food 2
3 25928747 Food 1
4 25928748 Food 2
Similarly I could do the same thing to the servings table where the serving id might relate to the serving id in the source data
Do you think this is the way to go? Or would you suggest something else?
Upvotes: 2
Views: 619
Reputation: 57023
I would recommend against modelling values from two distinct types (domains) in the same column, especially when the types in question map to distinct SQL data types.
Suggestion: use a 'subtype' table, including their respective 'natural' key, for each source and a single 'supertype' table to consolidate them using your artifical key FoodId
e.g.
CREATE TABLE Foods
(
FoodId INTEGER NOT NULL UNIQUE,
Name CHAR(6) NOT NULL
CHECK (Name IN ('Food 1', 'Food 2')),
UNIQUE (Name, FoodId)
);
CREATE TABLE Foods1
(
FoodId INTEGER NOT NULL UNIQUE,
Name CHAR(6) NOT NULL
CHECK (Name = 'Food 1'),
FOREIGN KEY (Name, FoodId)
REFERENCES Foods (Name, FoodId)
ON DELETE CASCADE
ON UPDATE CASCADE,
Food1_ID CHAR(9) NOT NULL UNIQUE
CHECK (Food1_ID LIKE '#FOOD[0-9][0-9][0-9][0-9]')
);
CREATE TABLE Foods2
(
FoodId INTEGER NOT NULL UNIQUE,
Name CHAR(6) NOT NULL
CHECK (Name = 'Food 2'),
FOREIGN KEY (Name, FoodId)
REFERENCES Foods (Name, FoodId)
ON DELETE CASCADE
ON UPDATE CASCADE,
Food2_ID INTEGER NOT NULL UNIQUE
);
Upvotes: 2
Reputation: 70523
This seems like a fine plan. Another more common option would be to make a support table with INT FoodID
as a foreign key (to the foods table) and VARCHAR ID
. Then when you no longer need to support the imports you can just toss the table.
Upvotes: 1