2012-01-09 7 views
10

Próbuję załadować zbiorcze około 12-metrowe rekordy do tabeli InnoDB w (lokalnym) mysql przy użyciu LOAD DATA INFILE (z CSV) i stwierdzenie, że ukończenie zajmuje bardzo dużo czasu.poprawa wydajności pliku danych obciążenia mysql

Podstawowym typem klucza jest UUID, a klucze są nieposortowane w plikach danych.

mam podzielić plik danych do plików zawierających 100000 rekordy i zaimportować go jako:

mysql -e 'ALTER TABLE customer DISABLE KEYS;' 
for file in *.csv 
    mysql -e "SET sql_log_bin=0;SET FOREIGN_KEY_CHECKS=0; SET UNIQUE_CHECKS=0; 
    SET AUTOCOMMIT=0;LOAD DATA INFILE '${file}' INTO TABLE table 
    FIELDS TERMINATED BY ',' LINES TERMINATED BY '\n'; COMMIT" 

to działa dobrze przez pierwsze kilkaset tysięcy rekordów, ale wtedy czas wkładka dla każdego kolejnego ładunku wydaje się utrzymać rośnie (od około 7 sekund do około 2 minut na obciążenia przed Zabiłem ją.)

biegnę na maszynie z 8 GB pamięci RAM, a ustawione parametry InnoDB do:

innodb_buffer_pool_size =1024M 
innodb_additional_mem_pool_size =512M 
innodb_log_file_size = 256M 
innodb_log_buffer_size = 256M 

Próbowałem też załadować pojedynczy plik CSV zawierający wszystkie wiersze bez powodzenia - to trwało ponad 2 godziny, zanim je zabiłem.

Czy jest coś jeszcze, co mogłoby przyspieszyć ten proces, ponieważ wydaje się, że jest to zbyt długi czas na załadowanie tylko 12-metrowych rekordów?

+0

[WYŁĄCZ KLAWISI nie działa w InnoDB] (http://serverfault.com/questions/291100/with-mysql-how-long-does-an-alter-table-disable-keys-statement- ostatnie), odpowiedzi na temat zrzucania i dodawania indeksów wtórnych są dobre. – KCD

+0

Nie można wyłączyć "KLUCZA PODSTAWOWEGO". Lub, jeśli możesz, "naprawa" będzie kosztować strasznie długo. –

Odpowiedz

2

Zawsze ciężko powiedzieć, co jest przyczyną problemów z wydajnością, ale są to moje 2 centy: Klucz, który jest uuid, jest losowo rozdzielany, co utrudnia utrzymanie indeksu. Powodem jest to, że klucze są przechowywane przez zakres w bloku systemu plików, więc dzięki temu, że przypadkowe uuidy podążają za sobą, system operacyjny odczytuje i zapisuje bloki w systemie plików bez korzystania z pamięci podręcznej. Nie wiem, czy możesz zmienić klucz, ale możesz też posortować uuidy w pliku wejściowym i zobaczyć, czy to pomaga. FYI, aby lepiej zrozumieć ten problem, przyjrzałbym się tej blog post i może przeczytałem tę książkę mysql high performance ma ładny rozdział o indeksie klastrowym innodb. Powodzenia!

+0

Tak, wydaje się, że klucz podstawowy oparty na UUID powodował większość problemów - zmiana go w pliku danych na coś, co jest po prostu posortowaną sekwencją ciągów, przyspieszyła o około 6. – Michael

+0

"Innodb_buffer_pool_size = 5G" również pomogłoby. –

+0

Więcej dyskusji na temat [zła indeksowania UUIDs_] (https://mariadb.com/kb/en/guiduuid-performance/). Obejmuje obejście _if_, które jest "typem 1". –

7

Jeśli wiesz, że zna dane "", możesz usunąć indeksy z zajętych tabel przed ich zaimportowaniem, a następnie dodać je ponownie po zakończeniu importu.

W przeciwnym razie każdy rekord powoduje indeksowanie, a jeśli masz kilka indeksów, może to spowolnić proces.

+0

W tym przypadku nie pomoże, ponieważ indeks naruszający jest kluczem podstawowym. W przypadku innodb klucz podstawowy jest zaimplementowany jako indeks klastrowy, który przechowuje dane i główny indeks klucza w tej samej strukturze. –

+0

Ponieważ OP nie wskazywał, i ogólnie dobrze jest mieć alternatywne indeksy w dowolnej tabeli, która przechowuje nietrywialne informacje (i dużo tego), założyłem, że istnieją inne indeksy obecne. Upuszczenie tych dodatkowych indeksów _ pomogłoby zwiększyć prędkość wstawiania, ponieważ będzie musiało wykonać __newicz_ obliczeń. Zgadzam się, że indeks klucza głównego również może powodować problemy, ale usunięcie indeksów nadal przyspieszy wstawienie. – cdeszaq

+0

Sądzę, że masz rację, jeśli są zaangażowane inne indeksy. –

Powiązane problemy