NOVINKA - Online rekvalifikační kurz Python programátor. Oblíbená a studenty ověřená rekvalifikace - nyní i online.
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í.

Diskuze – Lekce 3 - CMS v Nette a Doctrine 2 - Modely a Layout

Zpět

Upozorňujeme, že diskuze pod našimi online kurzy jsou nemoderované a primárně slouží k získávání zpětné vazby pro budoucí vylepšení kurzů. Pro studenty našich rekvalifikačních kurzů nabízíme možnost přímého kontaktu s lektory a studijním referentem pro osobní konzultace a podporu v rámci jejich studia. Toto je exkluzivní služba, která zajišťuje kvalitní a cílenou pomoc v případě jakýchkoli dotazů nebo projektů.

Komentáře
Avatar
Odpovídá na Dominik Gavrecký
Martin Konečný (pavelco1998):15.11.2016 20:08

Protože Base* třídy jsou takový antipattern. Dědičnost se má použít v případě, že její potomci opravdu využijí to, co ta základní třída obsahuje (atributy, chování (metody)). Tady pak mohou nastat dvě nepříjemné situace:

  1. Některá z fasád nevyužije to, co BaseFacade nabízí - pak dědičnost logicky nedává smysl
  2. Některá z fasád by nedědila od BaseFacade - tady bys zase měl podivně strukturu aplikace

Typicky se do Base* tříd ve vrstvě "Model" dává objekt, který zprostředkovává komunikaci s databází - EntityManager, Nette\Database\Con­nection, PDO atd.
Když bys ale měl fasádu, která by s databází nekomunikovala, k čemu by měla v sobě ten objekt mít (pokud by dědila od BaseFacade)? To z hlediska návrhu OOP nedává smysl.
Navíc se ty fasády v podstatě stanou závislými na té BaseFacade. Pokud budu chtít upravit něco v BaseFacade, automaticky se mi to promítne do všech fasád v aplikaci. Někdy to může být fajn, ale někdy si tím naopak pěkně nabiju hubu :D
Raději budu mít fasády nezávislé, ať se případné změny týkají jednotlivě každé fasády. Dívám se na to tak, že každá fasáda je nezávislá část aplikace, která (dle SRP) se stará o jednu konkrétní věc - a k tomu nemusí vždy využít např. připojení k databázi (nebo cokoliv jiného, co definuje BaseFacade).

Dědičnost se má použít tam, kde to má smysl, ne abych si ušetřil psaní.

Co se týká CURRENT_TIMESTAMP - to by se zřejmě dalo. Já si jen zvykl s daty pracovat ručně :) ono se to dá udělat i tak, že si to datum vytvoříš v konstruktoru:

class User
{

        protected $registrationDate;


        public functon __construct()
        {
                $this->registrationDate = new \DateTime();
        }

}

Magie je v tom, že když entitu vytváří Doctrine, když data vytahuje z databáze, pak se konstruktor nevolá, a tedy se do toho neuloží žádná jiná hodnota - jen ta, kterou tam Doctrine nastrčila.
Vytvoření objektu bez zavolání konstruktoru jde přes reflexi:

$rc = new ReflectionClass("User");
$entity = $rc->newInstanceWithoutConstructor();

viz http://php.net/…structor.php.

Editováno 15.11.2016 20:09
Odpovědět
15.11.2016 20:08
Aktuálně připravuji browser RPG, FB stránka - https://www.facebook.com/AlteiraCZ
Avatar
Odpovídá na Martin Konečný (pavelco1998)
Dominik Gavrecký:16.11.2016 17:59

Nesúhlasím s tebou ale je to znova vec pohody a myslenia programátora ... Čo v prípade že programátor si spraví niečo takéto ?

<?php
/**
 * Created by PhpStorm.
 * User: Dominik Gavrecký
 * Date: 15.11.2016
 * Time: 19:45
 */

namespace App\Model\Facades;

use Kdyby\Doctrine\EntityManager;
use Nette\Object;

/**
 * Class BaseFacades
 * @package app\model\Facades
 */
class BaseFacade extends Object
{
    const
        ENTITIE = '';

    /**
     * @var EntityManager
     */
    private $em;

    /**
     * BaseFacades constructor.
     * @param EntityManager $em
     */
    public function __construct(EntityManager $em)
    {
        $this->em = $em;
    }

    public function getAll()
    {
        return $this->em->getRepository($this::ENTITIE)->findAll();
    }


    public function delete($id)
    {
        $query = $this->em->getRepository($this::ENTITIE)->find($id);
        return $this->em->remove($query);
    }

    ...
}

Dosť ti to uľahčí prácu nie ?

A k tomu CURENT_TIMESTAMP

/**
     * @ORM\Column(type="datetime", options={"comment":"Dátum a čas registrácie uživateľa", "default": 0})
     */
    protected $time;

Dá sa to riešiť aj takto :)

Odpovědět
16.11.2016 17:59
Hlupák nie je ten kto niečo nevie, hlupákom sa stávaš v momente keď sa na to bojíš opýtať.
Avatar
Odpovídá na Dominik Gavrecký
Martin Konečný (pavelco1998):16.11.2016 19:31

A co v případě, že budu mít fasádu, která nebude pracovat s databází, a tedy nebude potřebovat EntityManager a metody getAll() a delete()? To pak nebude dědit od BaseFacade, nebo bude mít nesmyslně metody a závislosti, které vůbec nepotřebuje? To pak půjdeš proti logice a budeš to mít návrhově špatně :)

Navíc jedna fasáda obvykle nepracuje jen s jednou entitou, takže v tmo $this::ENTITIE nevidím moc reálné využití.

Odpovědět
16.11.2016 19:31
Aktuálně připravuji browser RPG, FB stránka - https://www.facebook.com/AlteiraCZ
Avatar
Odpovídá na Martin Konečný (pavelco1998)
Dominik Gavrecký:16.11.2016 20:02

Niekde som čítal ze v Nette by mal model (fasada) pracovať s jednou tabuľkou. Teda toho sa aj držím ... A co v prípade ze všetky fasády s ňou pracovať budú ? A o takýchto "co ak" sa tu môžme baviť do nekonečna

Odpovědět
16.11.2016 20:02
Hlupák nie je ten kto niečo nevie, hlupákom sa stávaš v momente keď sa na to bojíš opýtať.
Avatar
Odpovídá na Dominik Gavrecký
Martin Konečný (pavelco1998):16.11.2016 20:18

Jedna fasáda ani jedna entita nemusí pracovat jen s jednou tabulkou v databázi. Hlavně z pohledu ORM bys ani neměl řešit, že nějakou relační databázi máš (a tedy nějaké tabulky), měl bys uvažovat čistě v objektech (ale je jasné, že to úplně spolehlivě nejde).
Fasády mají zastřešovat určitou operaci, ve které naopak často bývá zapojeno více než jedna entita / tabulka. Minimálně bys narazil na problém, kdy bys měl jednu entitu složenou z více tabulek.

Pokud jsi si jistý, že všechny fasády s EM pracovat budou, pak je to zřejmě v pořádku. Nedá se ale brát tu logiku OOP vždy doslova, někdy se pro ulehčení práce musí udělat nějaká výjimka, která nějaké pravidlo porušuje. Já jen říkám, jak by to asi mělo být (aspoň dle mého názoru, co jsem za těch pár let zkušeností získal), ne že to tak být musí. I třeba magie jako Kdyby\Doctrine\En­tities\MagicAc­cessors není z hlediska logiky správná, ale kdo by pořád psal ty gettery a settery... někdy se pro zjednodušení práce nějaké pravidlo poruší, jen je potřeba na to dávat pozor, aby se to později v projektu nevymstilo.

Odpovědět
16.11.2016 20:18
Aktuálně připravuji browser RPG, FB stránka - https://www.facebook.com/AlteiraCZ
Avatar
David Koníček:14.11.2018 17:00

Kdyby\Doctrine\En­tities\BaseEn­tity

Je zastaralý, tak si nejsem jistý, zda je dobré ji používat?

Odpovědět
14.11.2018 17:00
Věř, běž a dokážeš!
Avatar
Odpovídá na David Koníček
Martin Konečný (pavelco1998):14.11.2018 17:02

Zdravím,

aktuálně je lepší používat spíše traitu Kdyby\Doctrine\En­tities\MagicAc­cessors.

Odpovědět
14.11.2018 17:02
Aktuálně připravuji browser RPG, FB stránka - https://www.facebook.com/AlteiraCZ
Avatar
Odpovídá na Martin Konečný (pavelco1998)
David Koníček:15.11.2018 7:39

Ok, díky, jo a mimochodem

UserFacade extends Nette\Object

Object už by se podle mě také neměl používat.

Odpovědět
15.11.2018 7:39
Věř, běž a dokážeš!
Avatar
Kateřina Záhorská Raždíková:25.8.2022 14:04

neaktuální informace, kód tak nefunguje. Musela jsem přepisovat do aktuálního get-set

 
Odpovědět
25.8.2022 14:04
Děláme co je v našich silách, aby byly zdejší diskuze co nejkvalitnější. Proto do nich také mohou přispívat pouze registrovaní členové. Pro zapojení do diskuze se přihlas. Pokud ještě nemáš účet, zaregistruj se, je to zdarma.

Zobrazeno 9 zpráv z 19.