2016-10-28 36 views
3

通常我通過刪除外鍵並重新創建它來更改表的更新和刪除規則。示例如下:僅更改MySQL中一組表的更新和刪除規則

ALTER TABLE xyz DROP FOREIGN KEY fk_1;

ALTER TABLE xyz ADD CONSTRAINT fk_1 FOREIGN KEY (a) REFERENCES batch_details a) ON DELETE CASCADE ON UPDATE CASCADE;

但是,如果我有一組數據表,然後做這樣很乏味的。 雖然我可以看到更新和使用

select * from information_schema.referential_constraints;

我也曾嘗試刪除所有表規則:

update information_schema.referential_constraints set update_rule='CASCADE',delete_rule='CASCADE' where table_name='x';

不過需要root權限,我不能放棄。 請幫助如何做到這一點。

由於提前

+0

您是否有權限在服務器上執行此操作?也許你沒有權利更新這個表或沒有權利更新表結構 – rbr94

+1

是的,我可以使用上面給出的基本alter命令更新 – Sanghita

+0

我的意思是更新'information_schema.referential_constraints' – rbr94

回答

0

我的建議是創建一組可以重用執行這些操作,然後把這種行政程序的存儲過程 - 無論是在環路外的程序,或從腳本。例如,您可以遍歷原始information_schemaSELECT查詢的結果(可能在過程中使用遊標),然後爲返回的每一行調用新的管理過程。

以下是可用於刪除外鍵的管理存儲過程。您可以使用相同的原則來創建類似的過程來添加約束。

DROP PROCEDURE IF EXISTS `admin_drop_fk`; 

DELIMITER $$ 

CREATE PROCEDURE `admin_drop_fk`(
    fk_name VARCHAR(64),  
    table_name VARCHAR(64), 
    db_name VARCHAR(64) 
) 
BEGIN 
SET @sqlexec := 
CONCAT 
(
    'SELECT @i := COUNT(*) FROM INFORMATION_SCHEMA.KEY_COLUMN_USAGE WHERE CONSTRAINT_NAME = \'', 
    fk_name, 
    '\' AND TABLE_NAME = \'', 
    table_name, 
    '\' AND TABLE_SCHEMA = \'', 
    db_name, 
    '\'' 
); 

SELECT CONCAT('Executing: "', @sqlexec, '"') AS 'Info'; 
PREPARE lookup FROM @sqlexec; 
EXECUTE lookup; 
DEALLOCATE PREPARE lookup; 

IF @i > 0 THEN 
    SET @sqlexec := CONCAT('ALTER TABLE `', db_name, '`.`', table_name, '` DROP FOREIGN KEY `', fk_name, '`'); 
    SELECT CONCAT('Executing: "', @sqlexec, '"') AS 'Info'; 
    PREPARE statement FROM @sqlexec; 
    EXECUTE statement; 
    DEALLOCATE PREPARE statement; 
    SELECT CONCAT('Successful execution of: "', @sqlexec, '"') AS 'Info'; 
ELSE 
    SELECT CONCAT('Warning: Foreign key `', fk_name, '` does not exist on `', db_name, '`.`', table_name, '`') AS 'Warning'; 
END IF; 

END$$ 

DELIMITER ;