importação de despejo mysql incrivelmente lenta na máquina do meu desenvolvedor


22

Eu tenho um dump SQL, é muito grande (411 MB) e demorou 10 minutos para importar no servidor A, a mesma importação na minha estação de trabalho B tem uma estimativa (pipeviewer) de 8 horas para importar (importou 31 MB em 40 minutos) ) Portanto, esse é o fator 53 mais lento.

As especificações:

Server A:
   MySQL Version: 5.5.30-1.1 (Debian)
   2 GB RAM
   1 core QEMU Virtual CPU version 1.0 - cpu MHz: 3400.020

Workstation B: 
   MySQL Version: 5.5.41-MariaDB-1ubuntu0.14.04.1
   14 GB RAM
   4 cores Intel(R) Core(TM) i5-2400 CPU @ 3.10GHz - cpu MHz: 1600.000

A configuração do mysql / maria é a configuração de estoque.

Mudei ontem para o MariaDB na minha estação de trabalho - mas antes do MariaDB as estatísticas eram ainda piores.

Eu já removi todos os bancos de dados da minha estação de trabalho - não há diferença.

A grande questão é: como o desempenho pode ser fator 53 mais lento? Eu não posso trabalhar assim :-(

Meu comando de importação:

pv sql/master.sql | mysql -h'localhost' -u'root' -p'root' 'master'

iostat -xm 5

servidor A:

avg-cpu:  %user   %nice %system %iowait  %steal   %idle
      17,43    0,00   30,28   51,85    0,00    0,44

Device:         rrqm/s   wrqm/s     r/s     w/s    rMB/s    wMB/s avgrq-sz avgqu-sz   await r_await w_await  svctm  %util
sda               0,00   254,03    0,00 1305,45     0,00     6,09     9,56     0,78    0,60    0,00    0,60   0,57  74,25

estação de trabalho B:

avg-cpu:  %user   %nice %system %iowait  %steal   %idle
       7,32    0,00    3,22    5,03    0,00   84,42

Device:         rrqm/s   wrqm/s     r/s     w/s    rMB/s    wMB/s avgrq-sz avgqu-sz   await r_await w_await  svctm  %util
sda               0,00     1,40    0,80  172,40     0,00     0,56     6,72     1,17    6,75   12,00    6,72   5,40  93,52

dd if=/dev/zero of=tempfile bs=1M count=1024 conv=fdatasync,notrunc

servidor A:

1073741824 bytes (1,1 GB) copied, 18,6947 s, 57,4 MB/s

estação de trabalho B:

1073741824 bytes (1,1 GB) copied, 8,95646 s, 120 MB/s

Você pode me descrever como deseja importar o banco de dados? (qual é a sua declaração concreta do mysql) O que significa "show processlist;" dizer? Você já viu o que o processo está fazendo concreto com strace? Você também pode dar uma olhada se sua máquina está trocando?

Eu editei minha pergunta.
Alex

InnoDB? Qual é o valor de innodb_buffer_pool_sizecada máquina?
Rick James

Respostas:


47

Essa resposta acelerou muito tudo:

/programming//a/2167641/292408

eu simplesmente

SET autocommit=0;
SET unique_checks=0;
SET foreign_key_checks=0;

no começo e

COMMIT;
SET unique_checks=1;
SET foreign_key_checks=1;

no fim.

Agora demorou 3 minutos.

(Cortesia de @andreasemer via twitter)


Truques impressionantes. Algo que eu preciso saber: existem efeitos colaterais de fazer isso?
Dharma Saputra

1
Caso seus dados estejam corrompidos, as restrições de chave estrangeira podem não ser atendidas após a importação.
27417 Alex

Ótimo trabalho. Você me salvou literalmente horas.
Jafo

Não acelerou o desempenho para mim. Sem isso, foram 23 minutos e depois foram 23 minutos (arquivo .sql de 3 GB).
Joshua Pinter

5

Complementando o que vejo acima ... Meu arquivo de despejo já é gerado automaticamente por algo como:

mysqldump my_db > db-dump-file.sql

Eu quero automatizar esse importação então eu criei dois arquivos no meu computador chamados default-start-import.sqle default-end-import.sqle os seus conteúdos são default-start-Import.sql :

SET autocommit=0;

e default-end-import.sql :

COMMIT;
SET autocommit=1;

e o script que eu corro é mais ou menos assim;

cat default-start-import.sql db-dump-file.sql default-end-import.sql | mysql my_other_db

mesmo comando, mas mais fácil de ler:

cat default-start-import.sql \
    db-dump-file.sql \
    default-end-import.sql \
| mysql my_other_db

Nesse caso, caté usado para concatenar esses arquivos antes de enviá-los ao canal. Eu acho importante que todos os arquivos terminem com um caractere de nova linha (uma linha vazia no final do arquivo, se vista de um editor de texto), para que o catcomando não mescle linhas entre os arquivos.

A importação funciona bem, não testei se é realmente mais rápido devido a essa melhoria na coisa de habilitar e desabilitar a confirmação automática, mas se isso agiliza as coisas, essas etapas extras facilitam as coisas.


1

Eu tentei --compress, SET autocommit=0;e eles ajudaram uma pequena quantidade no entanto ...

Eu descobri que converter várias INSERT INTO ...instruções em uma declaração grande com várias VALUES(...), (...)velocidades aprimoradas consideravelmente.

Estou usando mysqlSSL sobre WAN. O banco de dados MySQL remoto está hospedado na Amazon.

Com 9 colunas e 2.100 linhas:

  • 2.100 INSERTdeclarações separadas : 82s
  • 2 INSERTdemonstrações consolidadas : <1s

Com 7 colunas e 42.000 linhas:

  • 42.000 INSERTdeclarações separadas : 1.740s
  • 42 INSERTdemonstração consolidada : 105s

Portanto, dependendo da ferramenta que gera o despejo do banco de dados (ou mais especificamente do formato das INSERTinstruções), a velocidade pode ser influenciada.

Nota: Isso também diminui o .sqlarquivo de despejo em mais de 60% nos meus testes, para que ele também economize em E / S.

Aviso: existem limitações físicas para essa técnica commysql e para aqueles que precisam de portabilidade ... O SQL Server parece estar limitado a apenas 1.000 linhas por vez.

Ainda assim, fazer 1.000 linhas por vez para 42.000 linhas ainda gera uma melhoria de 1.657%!

Ao utilizar nosso site, você reconhece que leu e compreendeu nossa Política de Cookies e nossa Política de Privacidade.
Licensed under cc by-sa 3.0 with attribution required.