Hlavní navigace

Django - Optimalizace SQL dotazů

19. 7. 2009 0:01 (aktualizováno) | Tomáš Ehrlich

Už jsem chtěl nadávat na způsob, jakým Django pracuje s relací 1:N, naštěstí to byl klasický RTFM problém.

Django debug toolbar umožňuje (krom dalších věcí) sledovat SQL dotazy, které framework poslal do databáze, jejich četnost i časovou náročnost, s jeho pomocí jsem tedy zjistil, že něco není v pořádku, když jsem ve výpisu viděl 4 duplicitní dotazy.

Vytvořil jsem jednoduchý modul news pro publikování krátkých zpráv (uživatel, titulek, obsah, datum). Implementoval jsem ho jako jednoduchý blog a s hrůzou zjistil, kolik SQL dotazů se musí vykonat, aby se zobrazil seznam příspěvků.

Problém 1: Používat RequestContext pouze jednou

Každé vytvoření instance třídy RequestContext následuje řada operací a databázových volaní v závislosti na použitých ContextProcessors. Processor Auth vyhledá informace o aktuálním uživateli, jeho zprávách a právech. Pro superuživatele 2 dotazy, pro běžného tuším tři.
Už samotné vytváření více instancí je naprostá blbost a programátorova neschopnost předávat funkcím context místo requestu, takže to nebudu dál rozebírat :)

Problém 2: Používat select_related() pokud dopředu víme, že s cizím klíčem budeme pracovat

select_related() způsobí, že data ze souvisejících tabulek jsou rovnou připojena JOINem, jinak je pro ně zavolán samostatný dotaz. Tento problém byl pro změnu způsobený programátorovou neschopností přecíst si pořádně manuál, takže to taky nebudu dál rozebírat :)

Tak i tak, odstranění těchto dvou problémů dost výrazně urychlilo práci s DB, takže pokud je někdo stejná trubka jako já, snad mu to urychlí hledání problému.