2010-08-29 50 views
23

據possbile設置/通過更新AUTO_INCREMENT值

ALTER TABLE some_table AUTO_INCREMENT = 1000

重置MySQL表的AUTO_INCREMENT值。然而,我需要在它的現有值來設置AUTO_INCREMENT(固定MM複製),是這樣的:

ALTER TABLE some_table SET AUTO_INCREMENT = AUTO_INCREMENT + 1這是不工作

嗯,事實上,我想運行此查詢在數據庫中的所有表。但實際上這不是非常重要。

我找不到解決這個問題的方法,只能手動運行查詢。請你提出一些建議或指出我的想法。

感謝

+0

這不是工作,以及: 'ALTER TABLE my_db.customer AUTO_INCREMENT =(SELECT AUTO_INCREMENT FROM INFORMATION_SCHEMA。WHERE table_name ='customer')' – pars 2010-08-29 17:32:01

+0

由於您提到了M-M複製:是否真的需要觸摸AUTO_INCREMENT以使複製工作?我通常只需在my.cnf中設置自動增量增量和自動增量偏移值。 – faxi05 2010-08-29 17:34:58

+0

@ faxi05是的,你是對的。我也有相同的配置工作正常。但是爲了在硬件故障後重新同步兩個數據庫,我不得不從一個數據庫轉儲所有數據並將其導入另一個數據庫。在這個過程中有一些錯誤。令人驚訝的是,沒有我做任何事情,他們都走了。 – pars 2010-08-29 20:38:40

回答

36

使用:

ALTER TABLE some_table AUTO_INCREMENT = 0 

...將重置AUTO_INCREMENT值是基於AUTO_INCREMENT列中最高的現有值的下一個值。

要在所有表上運行此操作,您需要使用MySQL's dynamic SQL syntax called PreparedStatements,因爲您無法將ALTER TABLE語句的表名作爲變量提供。您將不得不循環輸出:

SELECT t.table_name 
    FROM INFORMATION_SCHEMA.TABLES t 
WHERE t.table_schema = 'your_database_name' 

...針對每個表運行上面的ALTER TABLE語句。

+0

'ALTER TABLE some_table AUTO_INCREMENT = 0'沒有按預期工作。另一方面,我可能還需要顯式設置auto_increment值。就像增加9個一樣。 這件事情變得越來越複雜。我懷疑我的方向是錯誤的。也許我應該找到另一種方式。 – pars 2010-08-29 20:31:55

+1

@celalo:我不同意'AUTO_INCREMENT = 0'不起作用 - 我在發佈之前自己測試了一下:我添加了三條記錄,在插入第四條記錄之前將auto_increment更新爲100。刪除ID值爲100的記錄,然後在插入第五條記錄之前運行「AUTO_INCREMENT = 0」。插入的記錄高於現有的第三條記錄。 – 2010-08-29 20:39:31

+2

至多幷包括MySQL 5.5,[documentation](http://dev.mysql.com/doc/refman/5.5/en/alter-table.html)陳述:'對於InnoDB,如果該值小於當前值列中的最大值,不會發生錯誤,並且當前的序列值不會更改。「從MySQL 5.6開始,[documentation](http://dev.mysql.com/doc/refman/5.5/en/alter-table。 html)現在聲明:'對於InnoDB和MyISAM,如果該值小於或等於當前AUTO_INCREMENT列中的最大值,則將該值重置爲當前的最大AUTO_INCREMENT列值加1。「#」 – vladr 2014-05-13 18:52:41

1

假設您必須通過修改自動增量列而不是分解N:M關係的表中的外鍵來解決此問題,並且可以引導正確的值,請嘗試使用臨時表,其中相關列不是自動遞增的,然後將其映射回原始表的位置,並將列類型更改爲自動遞增,或者截斷原始表並從臨時表中加載數據。

5

在下面的說明中,您需要用正確的值替換[括號內]中的所有內容。備份之前進行測試。

如果您可以登錄通過命令行來MySQL作爲根,那麼你可以做以下的AUTO_INCREMENT重置所有表,首先我們將構建我們的查詢,我們要運行:

進行數據庫備份:

mysqldump -u [uname] -p [dbname] | gzip -9 > [backupfile.sql.gz] 

登錄:

mysql -u root -p 

設置group_concat_max_length到一個更高的值,因此我們查詢列表不被截斷:

SET group_concat_max_len=100000; 

使用下列創建我們的查詢列表:

SELECT GROUP_CONCAT(CONCAT("ALTER TABLE ", table_name, " AUTO_INCREMENT = 0") SEPARATOR ";") FROM information_schema.tables WHERE table_schema = "[DATABASENAME]"; 

然後你會收到MySQL的查詢,然後一堆短線的長長的一串。查詢字符串複製到剪貼板,它看起來類似於:

ALTER table1 AUTO_INCREMENT = 0;ALTER table2 AUTO_INCREMENT = 0;...continued... 

更改到數據庫中你想運行的命令:

USE [DATABASENAME]; 

然後粘貼是在弦上你的剪貼板並按回車來運行它。這應該在數據庫中的每個表上運行alter。

搞砸了嗎?從備份中恢復,確保運行以下之前註銷的MySQL(只需輸入exit;這樣做)

gzip -d < [backupfile.sql.gz] | mysql -u [uname] -p [dbname] 

我不會把你使用這些命令的任何損壞原因的責任,在使用你自己的風險。

0

我已經寫了下面的程序更改數據庫名稱和執行程序

CREATE DEFINER=`root`@`localhost` PROCEDURE `setAutoIncrement`() 
BEGIN 
DECLARE done int default false; 
    DECLARE table_name CHAR(255); 
DECLARE cur1 cursor for SELECT t.table_name FROM INFORMATION_SCHEMA.TABLES t 
     WHERE t.table_schema = "buzzer_verifone"; 

    DECLARE CONTINUE HANDLER FOR NOT FOUND SET done = TRUE; 
    open cur1; 

    myloop: loop 
     fetch cur1 into table_name; 
     if done then 
      leave myloop; 
     end if; 
     set @sql = CONCAT('ALTER TABLE ',table_name, ' AUTO_INCREMENT = 1'); 
     prepare stmt from @sql; 
     execute stmt; 
     drop prepare stmt; 
    end loop; 

    close cur1; 
END 

執行上面使用以下行的程序

Call setAutoIncrement(); 
4
set @db = 'your_db_name'; 

SELECT concat('ALTER TABLE ', @db, '.', TABLE_NAME, ' AUTO_INCREMENT = 0;') 
FROM information_schema.TABLES WHERE TABLE_SCHEMA = @db 

然後複製,粘貼和運行輸出你得到。

+1

這工作得很好,使用起來非常簡單。切記:不要忘記用您的實際數據庫名稱先替換your_db_name! – 2017-10-24 19:40:46

0

我發現在GitHub上這個要點和它的工作就像一個魅力對我來說:https://gist.github.com/abhinavlal/4571478

命令:

mysql -Nsr -e "SELECT t.table_name FROM INFORMATION_SCHEMA.TABLES t WHERE t.table_schema = 'DB_NAME'" | xargs -I {} mysql DB_NAME -e "ALTER TABLE {} AUTO_INCREMENT = 1;" 

如果您的數據庫需要密碼,你不幸不得不把在命令爲它工作。一個解決方法(仍然不是偉大的但作品)是把密碼放在一個安全的文件。您可以隨時刪除該文件後,所以密碼不會在你的命令歷史留:

... | xargs -I {} mysql -u root -p`cat /path/to/pw.txt` DB_NAME -e...