Yaparken:
DELETE FROM `jobs` WHERE `job_id` =1 LIMIT 1
Hata veriyor:
#1451 - Cannot delete or update a parent row: a foreign key constraint fails
(paymesomething.advertisers, CONSTRAINT advertisers_ibfk_1 FOREIGN KEY
(advertiser_id) REFERENCES jobs (advertiser_id))
İşte masalarım:
CREATE TABLE IF NOT EXISTS `advertisers` (
`advertiser_id` int(11) unsigned NOT NULL AUTO_INCREMENT,
`name` varchar(255) NOT NULL,
`password` char(32) NOT NULL,
`email` varchar(128) NOT NULL,
`address` varchar(255) NOT NULL,
`phone` varchar(255) NOT NULL,
`fax` varchar(255) NOT NULL,
`session_token` char(30) NOT NULL,
PRIMARY KEY (`advertiser_id`),
UNIQUE KEY `email` (`email`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8 AUTO_INCREMENT=2 ;
INSERT INTO `advertisers` (`advertiser_id`, `name`, `password`, `email`, `address`, `phone`, `fax`, `session_token`) VALUES
(1, 'TEST COMPANY', '', '', '', '', '', '');
CREATE TABLE IF NOT EXISTS `jobs` (
`job_id` int(11) unsigned NOT NULL AUTO_INCREMENT,
`advertiser_id` int(11) unsigned NOT NULL,
`name` varchar(255) NOT NULL,
`shortdesc` varchar(255) NOT NULL,
`longdesc` text NOT NULL,
`address` varchar(255) NOT NULL,
`time_added` int(11) NOT NULL,
`active` tinyint(1) NOT NULL,
`moderated` tinyint(1) NOT NULL,
PRIMARY KEY (`job_id`),
KEY `advertiser_id` (`advertiser_id`,`active`,`moderated`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8 AUTO_INCREMENT=2 ;
INSERT INTO `jobs` (`job_id`, `advertiser_id`, `name`, `shortdesc`, `longdesc`, `address`, `active`, `moderated`) VALUES
(1, 1, 'TEST', 'TESTTEST', 'TESTTESTES', '', 0, 0);
ALTER TABLE `advertisers`
ADD CONSTRAINT `advertisers_ibfk_1` FOREIGN KEY (`advertiser_id`) REFERENCES `jobs` (`advertiser_id`);
Bu haliyle, başvurduğu işler tablosundaki satırı silmeden önce satırı reklamverenler tablosundan silmeniz gerekir. Bu şekilde:
ALTER TABLE `advertisers`
ADD CONSTRAINT `advertisers_ibfk_1` FOREIGN KEY (`advertiser_id`)
REFERENCES `jobs` (`advertiser_id`);
...aslında olması gerekenin tam tersidir. Bu haliyle, reklamverenlerden önce işler tablosunda bir kaydın olması gerektiği anlamına gelir. Bu yüzden kullanmanız gerekir:
ALTER TABLE `jobs`
ADD CONSTRAINT `advertisers_ibfk_1` FOREIGN KEY (`advertiser_id`)
REFERENCES `advertisers` (`advertiser_id`);
Yabancı anahtar ilişkisini düzelttiğinizde, silme deyiminiz çalışacaktır.
Mevcut (muhtemelen kusurlu) tasarımınıza göre, başvurduğu işler tablosundaki satırı silebilmeniz için önce reklamverenler tablosundan satırı silmeniz gerekir.
Alternatif olarak, yabancı anahtarınızı, üst tablodaki bir silme işleminin alt tablolardaki satırların otomatik olarak silinmesine neden olacak şekilde ayarlayabilirsiniz. Buna basamaklı silme denir. Şöyle bir şey gibi görünür:
ALTER TABLE `advertisers`
ADD CONSTRAINT `advertisers_ibfk_1`
FOREIGN KEY (`advertiser_id`) REFERENCES `jobs` (`advertiser_id`)
ON DELETE CASCADE;
Bununla birlikte, diğerlerinin de belirttiği gibi, reklamverenler tablosu gerçekten birincil anahtarı içerdiğinden ve işler tablosu yabancı anahtarı içerdiğinden, yabancı anahtarınız diğer tarafa gitmeli gibi görünüyor. Ben olsam şu şekilde yeniden yazardım:
ALTER TABLE `jobs`
ADD FOREIGN KEY (`advertiser_id`) REFERENCES `advertisers` (`advertiser_id`);
Ve basamaklı silme gerekli olmayacaktır.
Aynı advertiser_id'ye sahip birden fazla iş varsa, yabancı anahtarınız şu şekilde olmalıdır:
ALTER TABLE `jobs`
ADD CONSTRAINT `advertisers_ibfk_1`
FOREIGN KEY (`advertiser_id`)
REFERENCES `advertisers` (`advertiser_id`);
Aksi takdirde (sizin durumunuzda tam tersi ise), job'taki satır silindiğinde advertiser'daki satırların otomatik olarak silinmesini istiyorsanız yabancı anahtarınızın sonuna 'ON DELETE CASCADE' seçeneğini ekleyin:
ALTER TABLE `advertisers`
ADD CONSTRAINT `advertisers_ibfk_1`
FOREIGN KEY (`advertiser_id`)
REFERENCES `jobs` (`advertiser_id`)
ON DELETE CASCADE;
Yabancı Anahtar kısıtlamalarına göz atın]1