MySQL tüm tabloları OPTİMİZE EDİYOR MU?


245

MySQL, bir MySQL kurulumunda kullanılmayan alanı geri kazanmak için kullanılabilecek bir OPTIMIZE TABLE komutuna sahiptir. Veritabanındaki ve / veya sunucu kurulumundaki her tablo için bu optimizasyonu çalıştırmanın bir yolu (yerleşik komut veya ortak saklı yordam) var mıdır, yoksa bu, kendiniz kodlamanız gereken bir şey mi?


11
Bunun alanı geri kazanmayacağına dikkat edin. InnoDB'yi tablo başına ayrı dosyalar yerine tek bir dosyayla (muhtemelen bu günlerde en yaygın kurulum) kullanıyorsanız, yine de aynı miktarda disk alanı kullanacaksınız. Aslında, her şey söylendiğinde ve yapıldığında gerçekten daha fazla disk alanı kullandığını gördüm. Büyük masalarda, masa da çok uzun süre kilitlenebilir.
jmichalicek

1
OPTIMIZE TABLEMyISAM için kullanışlıdır. Şimdi bu Motor kullanımdan kaldırıldığına OPTIMIZE TABLE, özellikle tüm tabloları periyodik olarak optimize etme ihtiyacı ortadan kalkıyor.
Rick James

İyi bilgi rick için +1 - ancak standart gerçek dünya veritabanı uygulamaları göz önüne alındığında, eski MyISAM tabloları başka bir on yıl boyunca kalırsa şaşırmazdım
Alan Storm

Yanıtlar:


410

Bunu mysqlcheckkomut satırından yapmak için kullanabilirsiniz .

Bir veritabanı:

mysqlcheck -o <db_schema_name>

Tüm veritabanları:

mysqlcheck -o --all-databases

bu komutun ayda en az bir kez çalışacak şekilde zamanlanmasını önerir misiniz?
Gaia

11
Merhaba @Gaia. Şart değil. Belirli bir programdaki tüm tabloları optimize etmek herkes için yararlı değildir. Bu gönderiye
Ike Walker

18
basit kullanım:mysqlcheck -u [username] -p[password] -o [database name]
M Rostami

38
OPTIMIZE gerçekleştirilirken tabloların kilitlendiğini ve tabloların çok fazla veri barındırması uzun sürebileceğini lütfen unutmayın. Bu nedenle, bir tablo OPTİMİZE EDİLDİĞİ sırada yeni kayıt eklenemez veya silinemez. Genel olarak, bir üretim sisteminin tüm tablolarını OPTİMİZE ETMEK önemsiz bir işlem olarak kabul edilemez.
Werner

2
@ No-Chip, dev.mysql.com/doc/refman/5.5/en/optimize-table.htmlOPTIMIZE TABLE komutunu kullanarak MySQL istemcisindeki tabloları optimize edebilirsiniz . Örneğin, aşağıdaki gibi bir tabloyu optimize edin:, belirli bir şemadaki tüm tabloları şu şekilde optimize edin:OPTIMIZE TABLE <your_schema>.<your_table>;select concat('OPTIMIZE NO_WRITE_TO_BINLOG TABLE ',table_schema,'.',table_name,';') into outfile '/tmp/optimize_all_tables.sql' from information_schema.tables where table_schema = 'pabeta' and table_type = 'base table'; source /tmp/optimize_all_tables.sql;
Ike Walker

28

Bu 'basit' senaryoyu yaptım:

set @tables_like = null;
set @optimize = null;
set @show_tables = concat("show tables where", ifnull(concat(" `Tables_in_", database(), "` like '", @tables_like, "' and"), ''), " (@optimize:=concat_ws(',',@optimize,`Tables_in_", database() ,"`))");

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

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

set @show_tables = null, @optimize = null, @tables_like = null;

Çalıştırmak için veritabanınıza bağlı herhangi bir SQL IDE'ye yapıştırmanız yeterlidir.

Uyarı: Bu kod phpmyadmin üzerinde çalışmaz .

Nasıl çalışır

Bir show tablesifade çalıştırır ve hazırlanmış bir deyimde saklar. Sonra optimize tableseçilen kümede a çalışır .

Var'da farklı bir değer ayarlayarak hangi tabloların optimize edileceğini kontrol edebilirsiniz @tables_like(örn :) set @tables_like = '%test%';.


4
Paylaşılan barındırma ortamımda 'mysqlchk' mevcut değil, bu yüzden bunu doğrudan 'mysql' terminal oturumundan çalıştırabilirim. Teşekkür ederim!
funwhilelost

Rica ederim. Bu veritabanını 50 veritabanını optimize etmek ve olabildiğince az zaman harcamak için kullanıyorum. Kodu herhangi bir şekilde geliştirebileceğimi düşünüyorsanız, devam edin ve bana önerilerinizi verin. Bu değerli kod parçasını geliştirmekten mutlu olacağım.
Ismael Miguel

bd@B Hata Kodundan hazırlayın : 1064. SQL sözdiziminizde bir hata var; 1. satırda 'NULL' yakınında kullanılacak doğru sözdizimi için MySQL sunucu sürümünüze karşılık gelen kılavuza bakın
Paul Gregoire

@IsmaelMiguel bu MySQL, cevabınız TSQL sözdizimi kullanıyor ve MySQL ile çalışmaz.
Phrancis

2
@LorenzoBelfanti Onayladığınız için teşekkür ederiz. 2 yıl sonra bile bu kodun en az 10 kişi için yararlı olduğunu düşünüyorum. Bu benim için büyük bir zafer! Bir kez daha teşekkür ederim!
Ismael Miguel

20

Aşağıdaki örnek php betiği, veritabanınızdaki tüm tabloları optimize etmenize yardımcı olabilir

<?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());

   }
}

?>

7
200 tablo içeren bir veritabanında, her seferinde 1 tablo optimize eden 200 ayrı sorgu çalıştıracaksınız. Tablo adlarını bir dizeye yerleştirmelisiniz ve bu nedenle yalnızca bir en iyi duruma getirme tablosu sorgusu gereklidir.
Dean Marshall

8
Ayrı sorgu yaklaşımının bazen daha iyi olup olmadığını merak ediyorum. MySQL, OPTIMIZE TABLE çalışırken tabloların kilitli olduğunu söylüyor. Daha sonra, sunucunun minimum süre kilit almasını sağlamak için her birini optimize etmek daha akıllıca görünecektir. Açıkçası, erişilen bir sunucu içindir. Değilse, o zaman tek bir sorgu en iyi yaklaşım iss düşünüyorum.
glarrain

1 sorguya yerleştirilir ve yazılırsanız komut dosyası nasıl görünür? Teşekkürler.
H. Ferrence

8
@Dean Ayrı bir sorgu yaklaşımı, canlı bir uygulama için nefes alan sağlamak için genellikle daha iyidir. Aslında, tam olarak bu amaç için bir gecikme (sadece 750ms ya da daha fazla) eklerim.
zanlok

15

Tüm veritabanlarındaki tüm tabloları basit bir kabuk komut dosyasıyla düzeltmek için gerekli tüm işlemleri yapın:

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

11

tüm veritabanları için:

mysqlcheck -Aos -uuser -p 

Bir Veritabanı optimizasyonu için:

mysqlcheck -os -uroot -p dbtest3

En azından benim için, Linux altında, komut mysqlcheck -Aoskullanıcı + şifre gerektirmez.
Zuul

7

PhpMyAdmin ve diğer kaynaklardan şunları kullanabilirsiniz:

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>'

Ardından sonucu kopyalayıp yeni bir sorguya yapıştırabilir veya kendi kaynağınızdan çalıştırabilirsiniz. Tüm ifadeyi görmüyorsanız: phpmyadmin'de tüm ifadeyi görmenin yolu


bu güzel bir cevaptı, ama benim phpmyadmin tüm komutu göstermiyor, sadece ilk olanlar o zaman ... benim için üzgünüm, lol.
MonneratRJ

6

MySQL sunucunuzdaki tüm veritabanlarındaki tüm tabloları analiz etmek, onarmak ve optimize etmek istiyorsanız, bunu komut satırından tek seferde yapabilirsiniz. Yine de bunu yapmak için kök gerekir.

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

Bunu çalıştırdıktan sonra, MySQL kök parolanızı girmeniz istenir. Bundan sonra başlayacak ve sonuçları olduğu gibi göreceksiniz.

Örnek çıktı:

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

Kök parolasını bilmiyorsanız ve WHM kullanıyorsanız, şu adrese giderek WHM içinden değiştirebilirsiniz: Ana Sayfa> SQL Hizmetleri> MySQL Kök Parolası


5

Komut satırından:

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

sonra şifre yaz


4

Mysql istemcisini kullanarak tüm veritabanı tablolarını optimize edebilir / kontrol edebilir ve onarabilirsiniz.

İlk olarak, ',' ile ayrılmış tüm tablolar listesini almalısınız:

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

Şimdi, optimizasyon için tüm tablolar listesine sahip olduğunuzda:

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

3

MySQL Administrator(MySQL GUI Tools parçası) bir veritabanı düzeyinde sizin için yapabilir.

Şemanızı seçin ve Maintenancesağ alt köşedeki düğmeye basın .

GUI Araçları Kullanım Ömrü Sonu durumuna ulaştığından mysql sayfasında bulmak zor. Onları Google üzerinden buldum: http://dev.mysql.com/downloads/gui-tools/5.0.html

Yeni MySQL Workbench'in bunu da yapıp yapamayacağını bilmiyorum.

Ve bunu yapabilmesi gereken mysqlcheckkomut satırı aracını da kullanabilirsiniz.


2

Veritabanına doğrudan erişiyorsanız, aşağıdaki sorguyu yazabilirsiniz:

OPTIMIZE TABLE table1,table2,table3,table4......;

1

Bu bash betiği, kök parolasını seçenek olarak kabul eder ve durum çıktısıyla tek tek optimize eder:

#!/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

DB'lere karşı bir aracı listelemek ve çalıştırmak için bir başlangıç ​​bash betiği ...

#!/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

0

benim 2 sent: en yüksek parçalanma ile tablo ile başlayı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
Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.