sql >> Database >  >> RDS >> Sqlserver

Een externe sleutel maken in SQL Server (T-SQL-voorbeelden)

In dit artikel laat ik zien hoe je een externe sleutel in SQL Server maakt met Transact-SQL. Ik laat zien hoe je een externe sleutel maakt op het moment dat de tabel wordt gemaakt (in tegenstelling tot het bijwerken van een bestaande tabel).

Een refererende sleutel is een kolom die verwijst naar de primaire-sleutelkolom van een andere tabel. Dit creëert een relatie tussen de tabellen.

Voorbeeld 1 – Voorbereiding

In dit voorbeeld maak ik een testdatabase met één tabel. Deze tabel bevat de primaire sleutel waarnaar onze externe sleutel zal verwijzen.

Maak de database:

CREATE DATABASE FK_Test;

Maak nu de primaire sleuteltabel:

USE FK_Test;

CREATE TABLE Country
(
    CountryId int IDENTITY (1,1) NOT NULL PRIMARY KEY,
    CountryName nvarchar(60)
);

Voorbeeld 2 – Maak de externe sleutel

Nu we een tabel met een primaire sleutel hebben, gaan we een andere tabel maken met een externe sleutel die naar die primaire sleutel verwijst.

CREATE TABLE City
(
    CityId int IDENTITY (1,1) NOT NULL PRIMARY KEY,
    CountryId int NOT NULL REFERENCES Country(CountryId),
    CityName nvarchar(60)
);

Dit is de eenvoudigste manier om een ​​externe sleutel te maken. Het enige wat we doen is de REFERENCES . toevoegen clausule (samen met de primaire sleuteltabel en kolom) naar de kolom met de externe sleutelbeperking.

Voor alle duidelijkheid, het deel dat de externe sleutel definieert is dit:

REFERENCES Country(CountryId)

Dit is opgenomen in de kolomdefinitie en stelt eenvoudigweg dat deze kolom zal verwijzen naar de CountryId kolom in het Country tafel.

In dit geval hebben zowel de refererende sleutel als de primaire sleutel waarnaar deze verwijst dezelfde naam (CountryId ). Dit is echter geen vereiste – uw externe-sleutelkolom kan een geheel andere naam hebben dan de kolom waarnaar deze verwijst (hoewel alle kolommen die deelnemen aan een externe-sleutelrelatie moeten worden gedefinieerd met dezelfde lengte en schaal).

Dit voorbeeld zorgt ervoor dat SQL Server automatisch de naam van de refererende sleutel genereert. Dat komt omdat ik geen naam heb gegeven. Lees verder om te zien hoe u een naam voor uw externe sleutel kunt maken.

Maar laten we eerst eens kijken naar de beperking van de refererende sleutel die we zojuist hebben gemaakt.

Voorbeeld 3 – Controleer de Foreign Key-beperking

Er zijn veel manieren om een ​​externe sleutel te retourneren met T-SQL, en hier is er een van:

EXEC sp_fkeys @fktable_name = City;

Resultaat (met verticale uitvoer):

PKTABLE_QUALIFIER | FK_Test
PKTABLE_OWNER     | dbo
PKTABLE_NAME      | Country
PKCOLUMN_NAME     | CountryId
FKTABLE_QUALIFIER | FK_Test
FKTABLE_OWNER     | dbo
FKTABLE_NAME      | City
FKCOLUMN_NAME     | CountryId
KEY_SEQ           | 1
UPDATE_RULE       | 1
DELETE_RULE       | 1
FK_NAME           | FK__City__CountryId__38996AB5
PK_NAME           | PK__Country__10D1609FC8BFA7F2
DEFERRABILITY     | 7

De sp_fkeys systeem opgeslagen procedure retourneert informatie over onze externe sleutel, de bijbehorende primaire sleutel en andere relevante details. U geeft gewoon de naam van de refererende-sleuteltabel of de primaire-sleuteltabel door, en het zal de relevante informatie retourneren.

In dit voorbeeld geef ik de naam van de refererende sleuteltabel door - City . In de resultaten kunnen we kijken naar de FK_NAME kolom om te zien of deze tabel een externe sleutelbeperking heeft met de naam FK__City__CountryId__38996AB5 . Dit is degene die we zojuist hebben gemaakt.

Dus nu we de externe sleutel hebben gemaakt, telkens wanneer we proberen een waarde in te voegen of bij te werken in de City.CountryId kolom, staat de externe-sleutelbeperking dit alleen toe als dezelfde waarde al bestaat in de Country.CountryId kolom. Dit zorgt ervoor dat de referentiële integriteit binnen de database behouden blijft.

Voorbeeld 4 – Meer opties

Het is mogelijk om meer opties toe te voegen aan uw buitenlandse sleuteldefinitie.

U kunt bijvoorbeeld een naam voor de externe sleutel opgeven. U kunt ook specificeren wat er met de waarden in deze kolom moet gebeuren als de corresponderende waarde in de primaire sleutel wordt bijgewerkt of verwijderd.

Hier maak ik beide tabellen opnieuw, maar deze keer specificeer ik expliciet deze opties (ik doe hetzelfde voor de primaire sleutels):

CREATE TABLE Country
(
    CountryId int IDENTITY (1,1) NOT NULL,
      CONSTRAINT PK_Country_CountryId PRIMARY KEY CLUSTERED (CountryId),
    CountryName nvarchar(60)
);

CREATE TABLE City
(
    CityId int IDENTITY (1,1) NOT NULL,
      CONSTRAINT PK_City_CityId PRIMARY KEY CLUSTERED (CityId),
    CountryId int NOT NULL,
      CONSTRAINT FK_City_Country FOREIGN KEY (CountryID)
        REFERENCES Country (CountryID)
        ON DELETE CASCADE
        ON UPDATE CASCADE,
    CityName nvarchar(60)
);

In dit geval begint de definitie van de refererende sleutel met CONSTRAINT , gevolgd door de naam van de externe sleutel, gevolgd door FOREIGN KEY , gevolgd door de kolom waarop de externe-sleutelbeperking wordt toegepast (tussen haakjes ingevoegd).

We zien dan dezelfde REFERENCES clausule die we in het vorige voorbeeld zagen.

De ON DELETE CASCADE en ON UPDATE CASCADE clausules worden gebruikt om ervoor te zorgen dat wijzigingen in Country tabel worden automatisch doorgegeven aan de City tafel. Als een rij bijvoorbeeld wordt verwijderd uit de bovenliggende (primaire sleutel) tabel, worden alle bijbehorende rijen verwijderd uit de verwijzende (buitenlandse sleutel) tabel.

De standaardwaarde voor ON DELETE en ON UPDATE is NO ACTION . In dit geval genereert de database-engine een fout en wordt de update- of verwijderactie op de rij in de bovenliggende tabel teruggedraaid.

U kunt ook SET NULL . gebruiken om de externe sleutelkolom in te stellen op NULL (vereist dat de externe sleutelkolom nullable is), of SET DEFAULT om het in te stellen op de standaardwaarde (vereist dat de externe sleutelkolom een ​​standaarddefinitie heeft. Als een kolom nullable is en er geen expliciete standaardwaarde is ingesteld, NULL wordt de impliciete standaardwaarde van de kolom).

In dit voorbeeld heb ik ook van de gelegenheid gebruik gemaakt om de primaire sleutels een naam te geven. U kunt zien dat de primaire sleutelsyntaxis vergelijkbaar is met de externe sleutelsyntaxis, maar zonder de REFERENCES clausule (en met een toegevoegde CLUSTERED argument, wat de standaard is voor primaire sleutels).

Controleer nu de externe sleutel:

EXEC sp_fkeys @fktable_name = City;

Resultaat:

PKTABLE_QUALIFIER | FK_Test
PKTABLE_OWNER     | dbo
PKTABLE_NAME      | Country
PKCOLUMN_NAME     | CountryId
FKTABLE_QUALIFIER | FK_Test
FKTABLE_OWNER     | dbo
FKTABLE_NAME      | City
FKCOLUMN_NAME     | CountryId
KEY_SEQ           | 1
UPDATE_RULE       | 0
DELETE_RULE       | 0
FK_NAME           | FK_City_Country
PK_NAME           | PK_Country_CountryId
DEFERRABILITY     | 7

We kunnen zien dat de naam van de refererende sleutel nu FK_City_Country is en de primaire sleutelbeperking van de kolom waarnaar deze verwijst heet PK_Country_CountryId .

Voorbeeld 5 – Foreign key op meerdere kolommen

U kunt ook een externe sleutel maken op meerdere kolommen die verwijst naar een primaire sleutel met meerdere kolommen. Primaire sleutels met meerdere kolommen worden ook wel samengestelde primaire sleutels genoemd. Om een ​​samengestelde externe sleutel te maken, scheidt u de kolommen eenvoudig met een komma bij het definiëren van de sleutel.

Zoals dit:

CONSTRAINT FK_FKName FOREIGN KEY
 (FKColumn1, FKColumn2)
REFERENCES PrimaryKeyTable (PKColumn1, PKColumn2)

Zie Een samengestelde externe sleutel maken in SQL Server voor een gedetailleerder voorbeeld.

Is de primaire sleutel echt nodig?

Een primaire sleutel is niet absoluut noodzakelijk voor externe sleutels, omdat u een unieke beperking of unieke index kunt gebruiken. In de Microsoft-documentatie staat dit specifiek:

FOREIGN KEY beperkingen kunnen alleen verwijzen naar kolommen in PRIMARY KEY of UNIQUE beperkingen in de tabel waarnaar wordt verwezen of in een UNIQUE INDEX op de tabel waarnaar wordt verwezen.

Dus hoewel het meestal een goede gewoonte is om primaire sleutels op alle tabellen te hebben, zijn uw externe sleutels niet verplicht om ernaar te verwijzen.


  1. Hoe taalinstellingen uw FORMAT()-resultaten in SQL Server kunnen beïnvloeden (T-SQL-voorbeelden)

  2. ORA-27154 / ORA-27146

  3. Hoe bekijk ik de volledige inhoud van een tekst- of varchar(MAX)-kolom in SQL Server 2008 Management Studio?

  4. Vind index van het laatste voorkomen van een subtekenreeks met behulp van T-SQL