Dichiarazione di un vincolo predefinito durante la creazione di una tabella


100

Sto creando una nuova tabella in Microsoft SQL Server 2000 scrivendo il codice invece di usare la GUI, sto cercando di imparare come farlo "in modo manuale".

Questo è il codice che sto effettivamente utilizzando e funziona bene:

CREATE TABLE "attachments"
(
    "attachment_id" INT NOT NULL,
    "load_date" SMALLDATETIME NOT NULL,
    "user" VARCHAR(25) NOT NULL,
    "file_name" VARCHAR(50) NOT NULL,
    CONSTRAINT "pk_attachments" PRIMARY KEY ("attachment_id"),
    CONSTRAINT "fk_users" FOREIGN KEY ("user") REFERENCES "users" ("user"),
    CONSTRAINT "ch_load_date" CHECK ("load_date" < GETDATE())
)

Ho specificato la chiave primaria, la chiave esterna e i vincoli di controllo da soli perché in questo modo posso definire un nome per loro, altrimenti dichiararli inline farebbe generare a SQL Server un nome casuale, e non mi "piace".

Il problema è sorto quando ho provato a dichiarare il vincolo del valore di default: guardando le informazioni su internet e come le crea Microsoft SLQ Server Management Studio, ho capito che può essere creato sia inline che da solo:

"load_date" SMALLDATETIME NOT NULL DEFAULT GETDATE()

o

CONSTRAINT "df_load_date" DEFAULT GETDATE() FOR "load_date"

Il metodo inline funziona bene, ma come al solito genera un nome casuale per il constaint, il metodo stand alone genera un errore, dicendo Incorrect syntax near 'FOR'..

Inoltre, se creo la tabella e poi ALTERessa, il comando funziona:

ALTER TABLE "attachments"
ADD CONSTRAINT "df_load_date" DEFAULT GETDATE() FOR "load_date"


Come riferimento, ecco il codice completo che sto cercando di eseguire:

CREATE TABLE "attachments"
(
    "attachment_id" INT NOT NULL,
    "load_date" SMALLDATETIME NOT NULL,
    "user" VARCHAR(25) NOT NULL,
    "file_name" VARCHAR(50) NOT NULL,
    CONSTRAINT "pk_attachments" PRIMARY KEY ("attachment_id"),
    CONSTRAINT "fk_users" FOREIGN KEY ("user") REFERENCES "users" ("user"),
    CONSTRAINT "ch_load_date" CHECK ("load_date" < GETDATE()),
    CONSTRAINT "df_load_date" DEFAULT GETDATE() FOR "load_date"
)



Sono totalmente in perdita qui, quello che sto cercando di fare non è possibile o sto facendo qualcosa di sbagliato?


Modificare:

David M ha mostrato come aggiungere un vincolo predefinito con nome utilizzando la sintassi inline, sto ancora cercando di capire se la sintassi stand alone è completamente sbagliata o è colpa mia.


3
Sono d'accordo con la modifica. La risposta di David M non copre come aggiungere un vincolo tramite una dichiarazione di vincolo indipendente, ma poiché BOL non ha alcun esempio in cui è possibile nominare il vincolo predefinito tranne che tramite il modo in cui David M ha dimostrato, penso che sia sicuro assumere SQL Il server (in modo incoerente) non supporta questa sintassi.
Peter Majeed,

Risposte:


177

Fallo in linea con la creazione della colonna:

[load_date] SMALLDATETIME NOT NULL
        CONSTRAINT [df_load_date] DEFAULT GETDATE()

Ho usato le parentesi quadre anziché le virgolette poiché molti lettori non funzioneranno QUOTED_IDENTIFIERSper impostazione predefinita.


3
Grazie, questo risolve il problema del nome. Ora sto cercando di capire se questo comportamento è "by design" (cioè non è possibile farlo) o se c'è un modo per farlo. Sai, mi piace mantenere il mio codice "ordinato" e avere i vincoli dichiarati dopo le colonne rende i file SQL più chiari e facili da capire e da mettere a punto (o almeno è quello che penso).
Albireo

3
@Albireo - In base alla progettazione. table_constraintnella grammatica non includeDEFAULT
Martin Smith

2
Questa soluzione funziona solo per me quando rimuovo le virgolette intorno ai nomi dei campi e dei vincoli.
David S.

1
Per le versioni più recenti di SQL Server utilizzare [load_date] SMALLDATETIME NOT NULL CONSTRAINT [df_load_date] DEFAULT GETDATE(). Notare le parentesi quadre invece delle virgolette doppie.
deadlydog il

3
In realtà non è una cosa della versione più recente / precedente - SET QUOTED_IDENTIFIERalterna. Rivedrò la risposta, poiché preferisco comunque le parentesi quadre, avevo appena seguito lo stile della domanda dell'OP.
David M
Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.