2012-12-05 16 views
16

Le chiavi esterne mi causano troppi problemi nella modifica di una struttura di database per soddisfare nuovi requisiti - Voglio modificare le chiavi primarie ma sembra che non possa farlo quando le chiavi esterne fanno riferimento alla tabella in questione (I pensa perché MySQL abbandona la tabella e ricrea).DROP tutte le chiavi esterne nel database MYSQL

Così mentre lavoro sul DB, mi piacerebbe semplicemente rimuovere tutte le chiavi esterne e ricrearle in seguito. C'è un modo pulito per farlo?

+0

Basta un pensiero non testato, ma per quanto riguarda la modifica delle tabelle da InnoDB a MyISAM? Anche se la conversione potrebbe essere difficile ... – Sablefoste

+0

OffTopic? Lo sviluppo di database non fa più parte di SO? –

risposta

25

si può semplicemente eseguire il seguente comando prima di qualsiasi dichiarazione Alter Table che si sta per fare:

SET foreign_key_checks = 0; 

Questo si spegnerà controlli vincolo di chiave esterna per la connessione al database. È quindi possibile apportare le modifiche senza la necessità di preoccuparsi dei vincoli.

Dopo aver finito, non dimenticate di emettere:

SET foreign_key_checks = 1; 

Per riattivarli.

Si noti che questo non consente ancora di creare un nuovo vincolo di chiave esterna che non riuscirebbe perché i tipi di dati della colonna non corrispondono.

+1

Sembra perfetto, grazie! –

27

Run

SELECT concat('ALTER TABLE ', TABLE_NAME, ' DROP FOREIGN KEY ', CONSTRAINT_NAME, ';') 
FROM information_schema.key_column_usage 
WHERE CONSTRAINT_SCHEMA = 'db_name' 
AND referenced_table_name IS NOT NULL; 

ed eseguire l'output.

+0

_Come è possibile eseguire l'output? per esempio. in uno script –

+0

@LightnessRacesinOrbit Reindirizzare l'output in un file sql ed eseguire il file. – Zoozy

+3

E come reindirizzare l'output in un file SQL ed eseguire il file, _from all'interno di un'istruzione SQL_? –

2

Un'altra versione di codice Zoozy, qui è possibile selezionare solo una tabella:

SELECT concat('ALTER TABLE ', TABLE_NAME, ' DROP FOREIGN KEY ', CONSTRAINT_NAME, ';') 
FROM information_schema.key_column_usage 
WHERE CONSTRAINT_SCHEMA = 'YOUR DB HERE' 
AND TABLE_NAME='YOUR TABLE HERE' 
AND REFERENCED_TABLE_NAME IS NOT NULL; 

Anche con una procedura:

DROP PROCEDURE IF EXISTS dropForeignKeysFromTable; 

delimiter /// 
create procedure dropForeignKeysFromTable(IN param_table_schema varchar(255), IN param_table_name varchar(255)) 
begin 
    declare done int default FALSE; 
    declare dropCommand varchar(255); 
    declare dropCur cursor for 
     select concat('alter table ',table_schema,'.',table_name,' DROP FOREIGN KEY ',constraint_name, ';') 
     from information_schema.table_constraints 
     where constraint_type='FOREIGN KEY' 
      and table_name = param_table_name 
      and table_schema = param_table_schema; 

    declare continue handler for not found set done = true; 

    open dropCur; 

    read_loop: loop 
     fetch dropCur into dropCommand; 
     if done then 
      leave read_loop; 
     end if; 

     set @sdropCommand = dropCommand; 

     prepare dropClientUpdateKeyStmt from @sdropCommand; 

     execute dropClientUpdateKeyStmt; 

     deallocate prepare dropClientUpdateKeyStmt; 
    end loop; 

    close dropCur; 
end/// 
Problemi correlati