Přejít k navigační liště

Zdroják » Databáze » Kompletní průvodce po CouchDB – V – Návrhové dokumenty

Kompletní průvodce po CouchDB – V – Návrhové dokumenty

Články Databáze

Na databázi CouchDB je velmi zajímavá možnost hostování kompletní webové aplikace (CouchApp). CouchDB dokáže fungovat jako WWW server a zastat tak práci databáze, serveru i dynamického jazyka. Základem pro tyto funkce jsou návrhové dokumenty (design documents), které obsahují potřebnou aplikační logiku.

Nálepky:

Návrhové dokumenty

Návrhové dokumenty jsou speciálním typem dokumentů v CouchDB, které obsahují aplikační kód. Protože běží v prostřední databáze, je API aplikace vysoce strukturované. V předchozích kapitolách jsme si už ukazovali pohledy a další funkce; v této části se podíváme na funkční API a ukážeme si, jaký mají funkce v návrhovém dokumentu vztah k aplikaci.

Tato část knihy (Part II, “Developing with CouchDB”, kapitoly Chapter 5, Návrhové dokumenty Chapter 9, Transformace pohledů s funkcemi pro seznamy) tvoří základ pro Část III, “Ukázková aplikace”, ve které vše, co se teď budeme učit, dáme dohromady a ukážeme si jednoduchou blogovací aplikaci, na níž demonstrujeme princip vytváření CouchDB aplikací. Aplikace se jmenuje Sofa a příležitostně na ni budeme odkazovat už v této části. Pokud vám tedy nebude jasné, o čem je řeč, nebojte se, pochopíte to ve třetí části.

Modelování dokumentů

Zatím máme zkušenosti s dvěma druhy dokumentů. První druh připomíná něco, co ukládá textový procesor, nebo třeba uživatelský profil. S tímto typem dat můžete denormalizovat jak jen to jde. V podstatě jde o to, abyste byli schopni načíst celý dokument jedním požadavkem, a pak z něj získali něco, co dává smysl zobrazit.

Existuje technika pro vytváření „virtuálních“ dokumentů, kde pomocí pohledů sdružujete data z různých dokumentů. Můžete je použít např. k tomu, abyste si uložili všechny atributy z každého uživatelského profilu do samostatného dokumentu, ale to nedoporučujeme. Virtuální dokumenty jsou užitečné v případě, že dávají dohromady výsledky práce různých autorů; například v naší ukázce blogovacího systému to je článek a k němu komentáře – jako jediný „virtuální“ dokument. Článek  “CouchDB Joins,” (Christopher Lenz) vysvětluje tento princip detailněji.

Idea virtuálních dokumentů nás přivádí k dalšímu druhu dokumentů – záznamům o událostech (event log). Použijte je v případě, kdy nelze uživatelskému vstupu věřit, nebo když potřebujete spouštět nějakou asynchronní činnost. Logy uchovávají uživatelské akce jako „události“ a při zápisu do nich není zapotřebí provádět složitá ověřování. Až při čtení můžete zkontrolovat všechna komplexní omezení, jak jste zvyklí z relačních DB.

Můžete nahlížet na dokumenty jako na stavové automaty, kde vnitřní stav ovlivňuje uživatelský vstup a automatické zpracování dat na pozadí. Můžete použít pohled „podle stavu“ k tomu, abyste si vyzvedli relevantní dokumenty – změna vnitřního stavu je dostane „do pohledu“.

Tento přístup je taky použitelný pro logování, hlavně v kombinaci s  batch=ok může CouchDB fungovat jako velmi rychlé úložiště logů, a pohledy jsou pak skvělým nástrojem pro hledání věcí jako např. průměrný čas odezvy systému nebo podezřele vysoce aktivní uživatelé.

Query Server

Základní dotazový server (query server – SW balík, který provádí funkce z návrhového dokumentu) je v CouchDB napsán v JavaScriptu, ale existují dostupné servery pro nejrůznější jazyky. Implementace v novém jazyku je záležitostí zpracování JSON příkazů jednoduchým programem.

V této části si projdeme funkcionalitu jako jsou MapReduce pohledy, kontrola při updatu a transformace pomocí show a list.Rovněž si stručně popíšeme plánované novinky (dnes už některé z nich pravděpodobně v nových verzích fungují, pozn. překl.) jako replikační filtry, ovladače pro parsování vstupu v neJSON formátech nebo ovladač rewrite, který umožňuje použít hezčí URL. Protože je CouchDB open source, nelze říct přesně, kdy se která novinka objeví, ale doufáme, že v době, kdy o tom budete číst, budou už tyto funkce implementované. V textu na takové funkce vždy výslovně upozorníme.

Aplikace jsou dokumenty

CouchDB je navržena tak, že nejlépe pracuje v situacích, kdy aplikace odpovídá 1:1 návrhovému dokumentu.

Návrhový dokument je dokument CouchDB, jehož  id začíná řetězcem _design/. Kupříkladu ukázková blogovací aplikace Sofa je uložena v návrhovém dokumentu s ID _design/sofa (viz obrázek). Návrhové dokumenty jsou stejné jako ostatní dokumenty v CouchDB – replikují se mezi servery a jsou vnitřně verzované pomocí parametru  rev.

Návrhové dokumenty jsou tedy úplně obyčejné dokumenty, které mají pouze tu zvláštnost, že jejich ID začíná na  _design/.

CouchDB hledá pohledy a další funkce právě zde. Statické HTML stránky, které chceme poslat uživateli, jsou uložené jako přílohy u návrhového dokumentu. Pohledy a kontrolní funkce nejsou uloženy v přílohách, namísto toho jsou přímo součástí JSON dat v dokumentu.

Obr. 1 Anatomie návrhového dokumentu

CouchDB ukládá MapReduce dotazy do pole views. Tímto způsobem je Futon zobrazuje a dovoluje je upravovat. Indexy pro pohledy si databáze vytváří „per návrhový dokument“, a to podle hashe textu příslušných funkcí. To znamená, že přidáte-li přílohy nebo jiné funkce do návrhového dokumentu, nebudou indexy počítány znovu. Když ale změníte zápis map nebo reduce funkce, bude index smazán a bude se vytvářet znovu.

CouchDB dokáže výsledek vracet i v jiném formátu než JSON. Návrhový dokument obsahuje pole show a list, v nichž mohou být funkce, které transformují JSON do HTML, XML a dalších typů. Tak lze třeba posílat Atom feedy bez potřeby nějakého middleware. Funkce show a list jsou něco jako „akce“ v klasických webových frameworcích – spustí nějaký kód na základě požadavku a vykreslí odpověď. Ve skutečnosti se od pohledů liší jednou důležitou věcí, a to že nesmí mít vedlejší efekty na data. Tedy jsou omezeny pouze na požadavky typu GET, což na druhou stranu znamená, že jejich výsledky mohou být cachované v HTTP proxy serverech.

Upgrade aplikace může být jednoduše zařízená pomocí CouchDB replikace, protože veškerá aplikační logika je uložena v jednom dokumentu. To zároveň umožňuje, aby jeden server obsluhoval více aplikací. Redakční rozhraní pro editora deníku bude jiné než to, co dostanou čtenáři, ale data zůstávají stejná. Můžete tedy napsat jak adminské, tak čtenářské rozhraní, obojí poběží v téže databázi, nad stejnými daty, jen každé v jiném návrhovém dokumentu.

Databáze CouchDB může obsahovat mnoho návrhových dokumentů. Příklady jejich ID:

_design/calendar
_design/contacts
_design/blog
_design/admin

Ve struktuře URL u databáze CouchDB můžete poslat požadavek GET a získat tak návrhový dokument jako JSON z adres jako:

http://localhost:5984/mydb/_design/calendar
http://127.0.0.1:5984/mydb/_design/contacts
http://127.0.0.1:5984/mydb/_design/blog
http://127.0.0.1:5984/mydb/_design/admin

Na tomto příkladu vidíte jednu výjimku, kterou mají návrhové dokumenty – jsou to jediné dokumenty, u nichž se případné lomítko v názvu nepřekládá na %2F. U všech ostatních dokumentů je potřeba lomítko správně „escapovat“. Například dokument s DocID movies/jaws se objeví v URL jako:  http://127.0.0.1:5984/mydb/movies%2Fjaws.

Ukážeme si první „iteraci“ ukázkové aplikace bez  show a list, protože se naučíme práci s JSON API pomocí AJAXových dotazů. V druhé iteraci upravíme náš blog tak, abychom se obešli bez funkcionality na straně klienta. Prozatím ale zůstaneme u AJAXu, který nám ukáže mnohem názorněji, jak JSON/HTTP API funguje. JSON je částí JavaScriptu, takže pracovat s ním v JavaScriptu je snadné, ušetříme si případné zmatky, a o práci s HTTP se postará objekt XHR.

Databáze CouchDB používá funkci validate_doc_update k tomu, aby zabránila neplatným nebo neautorizovaným změnám dat. Používáme ji v ukázce k tomu, abychom se ujistili, že blogposty mohou být poslány pouze přihlášeným uživatelem. Ověřovací funkce rovněž nesmí mít žádné postranní efekty; na druhou stranu dokáže zabránit nejen změnám od uživatelů, ale i změnám „z replikace“. Tento efekt probereme později v části Part III, “Example Application”.

Obrázky, JavaScript, CSS a HTML, které blogovací aplikace Sofa potřebuje, jsou uložené v poli _attachments, které ukazuje pouze metadata souborů namísto plného obsahu (o této vlastnosti jsme mluvili už v předchozích dílech). Přílohy mohou být u všech dokumentů, nejen u návrhových, takže má návrhář v tomto směru poměrně dost svobody. Pokud jsou některé soubory nezbytné k běhu aplikace, měly by být přílohou návrhového dokumentu. Takový přístup umožní novému uživateli, aby spustil vaši aplikaci nad prázdnou databází.

Další pole návrhového dokumentu, které vidíte na obrázku (a které budeme používat), používá CouchApp při uploadu (více informací o CouchApp naleznete v Chapter 10, Standalone Applications). Pole signatures umožňuje ušetřit si upload souborů, které se nezměnily – stačí porovnat hashe. Pole lib slouží k uchování dalších JavaScriptů a JSON. Blíže si vysvětlíme CouchApp v dalších kapitolách.

Základní návrhový dokument

V dalším oddíle si ukážeme pokročilé metody pro práci s návrhovým dokumentem, ale nejprve se podíváme na to, jak takový dokument vypadá. Definujeme si jeden pohled, ale bude to dostatečné k tomu, abyste viděli, jak se dělají stejné návrhové dokumenty i pro velké aplikace.

Nejprve si vytvořte následující text jako textový soubor se jménem  mydesign.json:

{
  "_id" : "_design/example",
  "views" : {
    "foo" : {
      "map" : "function(doc){ emit(doc._id, doc._rev)}"
    }
  }
}

Teď použijte curl a metodu PUT k nahrání souboru do databáze (nejprve si databázi vytvoříme):

curl -X PUT http://127.0.0.1:5984/basic
curl -X PUT http://127.0.0.1:5984/basic/_design/example -d @mydesign.json

U druhého požadavku by měl být výsledek zhruba takovýto:

{"ok":true,"id":"_design/example","rev":"1-230141dfa7e07c3dbfef0789bf11773a"}

Nyní se můžeme dotazovat pohledu, který jsme vytvořili, ale nejprve je potřeba mít nějaké dokumenty. Spusťte párkrát následující příkaz, kterým se vytvoří prázdné dokumenty:

curl -X POST http://127.0.0.1:5984/basic -d '{}'

A teď se zeptáme pohledu:

curl http://127.0.0.1:5984/basic/_design/example/_view/foo

Výsledkem by měl být seznam všech dokumentů v databázi (s výjimkou návrhového dokumentu). Vytvořili jsme a použili jsme náš první návrhový dokument!

Pohled do budoucnosti

Existují i další funkce pro návrhové dokumenty, které byly představeny v době, kdy tento text vznikal, jako  _update nebo _filter, které teď nebudeme popisovat do hloubky. Bude se jim věnovat kapitola 20, Change Notifications. Představte si webovou službu, která posílá POSTem nějaká XML data na URL, co zadáte, vždy, když dojde k nějaké události. Příklad je třeba platba přes PayPal. S ovladačem _update můžete posílat tyto POSTy přímo do CouchDB, kde je XML převedeno na JSON dokument a ten je uložen. Totéž můžete dělat s CSV, multi-part formuláři a dalšími formáty.

V širším měřítku jde o cosi jako aplikační server, s jednou základní odlišností. Místo toho, abychom nechali vývojáře dělat co chtějí (procházet si seznamy DocID a dělat nad nimi nějaké operace, a dělat operace nad výsledky těchto operací), definujeme sadu „bezpečných“ transformací, jako pohled (view), show, list a update. Slovem „bezpečné“ máme na mysli to, že mají dobře známou charakteristiku výkonnosti a že zapadají do architektury CouchDB.

Naším cílem je nabídnout způsob, jak psát standalone aplikace, co mohou být snadno indexovány vyhledávačem nebo použité čtečkou. Tedy takové, které používají „staré dobré prosté HTML“. Můžete k tomu krásně použít i JavaScript (kromě těch případů, kde jej použít nemůžete). Pokud použijete HTML, dostanete z CouchDB cosi, k čemu mohou přistupovat přímo uživatelé webové aplikace.

Tento text je součástí překladu knihy CouchDB: The Definitive Guide. Stejně jako autoři originálu oceníme věcné připomínky a pomoc s textem, za které předem děkujeme.

Komentáře

Subscribe
Upozornit na
guest
0 Komentářů
Inline Feedbacks
View all comments

Enum a statická analýza kódu

Mám jednu univerzální radu pro začínající programátorty. V učení sice neexistují rychlé zkratky, ovšem tuhle radu můžete snadno začít používat a zrychlit tak tempo učení. Tou tajemnou ingrediencí je statická analýza kódu. Ukážeme si to na příkladu enum.