Czy MySQL Foreign_key_checks wpływa na całą bazę danych?

201

Kiedy wykonuję to polecenie w MySQL:

SET FOREIGN_KEY_CHECKS=0;

Czy wpływa to na cały silnik, czy to tylko moja bieżąca transakcja?

Sean Nguyen
źródło
15
test: zaloguj się do mysql: pokaż zmienne takie jak '% FOREIGN%'; SET FOREIGN_KEY_CHECKS = 0; Następnie zaloguj się do mysql przy użyciu innej konsoli. Widzę, że zmienne pokazujące, takie jak „% FOREIGN%”, są WŁĄCZONE zamiast WYŁĄCZONE.
Sean Nguyen,

Odpowiedzi:

98

W rzeczywistości istnieją dwie foreign_key_checkszmienne: zmienna globalna i zmienna lokalna (na sesję). Po połączeniu zmienna sesji jest inicjalizowana do wartości zmiennej globalnej.
Polecenie SET foreign_key_checksmodyfikuje zmienną sesji.
Aby zmodyfikować zmienną globalną, użyj SET GLOBAL foreign_key_checkslub SET @@global.foreign_key_checks.

Zapoznaj się z następującymi sekcjami podręcznika:
http://dev.mysql.com/doc/refman/5.7/en/using-system-variables.html
http://dev.mysql.com/doc/refman/5.7/en/server -system-variable.html

Ron Inbar
źródło
1
Czy ustawienie zagranicznych kluczy dla każdego żądania jest kosztowne? Mam skrypt do aktualizacji DB i nie chciałbym, aby ktokolwiek inny mógł domyślnie zastąpić sprawdzanie klucza obcego podczas tej aktualizacji. Zrobiłbym więc miliony zapytań i zastanawiałem się, czy SET będzie znaczący, czy nie?
Aki
@Aki Jeśli aktualizujesz DB, powiedziałbym, że lepiej zablokować dostęp dla wszystkich innych. Przynajmniej do pisania. W przeciwnym razie możesz spodziewać się wszelkiego rodzaju problemów z równoczesnym dostępem.
tishma
1
Świetna odpowiedź i wyróżnienie. Ważne jest, aby zdawać sobie sprawę z konsekwencji tego, jak to działa. Oznacza to, że nie można ustawić GLOBALNEGO foreign_key_checksi w tej samej sesji można oczekiwać, że zignoruje ograniczenia kluczy obcych. Musisz ustawić zmienną nieglobalną.
Tyler Collier,
12

Jak wyjaśnił Ron, istnieją dwie zmienne, lokalna i globalna. Zmienna lokalna jest zawsze używana i po podłączeniu jest taka sama jak globalna.

SET FOREIGN_KEY_CHECKS=0;
SET GLOBAL FOREIGN_KEY_CHECKS=0;

SHOW Variables WHERE Variable_name='foreign_key_checks'; # always shows local variable

Podczas ustawiania zmiennej GLOBAL, zmienna lokalna nie jest zmieniana dla żadnych istniejących połączeń. Musisz ponownie połączyć lub ustawić zmienną lokalną.

Być może nieintuicyjny, MYSQL nie wymusza kluczy obcych, gdy FOREIGN_KEY_CHECKS są ponownie włączone. Umożliwia to utworzenie niespójnej bazy danych, nawet jeśli klucze obce i kontrole są włączone.

Jeśli chcesz, aby klucze obce były całkowicie spójne, musisz dodać klucze, gdy sprawdzanie jest włączone.

Bouke Versteegh
źródło
1
Czy możesz rozwinąć ... „Jeśli chcesz, aby klucze obce były całkowicie spójne, musisz dodać klucze, gdy sprawdzanie jest włączone”.
user2782001
4
Załóżmy, że masz tabelę z referencyjnymi identyfikatorami, ale brakuje niektórych rekordów referencyjnych. Jeśli dodasz klucz obcy (FK), gdy FOREIGN_KEY_CHECKS są WŁĄCZONE, Mysql zgłosi błąd i odmówi dodania FK, z powodu zepsutego odwołania. Po dodaniu klucza obcego, gdy FOREIGN_KEY_CHECKS są wyłączone, mysql kontynuuje bezbłędnie. Nawet po późniejszym włączeniu kontroli nie wystąpi błąd. Masz teraz tabelę z niespójnymi danymi, nawet jeśli istnieje FK. W związku z tym istnienie FK nie gwarantuje spójności bazy danych, chyba że zostało dodane podczas sprawdzania FK.
Bouke Versteegh
10
# will get you the current local (session based) state.
SHOW Variables WHERE Variable_name='foreign_key_checks';

Jeśli nie ustawiłeś GLOBAL, dotyczy to tylko Twojej sesji.

Mike Karras
źródło
1

Miałem ten sam błąd, gdy próbowałem migrować bazę danych Drupal na nowy lokalny serwer Apache (używam XAMPP na komputerze z systemem Windows). Właściwie nie znam znaczenia tego błędu, ale po wykonaniu poniższych kroków zaimportowałem bazę danych bez błędów. Mam nadzieję, że to może pomóc:

Zmiana php.ini na C: \ xampp \ php \ php.ini

max_execution_time = 600
max_input_time = 600
memory_limit = 1024M
post_max_size = 1024M

Zmiana my.ini w C: \ xampp \ mysql \ bin \ my.ini

max_allowed_packet = 1024M
Saeed cr7
źródło
-2

W przypadku korzystania z przeglądarki zapytań MySQL SET FOREIGN_KEY_CHECKS=0;nie ma ona wpływu na wersję 1.1.20. Działa to jednak poprawnie w przeglądarce zapytań MySQL 1.2.17

użytkownik2682955
źródło