Komentáře k článku
Django: Databázový model podruhé

V minulém díle jsme se naučili ukládat záznamy do databáze, dnes se je naučíme odtamtud vybírat, upravovat a mazat. Rovněž si ukážeme vazby mezi tabulkami a několik tipů, týkajících se databázového modelu Djanga.
len vs .count() a dalsi drobnosti
Ke zjistovani poctu zaznamu je nevhodne pouzivat funkci len – stahne vsechny zaznamy z DB a spocita je misto toho aby se proste DB zeptala na pocet (SELECT COUNT(*) …) jako do tela metoda .count()
Misto .filter()[0] je lepsi vetsinou pouzit .get(), ma tu vyhodu ze sam hlida ze DB ma vratit prave jeden objekt a neni tak krypticky.
Mozna by take stalo za to zminit lazy vlastnost querysetu a jak se daji querysety za sebou retezit, tedy ze muzu udelat
A ve vysledku se udela jen jeden dotaz do DB. Obecne dotazy do DB se provedou pri iterovani pres queryset, sliceovani ([]) a volani .get ci .count. Specialni pripad je v ramci prace v interaktivnim rezimu, ktery vzdy vola repr() na vracene hodnote aby ho zobrazil uzivateli – repr() u querysetu vyvola iteraci a dotaz se tak provede.
Jinak dekuji za clanky, myslim si, ze je neco takoveho potreba :).
Re: len vs .count() a dalsi drobnosti
Díky za hodnotné připomínky, get jsem tam stručně zmínil, lenost a řetězení taky. S tím countem máte naprostou pravdu, je to efektivnější a neměl jsem o tom ani tušení. Django mě neustále překvapuje novými funkcemi…
Re: len vs .count() a dalsi drobnosti
No, ten count() neni ani tak funkce Djanga, ale vychazi z vlastnosti SQL databaze. Navic tyto ‚nove funkce‘ jsou zminene i v originalni dokumentaci, takze to by Vas prilis prekvapovat nemelo – narazim hlavne na ‚.get()‘ metodu, ktera se od Vami popsanych vyberovych kriterii atributu object lisi jen tim, ze nevraci Queryset, ale primo vlastni objekt.
Re: len vs .count() a dalsi drobnosti
Ano, samozřejmě, databázovou klauzuli COUNT znám, jenom jsem nevěděl, že to má Django implementováno jako zvláštní metodu – příště musím lépe nastudovat manuál. A metodu get jsem tam zmínil a přiložil na ní odkaz, i když jsem ji v rámci zpřehlednění nepoužil, rozhodně s ní však budu pracovat v nějakém dalším díle.
limit
neviete ako django robi limit napr. na DB oracle, alebo inych, ktore pojem limit nepoznaju?
Re: limit
V tomto pripade django ide standardnou cestou cez vlozeny select a rownum, zbytok podobne ako u limit…
Q object?
Kedze sa v clanku v hodnej miere spominaju metody QuerySet, a metoda filter (dokonca viac ako by mala), mozno stalo zato spomenut aj Q object.
Re: Q object?
Máte pravdu, Q objekt je hodně užitečná věc. Bohužel se to sem už nevešlo, databázový model Djanga je natolik komplexní, že by se jenom tomuto tématu dal věnovat celý seriál. Lepší je popsat jeden způsob pořádně než více povrchně.
Zjistovani vygenerovaneho SQL
Ja bych si jenom dovolil doplnit, ze vygenerovane dotazy se do connection.queries ukladaji jenom pokud je v settings.py nastaveno DEBUG = True (a je to mimochodem hlavni duvod, proc si zacatecnici stezuji na memory leak v Djangu).
Pokud chceme zjistit SQL, je jednodussi na QuerySet objektu pouzit .query.as_sql()
store_brno = Store.objects.filter(id=3)[0]
print store_brno.query.as_sql()
Snad to nekomu pomuze.
Jirka
Re: Zjistovani vygenerovaneho SQL
Ehm, v tom prikladu mam samozrejme chybu, protoze store_brno neni QuerySet. Predstavte si, ze na za filter(…) neni ono [0] :-)
Re: Zjistovani vygenerovaneho SQL
Ja jeste doplnim: nespolehejte na tohle. Je to tvar SQL __PRED__ expanzi a escapovanim promennych, casto to ani neni validni SQL. Pokud chcete 100% jistotu, pouzijte query log ve vasi DB.
debug toolbar, performance
Pro měření a inspekci skutečných dotazů je výborný django debug toolbar (http://github.com/…/tree/master), umí třeba zobrazit odkud z kódu queries lezou a další informace. Debug toolbar vyžaduje django >= 1.0.
Jinak pozor na fakt, že čas reportovaný djangem u query je skutečně jenom cena DB query a nepočítá se do toho overhead djanga, který může být klidně jednou tolik, viz následovní screenshot z kcachegrindu:
http://imgur.com/JMHSE.png
Taky šablonovací systém djanga rozhodně nepatří mezi nejrychlejší, i s překompilovanou šablonou to trvá celkem dlouho. Což se dá obejít cachováním a/nebo použitím jiného šablonovacího systému.
Eager loading / N+1 query problem
Zdravim,
zaujimalo by ma ako v django orm riesit eager loading, resp. N+1 query problem. select_related() pouzivam, ale potreboval by som to opacne. (Presiel som na django z Rails, kde to bola bezna vec). Vdaka :)
Jozef
Re: Eager loading / N+1 query problem
RE opačně:
To jako že chceš zjistit, které záznamy v jedné tabulce mají foreign-key na nějakou hodnotu v druhé?
Navím jak to řeší Rails, ale předpokládám že na to pod kapotou používají některý z joinů.
Zkus mrknout sem http://www.djangoproject.com/…many_to_one/, třeba ti to pomůže.
order_by syntax
Diky za clanok, mam otazku:
>>> Store.objects.exclude(city=‚Brno‘).filter(id__gt=0, id__lt=10).order_by(‚-city‘)
specificky mi nie je jasne:order_by(‚-city‘)
Preco je tam znamienko ‚-‘ ? Videl som to uz aj v off. dokumentacii/tutorialoch,
ale nikde som nenasiel vysvetlenie preco to znamienko tam je ?
Diky
Re: order_by syntax
„Když potřebujeme položky seřadit obráceně, napíšeme znak mínus před název atributu.“
Tedy jedná se o řazení sestupně, ne vzestupně (od největšího po nejmenší, ne naopak).
Re: order_by syntax
Som idiot, ta poznamka v clanku mi fakt unikla.
Diky a prajem hodne zdaru pri dalsich castiach serialu.
Kounicova 15?
Ahoj, diky za skveli serial, btw Kounicova 15?