2011-03-29 67 views
212

MySQL tiene un comando OPTIMIZE TABLE que se puede utilizar para recuperar espacio no utilizado en una instalación de MySQL. ¿Existe alguna forma (comando incorporado o procedimiento almacenado común) de ejecutar esta optimización para cada tabla en la base de datos y/o instalación del servidor, o es algo que tendrías que crear tú mismo?MySQL OPTIMIZE todas las tablas?

+9

tener cuidado en que esto no Necessari recuperar espacio Si está utilizando InnoDB con un solo archivo (probablemente la configuración más común actualmente) en lugar de archivos separados por tabla, igual utilizará la misma cantidad de espacio en disco al final. De hecho, he visto que realmente usa mucho más espacio en disco cuando todo estaba dicho y hecho. Con tablas grandes, la tabla también puede estar bloqueada durante mucho tiempo. – jmichalicek

Respuesta

347

Puede usar mysqlcheck para hacer esto en la línea de comando.

una base de datos:

mysqlcheck -o <db_schema_name> 

Todas las bases de datos:

mysqlcheck -o --all-databases 
+0

¿recomendaría este comando para programarse para ejecutarse al menos una vez al mes? – Gaia

+9

Hola, @Gaia. No necesariamente. Optimizar todas las tablas en un horario determinado no es beneficioso para todos. Eche un vistazo a esta publicación y lea los comentarios para una reflexión mucho más profunda sobre este tema de la que puedo proporcionar en un espacio limitado aquí: http://www.xaprb.com/blog/2010/02/07/how-often- should-you-use-optimize-table/ –

+0

más bien como "probablemente no" a menos que esté evitando tablas grandes y tenga en cuenta qué tablas son InnoDB vs MyISAM – zanlok

14

Siguiendo el ejemplo de script PHP puede ayudar a optimizar todas las tablas de la base de datos

<?php 

dbConnect(); 

$alltables = mysql_query("SHOW TABLES"); 

while ($table = mysql_fetch_assoc($alltables)) 
{ 
    foreach ($table as $db => $tablename) 
    { 
     mysql_query("OPTIMIZE TABLE '".$tablename."'") 
     or die(mysql_error()); 

    } 
} 

?> 
+5

En una base de datos con 200 tablas, ejecutará 200 consultas separadas para optimizar 1 tabla a la vez. Debería implotar los nombres de tabla en una cadena y, por lo tanto, solo se requiere una consulta de tabla de optimización. –

+0

buen punto Dean –

+7

Me pregunto si el enfoque de consulta por separado es a veces mejor. MySQL dice que las tablas están bloqueadas mientras se está ejecutando OPTIMIZE TABLE. Entonces, parecería más inteligente optimizar cada una a la vez para permitir que el servidor adquiera cerraduras por el tiempo mínimo. Obviamente, eso es para un servidor al que se ha accedido. Si no, entonces creo que una sola consulta es el mejor enfoque. – glarrain

3

El (parte de las herramientas visuales de MySQL) MySQL Administrator lo puede hacer por usted en un nivel de base de datos.

Simplemente seleccione su esquema y presione el botón Maintenance en la esquina inferior derecha.

Dado que las Herramientas GUI han alcanzado el estado de Fin de vida, son difíciles de encontrar en la página mysql. Los encontré a través de Google: http://dev.mysql.com/downloads/gui-tools/5.0.html

No sé si el nuevo MySQL Workbench puede hacer eso también.

Y puede usar la herramienta de línea de comandos mysqlcheck que también debería poder hacer eso.

4

Desde la línea de comandos:

mysqlcheck -o <db_name> -u<username> -p 

a continuación, escriba la contraseña

4

Puede optimizar/comprobar y reparar todos las tablas o f base de datos, utilizando el cliente mysql.

En primer lugar, usted debe obtener toda la lista de tablas, separados por '':

mysql -u[USERNAME] -p[PASSWORD] -Bse 'show tables' [DB_NAME]|xargs|perl -pe 's/ /,/g' 

Ahora, cuando se tiene toda la lista de tablas para la optimización:

mysql -u[USERNAME] -p[PASSWORD] -Bse 'optimize tables [tables list]' [DB_NAME] 
9

para todas las bases de datos:

mysqlcheck -Aos -uuser -p 

Para la optimización de una base de datos:

mysqlcheck -os -uroot -p dbtest3 
+0

Al menos para mí, en Linux, el comando' mysqlcheck -Aos' no requiere usuario + contraseña. – Zuul

19

hice este script 'simple':

set @a=null,@c=null,@b=concat("show tables where",ifnull(concat(" `Tables_in_",database(),"` like '",@c,"' and"),'')," (@a:=concat_ws(',',@a,`Tables_in_",database(),"`))"); 

Prepare `bd` from @b; 
EXECUTE `bd`; 
DEALLOCATE PREPARE `bd`; 

set @a:=concat('optimize table ',@a); 
PREPARE `sql` FROM @a; 
EXECUTE `sql`; 
DEALLOCATE PREPARE `sql`; 

set @a=null,@b=null,@c=null; 

para ejecutarlo, simplemente pegarlo en cualquier IDE SQL conectado a la base de datos.

Aviso: este código NO funcionará en phpmyadmin.

Cómo funciona

Se ejecuta una declaración show tables y lo almacena en una declaración preparada. Luego ejecuta un optimize table en el conjunto seleccionado.

Puede controlar qué tablas desea optimizar estableciendo un valor diferente en var @c.

+3

Mi entorno de alojamiento compartido no tiene 'mysqlchk' disponible, así que podría ejecutarlo directamente desde una sesión de terminal 'mysql'. ¡Gracias! – funwhilelost

+0

De nada. Utilizo este código para optimizar 50 bases de datos y pasar la menor cantidad de tiempo posible. Si crees que puedo mejorar el código de alguna manera, adelante y dame tus sugerencias. Estaré encantado de mejorar esta preciosa pieza de código. –

+0

Prepare 'bd' desde @b \t Código de error: 1064. Tiene un error en la sintaxis SQL; revise el manual que corresponde a su versión del servidor MySQL para la sintaxis correcta para usar cerca de 'NULL' en la línea 1 –

8

¿Todos los procedimientos necesarios para la fijación de todas las tablas de todas las bases de datos con un simple script de shell:

#!/bin/bash 
mysqlcheck --all-databases 
mysqlcheck --all-databases -o 
mysqlcheck --all-databases --auto-repair 
mysqlcheck --all-databases --analyze 
+0

¡Genial! Automatizado :) –

-1

mis 2cents: empezar con mesa con mayor fragmentación

for table in `mysql -sss -e "select concat(table_schema,".",table_name) from information_schema.tables where table_schema not in ('mysql','information_schema','performance_schema') order by data_free desc;" 
do 
mysql -e "OPTIMIZE TABLE $table;" 
done 
4

Desde phpMyAdmin y otra fuentes que puede usar:

SET SESSION group_concat_max_len = 99999999; 
SELECT GROUP_CONCAT(concat('OPTIMIZE TABLE `', table_name, '`;') SEPARATOR '') AS O 
FROM INFORMATION_SCHEMA.TABLES WHERE 
TABLE_TYPE = 'BASE TABLE' 
AND table_name!='dual' 
AND TABLE_SCHEMA = '<your databasename>' 

Luego puede copiar & pegue el resultado a una nueva consulta o ejecútelo desde su propia fuente.

0

Este script bash aceptará la contraseña de root como opción y optimizarlo uno por uno, con salida de estado:

#!/bin/bash 

if [ -z "$1" ] ; then 
    echo 
    echo "ERROR: root password Parameter missing." 
    exit 
fi 
MYSQL_USER=root 
MYSQL_PASS=$1 
MYSQL_CONN="-u${MYSQL_USER} -p${MYSQL_PASS}" 
TBLLIST="" 
COMMA="" 
SQL="SELECT CONCAT(table_schema,'.',table_name) FROM information_schema.tables WHERE" 
SQL="${SQL} table_schema NOT IN ('information_schema','mysql','performance_schema')" 
for DBTB in `mysql ${MYSQL_CONN} -ANe"${SQL}"` 
do 
    echo OPTIMIZE TABLE "${DBTB};" 
    SQL="OPTIMIZE TABLE ${DBTB};" 
    mysql ${MYSQL_CONN} -ANe"${SQL}" 
done 
1

Si se desea analizar, reparar y optimizar todas las tablas de todas las bases de datos del servidor MySQL , puedes hacer esto de una vez desde la línea de comando. Sin embargo, necesitarás root para hacer eso.

mysqlcheck -u root -p --auto-repair --optimize --all-databases 

Una vez que lo ejecute, se le pedirá que ingrese su contraseña de root de MySQL. Después de eso, comenzará y verá resultados mientras está sucediendo.

Ejemplo de salida:

yourdbname1.yourdbtable1  OK 
yourdbname2.yourdbtable2  Table is already up to date 
yourdbname3.yourdbtable3 
note  : Table does not support optimize, doing recreate + analyze instead 
status : OK 

etc.. 
etc... 

Repairing tables 
yourdbname10.yourdbtable10 
warning : Number of rows changed from 121378 to 81562 
status : OK 

Si no conoce la contraseña de root y está utilizando WHM, puede cambiar desde dentro WHM yendo a: Inicio> Servicios de SQL> MySQL contraseña de root

0

una escritura del golpe de arranque a la lista y ejecutar una herramienta contra la DB ...

#!/bin/bash 

declare -a dbs 
unset opt 

for each in $(echo "show databases;" | mysql -u root) ;do 

     dbs+=($each) 

done 



echo " The system found [ ${#dbs[@]} ] databases." ;sleep 2 
echo 
echo "press 1 to run a check" 
echo "press 2 to run an optimization" 
echo "press 3 to run a repair" 
echo "press 4 to run check,repair, and optimization" 
echo "press q to quit" 
read input 

case $input in 
     1) opt="-c" 
     ;; 
     2) opt="-o" 
     ;; 
     3) opt="-r" 
     ;; 
     4) opt="--auto-repair -c -o" 
     ;; 
     *) echo "Quitting Application .."; exit 7 
     ;; 
esac 

[[ -z $opt ]] && exit 7; 

echo " running option: mysqlcheck $opt in 5 seconds on all Dbs... "; sleep 5 

for ((i=0; i<${#dbs[@]}; i++)) ;do 
     echo "${dbs[$i]} : " 
     mysqlcheck $opt ${dbs[$i]} -u root 
    done 
Cuestiones relacionadas