sql >> Databáze >  >> NoSQL >> MongoDB

Je možné zlepšit rychlost Mongoexportu?

Existuje mnoho faktorů, které omezují exportní výkon.

  • Velikost dat je relativně velká v porovnání s dostupnou pamětí:~2 TB oproti ~5 GB mezipaměti WiredTiger (pokud je nastavena jako výchozí). To je:
    • Celá mezipaměť WiredTiger může obsahovat pouze přinejlepším ~0,22 % kolekce, ve skutečnosti je to velmi pravděpodobně mnohem méně, protože mezipaměť by obsahovala data z jiných kolekcí a indexů.
    • To znamená, že WiredTiger potřebuje načítat z disku velmi často a přitom vymazat aktuální obsah mezipaměti. Pokud je sada replik aktivně používána, znamenalo by to vyřazení „špinavých“ dat z mezipaměti a jejich uložení na disk, což by nějakou dobu trvalo.
    • Upozorňujeme, že dokumenty v mezipaměti WiredTiger nejsou komprimovány.
  • Sbírka obsahuje velké dokumenty, z nichž potřebujete pouze jednu část. To znamená, že zpracování dokumentů vyžaduje více času.
  • Kolekce je komprimována pomocí zlib, což znamená, že k rozbalení dokumentů je třeba využít více času.
  • Předvolba čtení je secondaryPreferred , což znamená, že se pokusí číst ze sekundárního. Pokud se do sady replik aktivně zapisuje, operace aplikace oplog na sekundární zablokují čtečky. Tím se prodlouží další zpoždění.

Jedním z možných vylepšení je, že pokud se jedná o operaci, kterou provádíte často, vytvořte index v příslušných polích a exportujte jej pomocí krytý dotaz by mohl zlepšit výkon, protože index by byl menší než úplné dokumenty.

Upravit:Spuštění mongoexport paralelně může být užitečné v tomto případě:

Kromě poskytnutých dodatečných informací jsem provedl test, který, jak se zdá, tento problém poněkud zmírňuje.

Zdá se, že běží mongoexport paralelně, kde každý mongoexport zpracování podmnožiny kolekce může urychlit export.

Chcete-li to provést, rozdělte _id jmenný prostor odpovídající číslu mongoexport proces, který plánujete spustit.

Pokud mám například 200 000 dokumentů počínaje _id:0 na _id:199,999 a pomocí 2 mongoexport procesy:

mongoexport -q '{"_id":{"$gte":0, "$lt":100000}}' -d test -c test > out1.json &
mongoexport -q '{"_id":{"$gte":100000, "$lt":200000}}' -d test -c test > out2.json &

kde ve výše uvedeném příkladu jsou dva mongoexport každý proces zpracovává jednu polovinu kolekce.

Při testování tohoto pracovního postupu s 1 procesem, 2 procesy, 4 procesy a 8 procesy jsem dospěl k následujícímu načasování:

Použití 1 procesu:

real    0m32.720s
user    0m33.900s
sys 0m0.540s

2 procesy:

real    0m16.528s
user    0m17.068s
sys 0m0.300s

4 procesy:

real    0m8.441s
user    0m8.644s
sys 0m0.140s

8 procesů:

real    0m5.069s
user    0m4.520s
sys 0m0.364s

V závislosti na dostupných zdrojích spuštění 8 mongoexport Zdá se, že paralelní procesy urychlují proces o faktor ~6. Toto bylo testováno na stroji s 8 jádry.

Poznámka :Halferova odpověď je myšlenkově podobná, i když se tato odpověď v podstatě snaží zjistit, zda má volání mongoexport nějakou výhodu paralelně.



  1. Operátor $arrayElemAt v agregaci s Mongo <3.2

  2. MongoDB $in Query Operator

  3. Jedna publikace skrývá vnořená pole z jiné publikace

  4. Nakonfigurujte Mongo pomocí mongodb+srv