Estou carregando um arquivo de 100 GB via LOAD DATA INFILE. Eu tive um bom sucesso com o MyISAM, algumas horas e pronto.
Estou tentando agora usando o InnoDB. O carregamento começa rapidamente em mais de 10 MB / s (observando o crescimento do arquivo da tabela, file_per_table
está ativado).
Mas, após cerca de 5 GB de dados, ele diminui para o intervalo de 2-4 MB / s, enquanto eu tenho mais de 20 GB, ele cai em torno de 2 MB / s.
O tamanho do buffer pool do InnoDB é 8G. E eu fiz o seguinte antes de executar o comando LOAD DATA INFILE:
SET @@session.sql_log_bin=0;
SET autocommit=0;
SET unique_checks=0;
SET foreign_key_checks=0;
alter table item_load disable keys;
//Run LOAD DATA INFILE....
Não vejo a razão pela qual está começando bem e diminuindo com o tempo.
Além disso, usando as mesmas configurações, executei o mesmo comando LOAD DATA INFILE com a tabela usando o InnoDB e o MyISAM e um conjunto de dados de teste de 5 GB, o MyISAM foi 20x mais rápido:
InnoDB:
mysql> LOAD DATA CONCURRENT LOCAL INFILE '/tmp/item' REPLACE INTO TABLE item_load;
Query OK, 2630886 rows affected, 6 warnings (21 min 25.38 sec)
Records: 2630886 Deleted: 0 Skipped: 0 Warnings: 6
MyISAM:
mysql> LOAD DATA CONCURRENT LOCAL INFILE '/tmp/item' REPLACE INTO TABLE item_load;
Query OK, 2630886 rows affected, 6 warnings (1 min 2.52 sec)
Records: 2630886 Deleted: 0 Skipped: 0 Warnings: 6
Mais alguma coisa que eu deva considerar tentar? O mecanismo MyISAM é capaz de manter a taxa de carga muito melhor.
Detalhes adicionais:
Eu tentei carregar os arquivos individualmente, não há diferença.
Aliás, tenho 150 arquivos de 500 MB cada, em cada arquivo as chaves são classificadas.
Após receber 40 GB da noite para o dia, 12 horas depois, a taxa de carregamento caiu para 0,5 MB / s, o que significa que a operação é, praticamente falando, impossível.
Não encontrei outras respostas para perguntas semelhantes em outros fóruns, parece-me que o InnoDB não suporta o carregamento de grandes quantidades de dados em tabelas com mais de alguns GB de tamanho.
fonte
A resposta final para esta pergunta foi não usar o InnoDB para uma tabela de referência massiva. O MyISAM está gritando rápido, quase com a taxa de transferência máxima da velocidade do disco para toda a carga, o InnoDB atola. MyISAM é simples, mas neste caso também são os requisitos desta tabela. Para uma tabela de referência simples com cargas em massa sobre LOAD DATA INFILE, o MyISAM é o caminho a percorrer, até agora tudo bem.
Mas observe que, se você executar as tabelas MyISAM e InnoDB, precisará considerar a alocação de memória para 2 mecanismos de armazenamento em cache, cada mecanismo possui seu próprio cache exclusivo, que precisa de alocação de memória separada.
fonte
Você pode tentar dividir seus arquivos de entrada em pedaços menores.
Eu pessoalmente uso http://www.percona.com/doc/percona-toolkit/2.1/pt-fifo-split.html para isso.
O que acontece se você obtiver um bloqueio de tabela durante a importação? Talvez o bloqueio no nível de linha do InnoDB o retarde (o MyISAM usa um bloqueio de tabela).
Você também pode ler aqui para obter mais ideias: http://derwiki.tumblr.com/post/24490758395/loading-half-a-billion-rows-into-mysql
fonte
Se o seu PK não for AUTO_INCREMENT ou os dados no arquivo csv não estiverem classificados no PK, isso poderá estar afetando o desempenho do carregamento de dados. Como a tabela no MySQL é um índice, portanto, todos os dados são armazenados em ordem classificada, se o valor PK não estiver em AUTO_INCREMENT, o MySQL precisará fazer muita troca de dados para obter os dados armazenados em ordem classificada. Esse é o motivo do carregamento mais lento de dados quando o tamanho da tabela começa a aumentar.
Estou carregando um arquivo csv de 91GB com PK em AUTO_INCREMENT usando LOAD DATA INFILE e não vejo nenhuma queda na taxa de transferência. Estou recebendo inserções de 140 a 145 mil por segundo. Usando o Percona MySQL 5.6.38
fonte