Lekce 2 - CMS v Nette a Doctrine 2 - Kostra aplikace
V minulé lekci, Úvod do Doctrine 2 v Nette frameworku, jsme si představili potřebné technologie.
V dnešním Nette tutoriálu si pomocí Composeru stáhneme všechny důležité knihovny a vytvoříme základní kostru naší aplikace.
Založení projektu
Získání potřebných knihoven
K získání knihoven použijeme Composer. Veškeré důležité informace naleznete na oficiálním webu https://getcomposer.org.
Composer využívá souboru composer.json, ve kterém je uvedeno jaké všechny knihovny mají v aplikaci být. Můžeme pak pomocí příkazového řádku všechny knihovny stáhnout.
Poté, co Composer nainstalujete, v příkazovém řádku zadejte cestu ke složce, kde chcete mít náš projekt, např.:
cd xampp/htdocs/nette_doctrine
a napište:
composer create-project nette/sandbox nazev_projektu
composer.json
Předchozím příkazem se nám stáhne sandbox Nette s adresářovou
strukturou. Automaticky se také vytvořil soubor composer.json. Ten otevřete a
do parametru require
přidejte:
... "doctrine/orm": "*", "kdyby/annotations": "^2.2", "kdyby/console": "^2.4", "kdyby/events": "^2.4", "kdyby/doctrine-cache": "^2.4", "kdyby/doctrine": "~2.3.1", "symfony/config": "~2.7", "symfony/translation": "~2.7", "kdyby/translation": "~2.2" ...
Tímto určíme, aby se nám stáhly všechny potřebné knihovny pro náš projekt. Nakonec v příkazovém řádku zadejte cestu ke složce, kde je soubor composer.json, a napište:
composer update
Tímto Composer projede soubor, zjistí, které knihovny jsou nové nebo
upravené, a provede aktualizaci. Všechny knihovny stahuje do složky
vendor/
.
Pokud budeme chtít v průběhu stahovat další knihovny, nemusíme ručně upravovat soubor, stačí v příkazovém řádku napsat příkaz
composer require nazev/knihovny
např.:
composer require kdyby/translation
Jelikož jsme stáhli sandbox nette, máme adresářovou strukturu vytvořenou automaticky.
Poznámka: Zkoušel jsem to pouze na Windows, na Linuxu bude zřejmě trochu jiný postup. Vše je ale na oficiálních stránkách Composeru vysvětleno.
Konfigurace
app/config/config.local.neon
V našem lokálním konfiguračním souboru config.local.neon
změníme informace o naší databázi pro Doctrine:
parameters: doctrine: user: root password: **** dbname: doctrine metadata: App: %appDir%
Přihlašovací jméno a heslo si samozřejmě nastavte podle sebe.
Metadata (informace o entitách atp.) bude Doctrine hledat v naší složce
app/
.
app/config/config.neon
Do hlavního konfiguračního souboru config.neon poté zaregistrujeme všechna naše rozšíření:
... extensions: console: Kdyby\Console\DI\ConsoleExtension events: Kdyby\Events\DI\EventsExtension annotations: Kdyby\Annotations\DI\AnnotationsExtension doctrine: Kdyby\Doctrine\DI\OrmExtension translation: Kdyby\Translation\DI\TranslationExtension
A na závěr si připravíme možnost překladů a povolíme češtinu a angličtinu (defaultně bude použita čeština).
... translation: default: cs fallback: [cs, en] whitelist: [cs, en]
Úprava routeru
app/router/RouterFactory.php
Abychom mohli rozpoznat, v jakém jazyce chce uživatel stránky zobrazit, přidáme do masky routeru nepovinný parametr locale.
<?php namespace App; use Nette; use Nette\Application\IRouter; use Nette\Application\Routers\Route; use Nette\Application\Routers\RouteList; /** * Routovací továrnička. * Řídí routování v celé aplikaci. * @package App */ class RouterFactory { /** * Vytváří router pro aplikaci. * @return IRouter výsledný router pro aplikaci */ public static function createRouter() { $router = new RouteList(); $router[] = new Route("[<locale=cs cs|en>/]<presenter>/<action>[/<id>]", "Homepage:default"); return $router; } }
Pomocí hranatých závorek jsme určili, že parametr locale
není povinný a pokud nebude v URL vyplněn, použije se defaultně
čeština.
Naše URL poté mohou vypadat např.
en/article-category/list
.
Způsob překladu
Všechny texty, které se budou překládat, budou uloženy pod klíčem v NEON souboru (stejný používá i konfigurační soubor). Jak to funguje, si můžete zkusit zde: http://ne-on.org.
Překlady budeme psát do jednotlivých souborů podle toho, kam dané texty
spadají (texty ohledně článků budou v souborech article, pro formuláře v
souborech form, pro výjimky exception, obecné texty common apod.).
Kdyby\Translation
se poté automaticky postará o načtení všech
důležitých souborů. Způsob rozdělení je tedy na nás, jak se nám to zdá
přehledné (přiznávám, že nakonec stejně budou texty různě
poházeny).
Výhodou tohoto nástroje také je, že můžeme překládat i texty s proměnlivým obsahem - jednoduše napíšeme zástupný identifikátor, který se poté přepíše hodnotou, např.:
textKey: "Celkem je zde %articlesCount% článků a %usersCount% aktivních uživatelů"
V šabloně poté hodnoty dosadíme pomocí pole.
{_textKey, ["articlesCount" => 500, "usersCount" => 30]} // vypíše Celkem je zde 500 článků a 30 aktivních uživatelů
Překlad již na úrovni vrstvy Presenteru obstarává třída
Kdyby\Translation\Translator
. Tu si automaticky injectujeme do
třídy BasePresenter
a také se bude předávat konstruktorem do
form factory tříd.
app/presenters/BasePresenter.php
Konečně se dostáváme k troše akce. Jako první si upravíme náš BasePresenter a vytvoříme mu atribut locale a Translator, který se automaticky injectuje. Nezapomínejte, že všechny atributy, které se injectují automaticky, musí mít viditelnost public.
<?php namespace App\Presenters; use App\Model; use Nette; use Nette\Application\UI\Presenter; /** * Základní presenter pro všechny ostatní presentery aplikace. * @package App\Presenters */ abstract class BasePresenter extends Presenter { /** @persistent null|string Určuje jazykovou verzi webu. */ public $locale; /** * @var \Kdyby\Translation\Translator Obstarává jazykový překlad na úrovni presenteru. * @inject */ public $translator; }
Atribut $locale obsahuje informaci o jazyku. Díky anotaci @persistent je hodnota automaticky předávána při každém požadavku - nemusíme ji proto uvádět v odkazech.
Makro na překlad
Dále si ještě do třídy BasePresenter
zaregistrujeme makro
na překlad:
... /** * Registrace makra na překlad. * @inheritdoc */ protected function createTemplate() { /** @var Template $template Latte šablona pro aktuální presenter. */ $template = parent::createTemplate(); $this->translator->createTemplateHelpers() ->register($template->getLatte()); return $template; }
Tímto zaregistrujeme makro {_}
, díky kterému lze v šabloně
jednoduše přeložit text, a nemusíme tak překlady ukládat do proměnných a
předávat šablonám.
Databázová struktura
Abychom nemuseli v každém dalším článku něco přidávat nebo
upravovat, přiložím rovnou soubor db.sql
s SQL příkazem,
který celou databázi vytvoří.
Databáze obsahuje pět tabulek:
- article
- article_category
- article_comment
- user
- user_settings
Do databáze budou automaticky přidání dva uživatelé:
Jméno | Heslo | Popis |
---|---|---|
admin | admin | administrátor |
user | user | uživatel |
Poznámka: Doctrine umí z entit vygenerovat strukturu databáze a opačně. Více se dozvíte zde.
Přebytečné soubory v Nette sandboxu
model/UserManager.php
- tento soubor z projektu úplně odstraňte - nejen, že nám k ničemu nebude, ale naopak by nám překážel (kvůli implementaci rozhraníNette\Security\IAuthenticator
). Také ho odstraňte ze souboru config.neon.forms/SignFormFactory.php
- můžete odstranit, my si budeme vytvářet náš vlastní, trochu odlišný.presenters/SignPresenter.php
- také si budeme vytvářet vlastní.
Tímto tuto lekci zakončíme.
V lekci příští, CMS v Nette a Doctrine 2 - Modely a Layout, začneme pomalu stavět naši modelovou vrstvu.
Měl jsi s čímkoli problém? Stáhni si vzorovou aplikaci níže a porovnej ji se svým projektem, chybu tak snadno najdeš.
Stáhnout
Stažením následujícího souboru souhlasíš s licenčními podmínkami
Staženo 287x (3.43 MB)
Aplikace je včetně zdrojových kódů v jazyce PHP