【问题标题】:Scheduling A Weekly Script for rebuild Mysql Index调度每周脚本以重建 Mysql 索引
【发布时间】:2019-04-06 13:37:03
【问题描述】:

我们计划部署一个存储过程来重建索引。根据 Mysql 论坛上的以下规范。有人可以发送任何示例脚本,对特定数据库中的所有表执行相同的操作。对于周末运行的以下脚本,我们是否会遇到任何顾虑或任何问题。

ALTER TABLE t1 ENGINE = InnoDB;

https://dev.mysql.com/doc/refman/5.7/en/rebuilding-tables.html#rebuilding-tables-alter-table

【问题讨论】:

    标签: mysql scalability database-indexes


    【解决方案1】:

    索引在 InnoDB 中保持最新,统计数据可能会过时。发布 5.6 即使据我所知也很少需要。运行 Alter 命令将修复表,这将修复任何碎片。您可以在此处阅读 ALTER TABLE 可用的不同类型的算法: ALTER TABLE

    如果你想检查数据库,你可以使用 check mysql 命令,它执行 ALTER 以及其他一些位 n 块来优化索引、更新统计信息等。 mysqlcheck

    【讨论】:

    • 嘿,谢谢,我们确实在周末运行了优化查询。周一感觉不到任何改善。在我的存储桶中,我似乎没有任何其他关于数据库性能的技巧。
    • 您查看过您的查询计划吗?你的 cpu 使用率、内存和磁盘是什么样的?不过,我建议您先检查您的查询计划 :)
    • 这不是一个通用的解决方案。在带有 innodb 的大型表上,我有可重复的索引降级,降至正常访问速度的 1/10000。特别是在应该是 HASH 类型的索引上(但 innodb 只有 btree) 现在“优化”或“更改”自然会解决这个问题,但在这里你需要存储和时间。在大表上,可能需要一周时间才能完成 OPTIMIZE,而且您需要 TB 的存储空间,如果表内有任何微小的损坏,您最终将一无所有。
    【解决方案2】:

    下面是一个用于优化 Mysql DB 的 mysql 脚本。然而,如前所述,它很少需要,因为 InnoDB 本身也能做到这一点。

    USE VIPLamar; 
    DROP PROCEDURE IF  EXISTS Lamar_Index_Rebuild_Script;
    DELIMITER //
    
    -- call Lamar_Index_Rebuild_Script();
    CREATE PROCEDURE Lamar_Index_Rebuild_Script()
    mysp:BEGIN
    
    Declare v_max_counter int;
    Declare v_counter int;
    
    Declare v_query longtext;
    Declare v_table_name varchar(1000);
    Declare v_datetime datetime default now();
    DROP temporary TABLE if exists temp_todo;
    
    create temporary table temp_todo
    (
        id int auto_increment primary key, 
        `table_name` varchar(1000)
    );
    
    create table if not exists VIP_Lamar_Index_Rebuild_Script
    (
        id int auto_increment primary key, 
        `table_name` varchar(1000),
        start_date datetime,
        finish_date datetime
    );
    
    insert into temp_todo (table_name)
    SELECT table_name FROM INFORMATION_SCHEMA.TABLES WHERE table_schema = DATABASE();
    
    -- loop thru table
    -- check if table exists
    Select max(id) Into v_max_counter from temp_todo;
    Set v_counter = 1;
    WHILE v_counter <= v_max_counter 
    Do
        select  `table_name` into  v_table_name from temp_todo where id = v_counter;
        IF (EXISTS (SELECT 1 FROM INFORMATION_SCHEMA.TABLES WHERE  table_name = v_table_name AND table_schema = DATABASE()))
        THEN
            set v_query = concat('OPTIMIZE TABLE ' , v_table_name , ';');
            set @stmt = v_query;
            PREPARE tempstatement FROM @stmt;
            EXECUTE tempstatement;
            DEALLOCATE PREPARE tempstatement;
        END if;
    
        set v_counter = v_counter +1 ;
    end while;   
    
    insert into VIP_Lamar_Index_Rebuild_Script(`table_name`,start_date,finish_date)
    select table_name,v_datetime,now() from temp_todo
    ;
    -- select * from VIP_Lamar_Index_Rebuild_Script;
    -- drop table VIP_Lamar_Index_Rebuild_Script;
    
    DROP temporary TABLE if exists temp_todo;
    
    END;
    //
    DELIMITER ;
    

    【讨论】:

      猜你喜欢
      • 2019-01-22
      • 1970-01-01
      • 2010-11-08
      • 2011-04-02
      • 1970-01-01
      • 1970-01-01
      • 2014-04-14
      • 2014-11-24
      • 2019-11-03
      相关资源
      最近更新 更多