I’m designing a data warehouse and am struggling to work out how I should be modelling this scenario. I’ve got Users stored in a Slowly Changing Dimension Type 2 table along these lines:
| UserKey | UserID | Language | EffectiveDate | ExpiryDate | IsCurrent |
|---|---|---|---|---|---|
| 1 | 1001 | EN | 2021-01-01 | 9999-12-3 | Y |
| 2 | 1002 | EN | 2021-07-31 | 2022-01-06 | N |
| 3 | 1002 | FR | 2022-01-06 | 9999-12-31 | Y |
And a Login fact table like:
| LoginKey | UserKey | LoginTime |
|---|---|---|
| 12345 | 2 | 2021-12-25 15:00 |
| 12399 | 3 | 2022-01-31 18:00 |
Thereby allowing us to report on logins by date by user language setting at the time, etc.
Now I have to consider that each user may have one, none, or many concurrent subscriptions, which I was thinking of modelling in a Type 1 SCD thus:
| SubsKey | SubsID | SubsType | UserKey | StartDate | EndDate |
|---|---|---|---|---|---|
| 55501 | SBP501 | Premium | 2 | 2021-08-01 | 2022-08-01 |
| 55502 | SBB123 | Bonus | 3 | 2022-01-31 | 2023-01-31 |
Is it right for one dimension table to reference the surrogate row key of another like this, or should it rather contain the UserID natural key? It seems unwieldy for the Subs table to have different UserKeys for the two concurrent Subscriptions for the same user like this. Or perhaps, when the third row was added to the Type 2 User table, should all the existing rows in Subs with UserKey=2 have been updated to UserKey=3?
The whole thing doesn't seem to fit comfortably into the classic snowflake pattern, which usually has the one-to-many relationship pointing the other way, as might be the case were Language to be a separate dimension table say, with a one-to-many relation on User.
Edit
Adding a bounty to try and get some more advice on this. I'm wrestling with not only in the one-to-many example described (one user has many subscriptions) but also many-to-one relations between SCDT2 tables e.g. if the user's language was stored in a SCDT2 table, should the User dimension use reference the Language ID or the LanguageKey for Language table's current row?