我正在尝试为医院创建一个数据库,其中包含诸如Patient,Ward等表格。
但是,在下面执行SQL脚本时出现以下错误。
如何解决此错误?
如果存在工作人员,则删除表|错误代码:1217。无法删除或更新父行:外键约束失败
当我注释掉DROP TABLE IF EXISTS Staff时,我收到此错误:
我的SQL脚本在下面。
非常感谢。
USE test;
DROP TABLE IF EXISTS Ward;
DROP TABLE IF EXISTS PatientWard;
DROP TABLE IF EXISTS Patient;
DROP TABLE IF EXISTS NextOfKin;
DROP TABLE IF EXISTS NextOfKinTelephone;
DROP TABLE IF EXISTS Medication;
DROP TABLE IF EXISTS Prescription;
DROP TABLE IF EXISTS Staff;
DROP TABLE IF EXISTS StaffPatient;
DROP TABLE IF EXISTS Hospital;
DROP TABLE IF EXISTS HospitalTelephone;
CREATE TABLE Ward(
wardID INT(5) NOT NULL AUTO_INCREMENT,
hospitalID INT(5) default 0,
name VARCHAR(100) NOT NULL,
specialism VARCHAR(50) NOT NULL,
PRIMARY KEY(wardID),
FOREIGN KEY(hospitalID) REFERENCES Hospital(hospitalID) ON DELETE CASCADE ON UPDATE CASCADE,
INDEX name(name)
)ENGINE=InnoDB DEFAULT CHARSET=utf8;
CREATE TABLE PatientWard(
wardID INT(5) NOT NULL,
nationalInsuranceNo VARCHAR(20) default 0,
dateOfAdmission date NOT NULL,
note VARCHAR(250),
PRIMARY KEY(wardID, nationalInsuranceNo, dateOfAdmission),
FOREIGN KEY(wardID) REFERENCES Ward(wardID) ON DELETE RESTRICT ON UPDATE CASCADE,
FOREIGN KEY(nationalInsuranceNo) REFERENCES Patient(nationalInsuranceNo) ON DELETE RESTRICT ON UPDATE CASCADE
)ENGINE=InnoDB DEFAULT CHARSET=utf8;
CREATE TABLE Patient(
nationalInsuranceNo VARCHAR(20) NOT NULL AUTO_INCREMENT,
name VARCHAR(100) NOT NULL,
dateOfBirth date NOT NULL,
sex VARCHAR(20) NOT NULL,
PRIMARY KEY(nationalInsuranceNo),
INDEX name(name)
)ENGINE=InnoDB DEFAULT CHARSET=utf8;
CREATE TABLE NextOfKin(
nextOfKinID INT(5) NOT NULL AUTO_INCREMENT,
nationalInsuranceNo VARCHAR(20) default 0,
name VARCHAR(100) NOT NULL,
PRIMARY KEY(nextOfKinID),
FOREIGN KEY(nationalInsuranceNo) REFERENCES Patient(nationalInsuranceNo) ON DELETE CASCADE ON UPDATE CASCADE
)ENGINE=InnoDB DEFAULT CHARSET=utf8;
CREATE TABLE NextOfKinTelephone(
nextOfKinID INT(5) default 0,
telephoneNumber VARCHAR(14) NOT NULL,
PRIMARY KEY(nextOfKinID, telephoneNumber),
FOREIGN KEY(nextOfKinID) REFERENCES NextOfKin(nextOfKinID) ON DELETE CASCADE ON UPDATE CASCADE
)ENGINE=InnoDB DEFAULT CHARSET=utf8;
CREATE TABLE Medication(
NHS_ID INT(5) NOT NULL AUTO_INCREMENT,
hospitalID INT(5) default 0,
name VARCHAR(100) NOT NULL,
contraindications VARCHAR(200) NOT NULL,
PRIMARY KEY(NHS_ID),
FOREIGN KEY(hospitalID) REFERENCES Hospital(hospitalID) ON DELETE CASCADE ON UPDATE CASCADE,
INDEX name(name),
INDEX contraindications(contraindications)
)ENGINE=InnoDB DEFAULT CHARSET=utf8;
CREATE TABLE Prescription(
prescriptionID INT(5) NOT NULL AUTO_INCREMENT,
staffID INT(5) default 0,
NHS_ID INT(5) default 0,
nationalInsuranceNo INT(5) default 0,
startDate date NOT NULL,
dose VARCHAR(30) NOT NULL,
frequencyOfAdministration VARCHAR(100) NOT NULL,
endDate date NOT NULL,
PRIMARY KEY(prescriptionID),
FOREIGN KEY(staffID) REFERENCES Staff(staffID) ON DELETE RESTRICT ON UPDATE CASCADE,
FOREIGN KEY(NHS_ID) REFERENCES Medication(NHS_ID) ON DELETE RESTRICT ON UPDATE CASCADE,
FOREIGN KEY(nationalInsuranceNo) REFERENCES Patient(nationalInsuranceNo) ON DELETE RESTRICT ON UPDATE CASCADE,
INDEX startDate(startDate)
)ENGINE=InnoDB DEFAULT CHARSET=utf8;
CREATE TABLE Staff(
staffID INT(5) NOT NULL AUTO_INCREMENT,
hospitalID INT(5),
forename VARCHAR(50) NOT NULL,
surname VARCHAR(50) NOT NULL,
salary DECIMAL(6,2) NOT NULL,
position VARCHAR(50) NOT NULL,
PRIMARY KEY(staffID),
FOREIGN KEY(hospitalID) REFERENCES Hospital(hospitalID) ON DELETE CASCADE ON UPDATE CASCADE,
INDEX salary(salary)
)ENGINE=InnoDB DEFAULT CHARSET=utf8;
CREATE TABLE StaffPatient(
staffID INT(5) default 0,
nationalInsuranceNo INT(5) default 0,
PRIMARY KEY(staffID, nationalInsuranceNo),
FOREIGN KEY(staffID) REFERENCES Staff(staffID) ON DELETE CASCADE ON UPDATE CASCADE,
FOREIGN KEY(nationalInsuranceNo) REFERENCES Patient(nationalInsuranceNo) ON DELETE CASCADE ON UPDATE CASCADE
)ENGINE=InnoDB DEFAULT CHARSET=utf8;
CREATE TABLE Hospital(
hospitalID INT(5) NOT NULL AUTO_INCREMENT,
name VARCHAR(100) NOT NULL,
postcode VARCHAR(20) NOT NULL,
emailAddress VARCHAR(50) NOT NULL,
PRIMARY KEY(hospitalID)
)ENGINE=InnoDB DEFAULT CHARSET=utf8;
CREATE TABLE HospitalTelephone(
hospitalID INT(5) default 0,
telephoneNumber VARCHAR(14),
PRIMARY KEY(hospitalID, telephoneNumber),
FOREIGN KEY(hospitalID) REFERENCES Hospital(HospitalID) ON DELETE CASCADE ON UPDATE CASCADE
)ENGINE=InnoDB DEFAULT CHARSET=utf8;
答案 0 :(得分:1)
在删除表格之前,请先删除FK。 还要在表格后创建FK,因此您可以为其指定一个明确的名称
IF EXISTS ( SELECT * FROM SYS.foreign_keys WHERE NAME = 'FK_Ward_Hospital' AND parent_object_id = OBJECT_ID('dbo.Ward'))
ALTER TABLE dbo.Ward DROP CONSTRAINT [FK_Ward_Hospital]
DROP TABLE IF EXISTS Ward;
CREATE TABLE Ward
(
wardID INT(5) NOT NULL AUTO_INCREMENT,
hospitalID INT(5) default 0,
name VARCHAR(100) NOT NULL,
specialism VARCHAR(50) NOT NULL,
PRIMARY KEY(wardID),
INDEX name(name)
) ENGINE=InnoDB DEFAULT CHARSET=utf8;
ALTER TABLE [dbo].[Ward] WITH CHECK ADD CONSTRAINT [FK_Ward_Hospital] FOREIGN KEY([hospitalID])
REFERENCES [dbo].[Hospital] ([hospitalID])
ALTER TABLE [dbo].[Ward] CHECK CONSTRAINT [FK_Ward_Hospital]
答案 1 :(得分:0)
该错误消息告诉您由于父行存在问题而无法删除该表。 (有关“问题”的更多信息,请参见后面的内容。)父行是另一个表中的行,它引用您要删除的表中的行。例如,在StaffPatient
表中,您有FOREIGN KEY(staffID) REFERENCES Staff(staffID)
。因此,StaffPatient
中有“父行”,它们引用了Staff
中的行。
现在,对于从StaffPatient
到Staff
的外键,您已经足够小心地指定了ON DELETE CASCADE ON UPDATE CASCADE
,这意味着当您从Staff
的父行中删除行时StaffPatient
也将被删除。到目前为止,一切都很好。
但是,在Prescription
表中,您有一个与ON DELETE RESTRICT ON UPDATE CASCADE
类似的外键。 RESTRICT
关键字表示将防止删除父行。因此,最有可能发生的事情是,存在引用Staff
行的处方行,从而防止您的Staff
表被删除。
一种解决方案是先删除Prescription
表,再尝试删除Staff
表。但是,从理论上讲,有可能进入循环级联的情况,在这种情况下,如果不依靠Chris Rodriguez的答案中建议的解决方案,即删除表之前先删除所有外键,则删除几乎是不可能的。
答案 2 :(得分:0)
只在这里发布是因为我在这里找到了问题的答案:mysql drop table and cascade delete to all references to the table
我使用了这段代码,现在正在创建我的表。问题是我试图删除使用外键链接到其他表的表。因此,通过禁用然后重新启用这些外键,可以创建我的表。
SET FOREIGN_KEY_CHECKS = 0;
drop table if exists <your_1st_table>;
drop table if exists <your_2nd_table>;
SET FOREIGN_KEY_CHECKS = 1;
编辑:您应该按照创建表的相反顺序删除表,这可能会解决您的问题。