IT rekvalifikace s garancí práce. Seniorní programátoři vydělávají až 160 000 Kč/měsíc a rekvalifikace je prvním krokem. Zjisti, jak na to!
Hledáme nové posily do ITnetwork týmu. Podívej se na volné pozice a přidej se do nejagilnější firmy na trhu - Více informací.

Lekce 11 - Jednoduchý redakční systém v Laravel - Práce s datem

V minulé lekci, Jednoduchý redakční systém v Laravel - Laravel Mix, jsme se věnovali zejména front-end části našeho projektu. Přidali jsme si také Font Awesome :)

Tentokrát si vysvětlíme práci s datem a následně se přesuneme na vyvíjení back-endu. Vytvoříme si totiž hlavní stránku.

Práce s datem

Určitě jste si už všimli, že data v naší aplikaci se vypisují ve výchozí podobě z databáze a to ve formátu Y-m-d H:i:s. Jedná se však o něco, co opravdu mít nechceme, jelikož to není zrovna intuitivní pro uživatele. Navíc se data ukládají v UTC, i když je celá naše aplikace v češtině (až na výjimky, tj. chybové hlášky knihoven či frameworku a URL adresy). Časové pásmo by tedy též mělo být nejlépe lokalizované.

V čistém PHP bychom vždy museli volat funkci date() a sami nastavovat formát času. V lepším případě bychom na to použili knihovnu. O to se však už postaral někdo za nás, jelikož Laravel ve výchozím nastavení používá knihovnu Carbon. Tato knihovna obsahuje mnoho užitečných metod a i překlady pro nespočet jazyků. Pokud vás zajímá více, zavítejte na oficiální stránky knihovny Carbon.

Nastavení lokalizace aplikace

Carbon si získává hodnoty pro nastavení z konfiguračního souboru aplikace, který je, jak již zřejmě tušíte, ve složce config/, přesněji v souboru app.php. Nás v tomto případě zajímají tyto hodnoty:

  • timezone - Definuje časové pásmo pro naší aplikaci. Výchozí hodnota je UTC. Pro střední Evropu bychom klidně mohli použít CET (Central European Time), zde však bohužel nastává problém s letním časem. Proto využijeme možnosti definovat kontinent s městem, v našem případě Europe/Prague, což vyřeší tento problém za nás.
  • locale - Zkratka pro jazyk, který má naše aplikace používat. Výchozí hodnota je en. My si však nastavíme cs, čímž změníme nejen konfiguraci jazyka pro samotný framework, ale i pro danou knihovnu. Pokud nelze najít frázi pro daný jazyk, použije se výchozí. Záložní jazyk je definovaný konfigurační hodnotou fallback_locale. Tato hodnota je jako výchozí nastavená na angličtinu (en).

Změny v souboru vypadají takto:

/*
|--------------------------------------------------------------------------
| Application Timezone
|--------------------------------------------------------------------------
|
| Here you may specify the default timezone for your application, which
| will be used by the PHP date and date-time functions. We have gone
| ahead and set this to a sensible default for you out of the box.
|
*/

'timezone' => 'Europe/Prague',

/*
|--------------------------------------------------------------------------
| Application Locale Configuration
|--------------------------------------------------------------------------
|
| The application locale determines the default locale that will be used
| by the translation service provider. You are free to set this value
| to any of the locales which will be supported by the application.
|
*/

'locale' => 'cs',

Nyní se již změny aplikují na naší aplikaci. Pokud si totiž zkusíme editovat článek, uvidíme, že datum poslední změny sedí i s lokálním časem. Co ale zatím nesedí, je výpis data, jelikož stále využívá výchozí formát. Pojďme to napravit.

Pokud se tyto změny neprojevily na vaší aplikaci, spusťte příkaz php artisan config:cache v kořenové složce projektu. Konfigurační hodnoty se totiž ukládají do mezipaměti a pomocí tohoto příkazu se naplní novými hodnotami.

Výpis dat v pohledech

Začneme nejdříve pohledem pro článek, který najdeme ve složce resources/views/article/ s názvem show.blade.php. Tam vypisujeme pouze jedno datum a to poslední změnu daného záznamu v patičce článku. Vytvoříme si tedy nový objekt třídy knihovny Carbon a následně vypíšeme časový rozdíl oproti poslední změně pomocí lokalizované metody diffForHumans():

@php
    $updatedAt = new Carbon\Carbon($article->updated_at);
@endphp
<footer>
    <p class="small text-secondary border-top pt-2 mt-4">
        <i class="fa fa-calendar"></i> {{ $updatedAt->diffForHumans() }}
    </p>
</footer>

Mimo klasické PHP tagy lze použít Blade direktivu @php ... @endphp. Není mezi nimi žádný rozdíl, pouze (a snad mi tuto připomínku ostatní vývojáři odpustí) se jedná o zkrášlení kódu daného pohledu.

Pokud si nyní zobrazíme nějaký článek, uvidíme v patičce článku výstup podobný tomuto:

Zobrazení rozdílu času ve výpisu článku pomocí knihovny Carbon v Laravel - Laravel framework pro PHP

Naše aplikace opět vypadá trochu profesionálněji. Bohužel naše řešení už na tom není tak dobře. Daný postup je samozřejmě bezchybný a funguje přesně tak, jak bychom si přáli. Představte si však, že byste na jedné stránce měli například 10 různých dat a pro všechna tato data byste museli vždy vytvořit nový objekt třídy knihovny Carbon. To by bylo poněkud zdlouhavé a zároveň by se kód stal nepřehledným.

Data záznamu jako instance knihovny Carbon

Jak jste si již určitě všimli v předchozích lekcích, vždy se dá vše zjednodušit. To samé platí pro data záznamů, jež jsou v instanci modelu vždy reprezentovaná jako objekt třídy Carbon dědící PHP třídu DateTime. My se tedy vytvářením nového objektu zatěžovat nemusíme a ihned můžeme přistupovat k metodám této knihovny.

Další datumy, které mají fungovat na stejném principu v daném modelu, se definují v proměnné $dates. Atributy created_at a updated_at už jsou automaticky zahrnuté. Pokud byste tedy chtěli definovat další data, je zbytečné je znovu specifikovat.

Část pohledu s patičkou si tedy můžeme upravit do následující podoby:

<footer>
    <p class="small text-secondary border-top pt-2 mt-4">
        <i class="fa fa-calendar"></i> {{ $article->updated_at->diffForHumans() }}
    </p>
</footer>

Lokalizované datum

Nejspíše se shodneme na tom, že v článku by se uživateli mělo zobrazovat přesné datum. Na to můžeme použít jednu z mnoha dostupných metod a to isoFormat(), jelikož jedna z výhod je lokalizovaný výstup (což neplatí například pro metodu format()):

<footer>
    <p class="small text-secondary border-top pt-2 mt-4">
        <i class="fa fa-calendar"></i> {{ $article->updated_at->isoFormat('LLL') }}
    </p>
</footer>

Výstup může vypadat podobně tomuto:

Zobrazení lokalizovaného času ve výpisu článku pomocí knihovny Carbon v Laravel - Laravel framework pro PHP

Více možností pro lokalizovaný výstup lze nalézt v oficiální dokumentaci knihovny Carbon.

Následně si také upravíme zobrazení dat v administraci článků, abychom tyto výstupy měli sjednocené. Otevřeme si tedy pohled resources/views/article/index.blade.php a upravíme následující část tabulky:

<td>{{ $article->description }}</td>
<td>{{ $article->created_at->isoFormat('LLL') }}</td>
<td>{{ $article->updated_at->isoFormat('LLL') }}</td>
<td>

Hlavní stránka

Zlepšování naší aplikace zakončíme vytvořením hlavní stránky (homepage) pro náš web. Nám zatím postačí, když bude obsahovat pouze výpis nejnovějších článků.

Začneme nejdříve od kontroleru.

Kontroler o jediné akci

Jak jsme si již řekli, kontroler pro zobrazení hlavní stránky bude definovat pouze jednu akci. Pozastavíme se však u názvu metody pro danou akci kontroleru. Jak bychom ji totiž měli pojmenovat? Názvy jako show() nebo index() se moc nehodí, jelikož se nejedná o CRUD kontroler pracující s jednou instancí modelu (na hlavní stránce nemusíme zobrazovat pouze výpis článků a navíc již jeden CRUD kontroler pro daný model máme). Možná vás ještě napadne něco jako getHome(), ani to však není ten nejlepší přístup.

Pro takovéto případy Laravel definuje tzv. kontrolery jediné akce (Single Action Controllers). Tyto kontrolery se vyznačují tím, že definují pouze jedinou metodu __invoke(), která může přijímat parametry stejně jako jakákoliv jiná akce.

Pojďme si nyní takový kontroler vytvořit přes Artisan příkaz make:controller. Předtím se však podíváme na jeho možnosti:

php artisan help make:controller
Zobrazení nápovědy k Artisan příkazu make:controller v Laravel frameworku - Laravel framework pro PHP

Možnost --model[=MODEL] již známe z předchozích lekcí. Nás však tentokrát bude zajímat možnost --invokable, která vytvoří kontroler jediné akce. Ten si pojmenujeme jako WelcomeController:

php artisan make:controller --invokable WelcomeController

Nově vygenerovaný kontroler najdeme ve složce s kontrolery app/Http/Controllers/ a obsahuje pouze zmíněnou metodu __invoke():

<?php

namespace App\Http\Controllers;

use Illuminate\Http\Request;
use Illuminate\Http\Response;

class WelcomeController extends Controller
{
    /**
     * Handle the incoming request.
     *
     * @param  Request $request
     * @return Response
     */
    public function __invoke(Request $request)
    {
        //
    }
}

My si přes tuto metodu zobrazíme hlavní stránku. Bude nám tedy stačit, aby vracela pohled, kterému předáme kolekci nejnovějších článků pomocí Eloquent metody latest():

/**
 * Zobraz hlavní stránku webu.
 *
 * @param  Request $request
 * @return View
 */
public function __invoke(Request $request): View
{
    return view('welcome', ['articles' => Article::latest()->get()]);
}

Nesmíme zapomenout importovat náš model a třídy zmíněné v dokumentaci:

use App\Models\Article;
use Illuminate\Contracts\View\View;

Routování

Routování kontrolerů jediné akce je trochu rozdílné - nedefinujeme totiž metodu daného kontroleru, ale pouze jeho název. Pro zobrazení hlavní stránky využívající tento kontroler si musíme do routovacího souboru routes/web.php přidat následující volání metody get() routovací třídy Route:

Route::get('', WelcomeController::class);

Opět musíme přidat import třídy kontroleru:

use App\Http\Controllers\WelcomeController;

Jak si můžete povšimnout, jako URI akci definujeme pouze prázdný řetězec. Tím dosáhneme toho, že při zobrazení webu bez jakýchkoliv jiných parametrů v URL adrese se vykoná metoda __invoke() kontroleru pro hlavní stránku WelcomeController.

Nesmíme také zapomenout odkázat na hlavní stránku v menu naší hlavní šablony resources/views/base.blade.php. Na to použijeme helper funkci url():

<nav class="my-2 my-md-0 mr-md-3">
    <a class="p-2 text-dark" href="{{ url('') }}">Hlavní stránka</a>
    <a class="p-2 text-dark" href="{{ route('article.index') }}">Seznam článků</a>
    <a class="p-2 text-dark" href="#">Kontakt</a>
</nav>

Pohled

Hlavní stránku zakončíme vytvořením pohledu s názvem welcome.blade.php ve složce s pohledy resources/views/. Momentálně nebude mít na starosti nic jiného než pouhé vypsání všech článků z naší databáze, které jsme předali v metodě kontroleru akce:

@extends('base')

@section('title', 'Jednoduchý redakční systém v Laravel')
@section('description', 'Ukázkový tutoriál pro jednoduchý redakční systém v Laravel frameworku z programátorské sociální sítě itnetwork.cz')

@section('content')
    <h1 class="text-center mb-4">Jednoduchý redakční systém v Laravel</h1>

    @forelse ($articles as $article)
        <article class="article mb-5">
            <header>
                <h2>
                    <a href="{{ route('article.show', ['article' => $article]) }}">{{ $article->title }}</a>
                </h2>
            </header>

            <p class="article-content mb-1">{{ $article->description }}</p>

            <footer>
                <p class="small text-secondary">
                    <i class="fa fa-calendar"></i> Naposledy upraveno {{ $article->updated_at->diffForHumans() }}
                </p>
            </footer>
        </article>
    @empty
        <p>Zatím se zde nenachází žádné články.</p>
    @endforelse
@endsection

Pokud si nyní otevřeme hlavní stránku přes odkaz v menu nebo při zadání URL adresy naší aplikace (v případě vestavěného web serveru http://127.0.0.1:8000/), uvidíme výpis nejnovějších článků spolu s odkázáním na ně a jejich datem poslední úpravy:

Hlavní stránky v jednoduchém redakčním systému v Laravel frameworku - Laravel framework pro PHP

Tímto jsme dokončili vylepšování našeho projektu. Pokud se vám něco nepodařilo, můžete si stáhnout projekt z přiloženého archivu níže nebo se zeptat v komentářích pod článkem.

V následujícím kvízu, Kvíz - Mix, práce s datem a Blade direktivy v Laravel, si vyzkoušíme nabyté zkušenosti z předchozích lekcí.


 

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 90x (52.33 MB)
Aplikace je včetně zdrojových kódů v jazyce PHP

 

Předchozí článek
Jednoduchý redakční systém v Laravel - Laravel Mix
Všechny články v sekci
Laravel framework pro PHP
Přeskočit článek
(nedoporučujeme)
Kvíz - Mix, práce s datem a Blade direktivy v Laravel
Článek pro vás napsal Jan Lupčík
Avatar
Uživatelské hodnocení:
20 hlasů
Autor se primárně věnuje vývoji webových stránek a aplikací v PHP (framework Laravel) a je jedním z herních vývojářů komunitní modifikace TruckersMP.
Aktivity