sql >> Base de Datos >  >> RDS >> Sqlserver

Clave foránea para varias tablas

Tiene algunas opciones, todas varían en "corrección" y facilidad de uso. Como siempre, el diseño adecuado depende de sus necesidades.

  • Simplemente podría crear dos columnas en Ticket, OwnedByUserId y OwnedByGroupId, y tener claves externas anulables para cada tabla.

  • Puede crear tablas de referencia M:M que permitan las relaciones ticket:usuario y ticket:grupo. ¿Quizás en el futuro querrá permitir que un solo ticket sea propiedad de varios usuarios o grupos? Este diseño no impone que un boleto debe ser propiedad de una sola entidad.

  • Puede crear un grupo predeterminado para cada usuario y tener boletos que simplemente sean propiedad de un grupo verdadero o del grupo predeterminado de un usuario.

  • O (mi elección) modele una entidad que actúe como base tanto para Usuarios como para Grupos, y tenga boletos propiedad de esa entidad.

Aquí hay un ejemplo aproximado usando su esquema publicado:

create table dbo.PartyType
(   
    PartyTypeId tinyint primary key,
    PartyTypeName varchar(10)
)

insert into dbo.PartyType
    values(1, 'User'), (2, 'Group');


create table dbo.Party
(
    PartyId int identity(1,1) primary key,
    PartyTypeId tinyint references dbo.PartyType(PartyTypeId),
    unique (PartyId, PartyTypeId)
)

CREATE TABLE dbo.[Group]
(
    ID int primary key,
    Name varchar(50) NOT NULL,
    PartyTypeId as cast(2 as tinyint) persisted,
    foreign key (ID, PartyTypeId) references Party(PartyId, PartyTypeID)
)  

CREATE TABLE dbo.[User]
(
    ID int primary key,
    Name varchar(50) NOT NULL,
    PartyTypeId as cast(1 as tinyint) persisted,
    foreign key (ID, PartyTypeId) references Party(PartyID, PartyTypeID)
)

CREATE TABLE dbo.Ticket
(
    ID int primary key,
    [Owner] int NOT NULL references dbo.Party(PartyId),
    [Subject] varchar(50) NULL
)