Atunci când faci:
DELETE FROM `jobs` WHERE `job_id` =1 LIMIT 1
Aceasta erori:
#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))
Aici sunt mesele mele:
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`);
Simplu mod ar fi să dezactivați control cheie străină; a face modificările apoi re-permite control cheie străină.
SET FOREIGN_KEY_CHECKS=0; -- to disable them
SET FOREIGN_KEY_CHECKS=1; -- to re-enable them
Cum este, trebuie să ștergeți rând din agenții de publicitate de masă înainte de a putea șterge rând în locuri de muncă tabel care aceasta face referire. Asta:
ALTER TABLE `advertisers`
ADD CONSTRAINT `advertisers_ibfk_1` FOREIGN KEY (`advertiser_id`)
REFERENCES `jobs` (`advertiser_id`);
...este de fapt opusul a ceea ce ar trebui să fie. Așa cum este, înseamnă că ai'd trebuie să aibă o înregistrare în locuri de muncă de masă înainte de agenții de publicitate. Deci, aveți nevoie pentru a utiliza:
ALTER TABLE `jobs`
ADD CONSTRAINT `advertisers_ibfk_1` FOREIGN KEY (`advertiser_id`)
REFERENCES `advertisers` (`advertiser_id`);
Odată ce ați corecta cheie externă relația ta delete va lucra.
Sub actuale (eventual eronate) de proiectare, trebuie să ștergeți rând din agenții de publicitate de masă înainte puteți șterge rând în locuri de muncă tabel care aceasta face referire.
Alternativ, ai putea configura cheie externă astfel încât să o ștergeți din tabela părinte cauze rânduri în copil tabele pentru a fi șterse în mod automat. Aceasta se numește o cascadă șterge. Arata ceva de genul asta:
ALTER TABLE `advertisers`
ADD CONSTRAINT `advertisers_ibfk_1`
FOREIGN KEY (`advertiser_id`) REFERENCES `jobs` (`advertiser_id`)
ON DELETE CASCADE;
Având în a spus că, așa cum alții au subliniat deja, dvs. cheie externă simte ca și cum ar trebui să meargă pe o altă cale în jurul valorii de la agenții de publicitate de masă într-adevăr conține cheia primară și locuri de muncă tabel conține cheia externă. Mi-ar rescrie astfel:
ALTER TABLE `jobs`
ADD FOREIGN KEY (`advertiser_id`) REFERENCES `advertisers` (`advertiser_id`);
Și în cascadă a șterge câștigat't fi necesar.
Dacă există mai mult de un loc de muncă având aceeași advertiser_id, apoi cheie externă trebuie să fie:
ALTER TABLE `jobs`
ADD CONSTRAINT `advertisers_ibfk_1`
FOREIGN KEY (`advertiser_id`)
REFERENCES `advertisers` (`advertiser_id`);
În caz contrar (daca este invers în cazul tău), dacă doriți rânduri în publicitate să fie șterse automat dacă la rând în slujba este șters adauga 'PE ȘTERGERE în CASCADĂ' opțiune la sfârșitul cheie externă:
ALTER TABLE `advertisers`
ADD CONSTRAINT `advertisers_ibfk_1`
FOREIGN KEY (`advertiser_id`)
REFERENCES `jobs` (`advertiser_id`)
ON DELETE CASCADE;
Check out constrângeri Cheie Străină
Am avut această problemă în laravel migrației prea
în scopul de a drop mese în jos() metoda contează
Schema::dropIfExists('groups');
Schema::dropIfExists('contact');
poate să nu funcționeze, dar dacă vă schimbați ordinea, funcționează.
Schema::dropIfExists('contact');
Schema::dropIfExists('groups');
Atunci când creați baza de date sau crea tabele
Ar trebui să adăugăm că linia de la partea de sus script crea baze de date sau tabel
SET @OLD_FOREIGN_KEY_CHECKS=@@FOREIGN_KEY_CHECKS, FOREIGN_KEY_CHECKS=1;
Acum doriți să ștergeți înregistrările din tabel? apoi scrie ca
SET @OLD_FOREIGN_KEY_CHECKS=@@FOREIGN_KEY_CHECKS, FOREIGN_KEY_CHECKS=1;
DELETE FROM `jobs` WHERE `job_id` =1 LIMIT 1
Mult noroc!
Cât despre această alternativă nu'am fost folosind: permite cheie externă pentru a fi NULL și apoi alegeți ON DELETE SET NULL.
Personal, eu prefer să folosesc ambele "PE ACTUALIZARE în CASCADĂ", precum "ON DELETE SET NULL" pentru a evita complicații inutile, dar pe dumneavoastră vă poate doriți o abordare diferită. De asemenea, NULL'ing externe valori-cheie din urmă poate duce la complicații ca ai castigat't știu exact ce s-a întâmplat acolo. Deci, această schimbare ar trebui să fie în strânsă legătură cu modul de aplicare funcționează codul.
Sper că acest lucru vă ajută.
dacă aveți nevoie pentru a sprijini clientul cât de curând posibil, și nu au acces la
FOREIGN_KEY_CHECKS
așa că integritatea datelor poate fi dezactivat:
ALTER TABLE `advertisers`
DROP FOREIGN KEY `advertisers_ibfk_1`;
activați ștergerea de funcționare cu ajutorul sql sau api
se adaugă cheie externă înapoi la schemă
ALTER TABLE `advertisers`
ADD CONSTRAINT `advertisers_ibfk_1` FOREIGN KEY (`advertiser_id`) REFERENCES `jobs` (`advertiser_id`);
cu toate acestea, este un hot-fix, astfel încât acesta este pe propriul risc, pentru că principalul defect al acestor abordări este că este nevoie de aceea de a păstra integritatea datelor manual.
Am încercat soluția menționat de @Alino Manzi, dar nu't de lucru pentru mine pe WordPress legate de tabele folosind wpdb.
apoi am modificat codul de mai jos si a mers
SET FOREIGN_KEY_CHECKS=OFF; //disabling foreign key
//run the queries which are giving foreign key errors
SET FOREIGN_KEY_CHECKS=ON; // enabling foreign key
Ai putea crea un declanșator pentru a șterge referire rânduri înainte de ștergerea de muncă.
DELIMITER $$
CREATE TRIGGER before_jobs_delete
BEFORE DELETE ON jobs
FOR EACH ROW
BEGIN
delete from advertisers where advertiser_id=OLD.advertiser_id;
END$$
DELIMITER ;
Principala problemă cu acest erorr Cod de Eroare: 1451. Nu poate șterge sau actualiza un părinte rând: o restricție de cheie externă nu
e care nu't să știi care tabel conține FK eșec, astfel încât este dificil de a rezolva conflictul.
Dacă utilizați MySQL sau similare, am aflat că puteți crea o diagramă ER](https://dataedo.com/kb/tools/mysql-workbench/create-database-diagram) pentru baza de date, atunci aveți posibilitatea de a revizui și în condiții de siguranță a elimina orice conflicte declanșarea eroare.