MySQL: Tablo oluşturulamıyor (errno: 150)


156

Bir .sql dosyası ve onun tablolar oluşturma başarısız almaya çalışıyorum.

Başarısız olan sorgu:

CREATE TABLE `data` (
`id` int(10) unsigned NOT NULL,
`name` varchar(100) NOT NULL,
`value` varchar(15) NOT NULL,
UNIQUE KEY `id` (`id`,`name`),
CONSTRAINT `data_ibfk_1` FOREIGN KEY (`id`) REFERENCES `keywords` (`id`) ON DELETE CASCADE ON UPDATE CASCADE
) ENGINE=InnoDB DEFAULT CHARSET=latin1;    

Ben aynı veritabanından .sql ihraç, ben tüm tabloları düştü ve şimdi im almaya çalışıyorum, neden başarısız?

MySQL: './dbname/data.frm' tablosu oluşturulamıyor (errno: 150)


1
Esasen bu hatanın tüm nedenleri için, burada MySQL'de errno 150'ye (ve errno 121 / diğer yabancı anahtar hatalarına) neyin sebep olduğu konusunda kapsamlı bir kaynak bulunmaktadır.
John Smith

21
Ben sütunlar aynı olması gerektiğini buldum (imzalanmamış bayrak bile eşleşmelidir).
Justin Skiles

3
@JohnSmith ... nerede?
Charles Wood

3
10 olası nedeni listeleyen bu blog gönderisini okumanızı öneririm: verysimple.com/2006/10/22/…
Mark Amery

@CharlesWood: " John Smith ... 6 Nisan 2013'te 19:29'da görüldü ", bu da yorumunuzdan yaklaşık üç ay önce. Korkarım, bu kirli dünyanın sonuna kadar bir "nerede" gizemi ortaya çıkmayacak! :>
trejder

Yanıtlar:


167

Gönderen MySQL - YABANCI ANAHTAR Kısıtlamaları Belgeleri :

Bırakılan bir tabloyu yeniden oluşturursanız, tabloya başvuran yabancı anahtar kısıtlamalarına uyan bir tanım olmalıdır. Doğru sütun adlarına ve türlerine sahip olmalı ve daha önce belirtildiği gibi başvurulan anahtarlarda dizinlere sahip olmalıdır. Bunlar karşılanmazsa, MySQL Hata 1005'i döndürür ve hata iletisinde Hata 150'ye başvurur, bu da bir yabancı anahtar kısıtlamasının doğru şekilde oluşturulmadığı anlamına gelir. Benzer şekilde, ALTER TABLE Hata 150 nedeniyle başarısız olursa, değiştirilen tablo için yabancı anahtar tanımının yanlış oluşturulacağı anlamına gelir.


1
Bir tablodaki iki sütun, PK olan başka bir tablodaki bir sütuna başvurabilir mi?
Eugene

1
@Eugene: İki sütunun her birinin başka bir tabloda PK ile yabancı anahtar ilişkisi olabilir - her iki sütun da tek bir yabancı anahtar ilişkisi olarak değil.
OMG Ponies

1
@OMGPonies: Bu soruya cevap verdiğiniz için teşekkürler! .. Aradım ... Burada da bir soru sordum stackoverflow.com/questions/13487010/… .... Bazı iyi yanıtlarım olmasına rağmen ben uyum sağlamak istiyorum Whether its possible to write Nested Query for my problem? .. Sizden de bana cevap vermenizi rica ediyorum!
Grijesh Chauhan

19
Benim hatam master tablo MyISAM ve çocuk tablo InnoDB motoru vardı. Şu anki create.sql betiği tüm tablolar için InnoDB kullanıyordu, ancak ilk betiğin MyISAM kullandığı çok eski bir kurulumum vardı.
Whome

2
@Whome - Yep, burada da aynı sorunla karşılaştı.
2013'te

96

Hata 150, yabancı anahtarınızla ilgili bir sorununuz olduğu anlamına gelir. Muhtemelen yabancı masanın anahtarı tam olarak aynı tipte değil mi?


15
Teşekkürler :) benim için veri türleri INT ama biri imzasız iken diğeri değil
Anh Nguyen

6
Şema üreteçlerini kullanırken çoğunlukla BIGINTvs ile INTkarşılaşıyorum.
Xeoncross

Yabancı anahtar INT değeri olmadığında da aynı sorunla karşılaştım. Yabancı anahtar söz konusu olduğunda sütun EŞSİZ olmalıdır.
PhatHV

62

Gerçek hata mesajını çalıştırarak SHOW ENGINE INNODB STATUS;ve sonra LATEST FOREIGN KEY ERRORçıkışta arayarak alabilirsiniz .

Kaynak: benzer bir soruda başka bir kullanıcının cevabı


7
Bu aslında çok faydalı. Kesin hatayı söyler.
Csongor Fagyal

Teşekkürler. MySQL Workbench bunu kullanmamak utanç verici.
scipilot

Muhteşem. Bu çok yardımcı oldu. Kesin hatayı söyler. Benimki, Sütun NULLABLE yaptık ama "delete set null" ayarlamıştı. Çok teşekkür ederim.
Abhishek Saini

Sunucunuzda ayrıcalıklarınız varsa :(
Christopher Smit

30

Veri türleri tam olarak eşleşmelidir. Varchar türleri ile uğraşıyorsanız, tablolar aynı harmanlamayı kullanmalıdır.


4
Harmanlama biti için teşekkürler.
arahant

25

Bence bütün bu cevaplar doğruyken soruya yanıltıcı.

Gerçek cevap, geri yüklemeye başlamadan önce, yabancı anahtarlarla bir döküm dosyasını geri yüklüyorsanız:

SET FOREIGN_KEY_CHECKS=0;

çünkü doğal olarak geri yükleme, yabancı tablo bile var olmadan önce bazı kısıtlamalar yaratacaktır.


Bunu yapmak benim için işe yaramadı, yine de hata veriyor. Herhangi bir fikir?
Joseph Astrahan

24

Bazı durumlarda, ilişkili tablolar arasında farklı motorlar varsa bu hata iletisiyle karşılaşabilirsiniz. Örneğin, bir tablo InnoDB kullanıyor, diğeri MyISAM kullanıyor olabilir. Her ikisinin de aynı olması gerekir


Teşekkürler - bu benim sorunumdu.
scipilot

Benim sorunum buydu. Teşekkürler
thed0ctor

Bu, mysqldump kullanarak innodb tablosunun bir sql dosyasını oluşturduysanız ve bunun yerine myisam talbes olarak dışa aktarıldıysa gerçekleşebilir.
Amado Martinez

11

Hata no. 150, yabancı anahtar kısıtlama hatası anlamına gelir. Muhtemelen bu tabloyu yabancı anahtarın bağlı olduğu tablodan önce oluşturuyorsunuz (tablo keywords). Önce bu tabloyu oluşturun ve iyi çalışmalıdır.

Değilse, yabancı anahtar deyimini kaldırın ve tablo oluşturulduktan sonra ekleyin - belirli kısıtlama hatası hakkında daha anlamlı bir hata iletisi alırsınız.


10

Errno 150'ye neden olabilecek birkaç şey var, bu yüzden bu konuyu arayan insanlar için, kapsamlı listeye yakın olduğunu düşünüyorum (Errno 150'nin kaynak nedenleri ):

Errno 150 veya errno 121 için, sadece SHOW ENGINE INNODB STATUS yazarak, "SON YABANCI ANAHTAR HATASI" adlı bir bölüm vardır. Bunun altında, size sorunun ne olduğunu hemen söyleyecek olan çok yararlı bir hata mesajı verecektir. Çalıştırmak için SÜPER ayrıcalıklara ihtiyacınız vardır, bu nedenle sahip değilseniz, aşağıdaki senaryoları test etmeniz yeterlidir.

1) Veri Türleri Eşleşmiyor: Sütun türlerinin aynı olması gerekir

2) Dizine Eklenmemiş (veya Yanlış Sırala Dizine Eklenmemiş) Üst Sütunlar

3) Sütun Harmanları Eşleşmiyor

4) SET NULL DEĞİL, NULL DEĞİL sütununda kullanma

5) Tablo Harmanlamaları Eşleşmiyor: sütun harmanlamaları eşleşse bile, bazı MySQL sürümlerinde bu bir sorun olabilir.

6) Üst Sütun Ana Tabloda Gerçekte Mevcut Değil. Yazımı denetleme (ve belki de sütunun başında veya sonunda bir boşluk)

7) Sütunlardan birindeki dizinlerden biri eksik veya sütun tam bir dizin için çok uzun. MySQL'in (ayarlamadığınız sürece) maksimum tek sütun anahtar uzunluğu 767 bayt olduğunu unutmayın (bu bir varchar (255) UTF sütununa karşılık gelir)

Bir errno 121 almanız durumunda, birkaç neden var:

1) Seçtiğiniz kısıtlama adı zaten alınmış

2) Bazı sistemlerde ifadenizde ve tablo adlarınızda büyük / küçük harf farkı varsa. Bu, bir sunucudan diğerine farklı vaka yönetimi kurallarına sahip bir şekilde giderseniz sizi ısıtabilir.


Bazı sürümlerde, tablo innodb değilse, errno 150 alırsınız, ancak bazı sürümlerde sessizce başarısız olur.
juacala

Teşekkürler, bu harikaydı: | ------------------------ | SON YABANCI ANAHTAR HATASI | ------------------------ | Bazı SET olsa NULL koşul tanımladınız. sütunlar NOT NULL olarak tanımlanır.
Sam Critchley

8

Bazen MySQL sadece süper aptal - yabancı anahtarların nedenini anlayabiliyorum .. ama benim durumumda, sadece tüm veritabanını düşürdüm ve hala hatayı alıyorum ... neden? yani, artık hiçbir veritabanı yok ... ve kullanıyorum sql-kullanıcı sunucu üzerinde herhangi bir diğer db's erişimi yok ... yani, sunucu geçerli kullanıcı için "boş" ve hala olsun bu hata? Üzgünüm ama sanırım MySQL bana yalan söylüyor ... ama onunla başa çıkabilirim :) Sadece bu iki SQL satırı sizin cehennem ifadesi etrafında ekleyin:

SET FOREIGN_KEY_CHECKS = 0;
# some code that gives you errno: 150
SET FOREIGN_KEY_CHECKS = 1;

Şimdi sql yürütülmesi gerekir ... Eğer gerçekten bir yabancı anahtar sorun varsa, tekrar kontrolleri etkinleştirmek hattı tarafından size gösterilir - bu başarısız olur o zaman .. ama sunucum sadece sessiz :)


Sütun ve başvurduğu sütun arasında gerçekte farklılıklar varsa, bu sorunlara neden olabilir. Örneğin. Başvurulan sütunun bir varchar (200) ve yönlendirenin varchar (50) olduğunu varsayalım, o zaman bir kaskat denendiğinde garip davranışlar ortaya çıkabilir. Veri uyuşmazlığı nedeniyle errno 150'nin yayınlandığı bir sorunla karşılaşmadım.
juacala

İlginç bilgiler @juacala :) Benim için komik sadece, ne zaman bu ben koştum, benim yaklaşım her zaman düzeltildi ... bugüne kadar en azından: D Ama biz asla öğrenme durdurmak, doğru;)
jebbie

Bu aslında bir senaryo sıvısı oluşturmama yardımcı oldu. Komut dosyası MySQL> 5.5 üzerinde kusursuz bir şekilde çalıştı, ancak 5.1 sürümü için başarısız oldu.
delbertooo

4

Yukarıdaki cevapları inceledikten ve biraz denedikten sonra, MySQL'de Yabancı Anahtar hatalarını çözmenin etkili bir yoludur (1005 - 150 hatası).

Yabancı anahtarın düzgün bir şekilde oluşturulması için tüm MySQL sorar:

  • Başvurulan tüm anahtarlar PRIMARY veya UNIQUE dizinine sahip olmalıdır.
  • Referans Sütunu tekrar Referans sütununa aynı veri tipine sahip olmalıdır ZORUNLU.

Bu gereksinimleri karşılayın ve her şey iyi olacak.


4

Windows uygulamasını Linux'a taşıdığımda bu hatayla karşılaştım. Windows'da, veritabanı tablosu adları büyük / küçük harfe duyarlı değildir ve Linux'ta büyük olasılıkla dosya sistemi farkı nedeniyle büyük / küçük harfe duyarlıdır. Yani Windows masada Table1aynıdır table1ve içinde REFERENCEShem table1ve Table1eserleri. Linux'ta, veritabanı yapısı oluştururken table1yerine uygulama kullanıldığında Table1# 150 hatası gördüm; Table1referanslarda doğru karakter durumunu yaptığımda Linux üzerinde de çalışmaya başladı. Yani, başka bir şey yardımcı olmazsa REFERENCES, Linux'ta tablo adında doğru karakter durumunu kullandığınızdan emin olun .


Bu da benim durumumdu! Komut dosyasını büyük / küçük harfe duyarlı olmayan bir bilgisayardan (OS X) büyük / küçük harfe duyarlı mysql sürümüne (Debian) taşıma.
mircealungu

3

Masalarınızın motorlarını değiştirin, sadece innoDB yabancı anahtarları destekler


3

PK tablo bir CHARSET içinde oluşturulan ve sonra başka bir CHARSET içinde FK tablo oluşturmak ... sonra da bu hatayı alabilirsiniz ... Ben de bu hatayı aldım ama karakter char PK değiştirdikten sonra hata olmadan yürütüldü

create table users
(
------------
-------------
)DEFAULT CHARSET=latin1;


create table Emp
(
---------
---------
---------
FOREIGN KEY (userid) REFERENCES users(id) on update cascade on delete cascade)ENGINE=InnoDB, DEFAULT CHARSET=latin1;

3

Bu hata, iki tablonun bir referansı varsa, örneğin bir tablonun Öğrenci ve başka bir tablonun Eğitim olması ve Eğitim tablosunun Öğrenci tablosunun yabancı anahtar başvurusunun olmasını istiyorsanız oluşabilir. Bu örnekte, her iki tablo için sütun veri türü aynı olmalıdır, aksi takdirde bir hata oluşturur.


3

Çoğu durumda sorun, MOTOR farklılığından kaynaklanmaktadır .Eğer ebeveyn InnoDB tarafından oluşturulduysa, MyISAM tarafından oluşturulması gereken referans tablolar ve bunun tersi


3

Benim durumumda. Hosting sunucum ayarları değiştirdi ve yeni tablolarım MyISAM, ancak eski tablolarım InnoDB olduğu için motor ve karakter takımı ile ilgili sorunlar yaşadım. Sadece değiştim.


Bu benim için doğruydu, çünkü benim tarafımdan yapılmayan bir veritabanını değiştiriyordum.
FonzTech

3

genellikle, yabancı anahtar ve birincil anahtar arasındaki uyumsuzluk şu hataya neden olur: 150.

Yabancı anahtar aynı olmalıdır veri türü olarak birincil anahtar . Ayrıca, birincil anahtar imzasız ise , yabancı anahtar da imzasız olmalıdır .


3

Ben de aynı sorunu yaşadım. Tablonun Harmanlama ve Karakter Kümesi sütunuyla ilgiliydi . İki tabloda bulunan her iki sütun için de Karakter Kümesi ve Harmanlama'nın aynı olduğundan emin olun . Bunun üzerine yabancı bir anahtar ayarlamak istiyorsanız. Örnek- userImage tablosunun userID sütununa user tablosunun userID sütununa başvuran yabancı anahtar koyarsanız, Harmanlama , her iki sütun için de utf8_general_ci ve Character set utf8 ile aynı olmalıdır . Genellikle bir tablo oluşturduğunuzda mysql bu iki yapılandırmayı sunucu ayarlarından alır.


Neden daha önce bu şiiri görmedim !? Temel nedeni bulmak için bir saat geçirdim. Benim durumumda karakter oldu. Referans verilen ve referans veren tablolar aynı karakter kümesine sahip olmalıdır.
Sujit Joshi

2

Lütfen hem birincil anahtar sütununuzun hem de başvurulan sütununuzun aynı veri türlerine ve özelliklerine (işaretsiz, ikili, işaretsiz sıfır doldurma vb.) Sahip olduğundan emin olun.


2

Gerçek bir uç durum, bir veritabanını yeniden adlandırmak için MySQL aracını (benim durumumda Sequel Pro) kullandığınız yerdir. Daha sonra aynı ada sahip bir veritabanı yarattı.

Bu, aynı anahtar adına yabancı anahtar kısıtlamaları getirdi, bu nedenle yeniden adlandırılan veritabanının (ör. My_db_renamed) yeni oluşturulan veritabanında (my_db) yabancı anahtar kısıtlamaları vardı

Bunun Sequel Pro'da bir hata olup olmadığından veya bazı kullanım durumlarının bu davranışı gerektirip gerektirmediğinden emin değilim, ancak bir sabahın en iyi parçası bana mal oldu: /


2

Aynı hatayla karşılaştım. Benim durumumda hatanın nedeni, tanımında kısıtlamayı koyduğum alanın NOT NULL ifadesi varken kısıtlamada bir ON DELETE SET NULL deyimi olmasıydı. Alanda NULL değerine izin vermek sorunu çözdü.


2

Textfile DB oluştururken bu tür bir sorunla karşı karşıya kaldım.

mysql -uroot -padmin < E:\important\sampdb\createdb.sql
mysql -uroot -padmin sampdb < E:\important\sampdb\create_student.sql
mysql -uroot -padmin sampdb < E:\important\sampdb\create_absence.sql

mysql -uroot -padmin sampdb < E:\important\sampdb\insert_student.sql
mysql -uroot -padmin sampdb < E:\important\sampdb\insert_absence.sql

mysql -uroot -padmin sampdb < E:\important\sampdb\load_student.sql
mysql -uroot -padmin sampdb < E:\important\sampdb\load_absence.sql 

Sadece yukarıdaki satırları yazdım Create.batve yarasa dosyasını çalıştırdım.

Benim hatam sql dosyalarım yürütme sırası sırasına göre. Birincil anahtar ve ayrıca yabancı anahtar ile tablo oluşturmaya çalıştım. Çalışırken referans tablosunu arayacaktır, ancak tablolar orada değildir. Yani bu tür bir hata verecektir.

Yabancı anahtar içeren tablolar oluşturuyorsanız, referans tabloların mevcut olup olmadığını kontrol edin. Ayrıca referans tablolarının ve alanlarının adını da kontrol edin.


Başka bir deyişle, henüz bulunmayan başka bir tabloya işaret eden yabancı anahtarlı bir tablo oluşturmaya çalıştınız. Sorunu çözmek için tabloları doğru sırayla oluşturun.
Vincent

2

Ben benzer bir sorun vardı ama benim veri vardı mevcut bir tabloya yeni bir alan ekliyordu ve yeni alan üst tablodan başka bir alan atıfta oldu ve ayrıca NOT NULL ve herhangi bir varsayılan değer olmadan tanımlaması vardı. - İşlerin çalışmamasının nedenini öğrendim çünkü

  1. Yeni alanımın, kısıtlamanın uygulanabilmesi için boş alanların her kaydın üst tablosundaki bir değerle otomatik olarak doldurulması gerekiyordu. Kısıtlama her uygulandığında tablo verilerinin Bütünlüğünü olduğu gibi bırakmalıdır. Kısıtlama (Yabancı Anahtar) uygulandığında, üst tablodaki değerlere sahip olmayan bazı veritabanı kayıtları vardı, verilerin bozuk olduğu anlamına gelir, bu nedenle MySQL ASLA KABULİNİZİ UYGULAMAZ

Normal koşullarda veritabanınızı önceden planladıysanız ve veri eklemeden önce kısıtlamalar uyguladıysanız, bu özel senaryodan kaçınılması gerektiğini hatırlamak önemlidir.

Bu sorundan kaçınmanın daha kolay Yaklaşımı

  • Veritabanı tabloları verilerinizi kaydedin
  • Tablo verilerini kısaltın (ve tablo yapaylıkları yani dizinler vb.)
  • Kısıtlamaları Uygulayın
  • Verilerinizi İçe Aktarın

Umarım bu birine yardımcı olur


1

Belki bu yardımcı olacaktır? Birincil anahtar sütununun tanımı, yabancı anahtar sütununun tam olarak aynı olmalıdır.


1

Tüm tabloların yabancı anahtarı desteklediğinden emin olun - InnoDB motoru


1

Alt tablodan bahsettiğiniz PARENT tablosunun sütunu benzersiz olmalıdır. Değilse, 150 numaralı hataya neden olun.


muhtemelen biraz daha ayrıntılı olarak eklemenize değer - örneğin, belirli sütun ve tablo adları
Jonathan

1

Tek bir tablo ile bir Django mysql veritabanı damping benzer bir sorun vardı. Veritabanını bir metin dosyasına dökerek, söz konusu tabloyu emacs kullanarak dosyanın sonuna taşıyarak ve değiştirilen sql dökümü dosyasını yeni örneğe aktararak sorunu çözmeyi başardım.

HTH Uwe


1

Değişkeni kabul ettirerek sorunu düzelttim null

ALTER TABLE `ajout_norme` 
CHANGE `type_norme_code` `type_norme_code` VARCHAR( 2 ) CHARACTER SET utf8 COLLATE utf8_general_ci NULL

1

Bir dizi MySQL komutunu çalıştırırken de aynı sorunu yaşadım. Bir yabancı anahtar henüz oluşturulmamış diğer tabloya atıfta bulunurken bir tablo oluşturulurken mayın oluşur. Referans vermeden önce tablo varlığının sırasıdır.

Çözüm: Yabancı anahtar içeren bir alt tablo oluşturmadan önce üst tabloları oluşturun.


1

Yabancı anahtar olmadan tablo oluşturun, ardından yabancı anahtarı ayrı olarak ayarlayın.

Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.