Přístup k modelu z továrny na formuláře

Upozornění: Tohle vlákno je hodně staré a informace nemusí být platné pro současné Nette.
Milan Obrtlík
Člen | 50
+
0
-

Dobrý den,
jaký je podle vás nejlepší způsob přístupu k modelu (manageru) z továrny na formuláře?

Nyní si třeba v app/forms/AdminFormFactory.php přidám kód:

	/** @var \App\Model\ProductManager @inject */
    public $productManager;

	public function __construct(\App\Model\ProductManager $productManager) {
		$this->productManager = $productManager;
	}

a po odeslání formuláře „přidej produkt“:

	$this->productManager->add($values);

Toto řešení mi připadne trochu těžkopádné, hlavně když mám ještě categoriesManager, imagesManager, imagesStorage atd… To se mi pak __construct nevleze na „Full HD“ řádek.
Existuje lepší způsob nebo jsem úplně mimo?

newbie
Člen | 31
+
0
-

Já bych to všechno schoval do fasády třeba ProductFacade a tam bych se až staral o jednotlivé Managery.

Tomáš Votruba
Moderator | 1114
+
0
-

Dobry den, jak vypada cely kod formulare?
Mozna to jde resit lepe.

Milan Obrtlík
Člen | 50
+
0
-

newbie napsal(a):

Já bych to všechno schoval do fasády třeba ProductFacade a tam bych se až staral o jednotlivé Managery.

Omlouvám se, netuším co jsou tofasády. Můžete mi sem hodit relevantní odkazy k nastudování této problematiky?

Tomáš Votruba napsal(a):

Dobry den, jak vypada cely kod formulare?
Mozna to jde resit lepe.

namespace App\Forms;

use Nette;
use Nette\Application\UI\Form;
use Nette\Utils\Random;

class AdminFormFactory extends Nette\Object {

    /** @var \App\Model\ProductManager @inject */
    public $productManager;

    /** @var \App\Model\CategoryManager @inject */
    public $categoryManager;

    /** @var \App\Model\ImageManager @inject */
    public $imageManager;

    /** @var ImageStorage @inject */
    private $imageStorage;

    public function __construct(\App\Model\ProductManager $productManager, \App\Model\CategoryManager $categoryManager, \ImageStorage $imageStorage, \App\Model\ImageManager $imageManager) {
        $this->productManager = $productManager;
        $this->categoryManager = $categoryManager;
        $this->imageManager = $imageManager;
        $this->imageStorage = $imageStorage;
    }
    public function createAddSubcategoryForm() {
        $form = new Form;
        $form->addText('name');
        $form->addText('id');
        $form->addSubmit('send');
        $form->onSuccess[] = [$this, "formAddSubcategorySucceeded"];
        return $form;
    }

    public function formAddSubcategorySucceeded(Form $form, $values) {
        $this->categoryManager->newChildOfCategory($values->id, $values->name);
    }
}

Zbylé formuláře jsou téměř totožné, teda až na formulářové prvky.

David Matějka
Moderator | 6445
+
0
-

udelej si factory pro kazdy formular zvlast…

Tomáš Votruba
Moderator | 1114
+
0
-

@MilanObrtlík Díky.

Vypadá to, že v této třídě potřebuješ jen $this->categoryManager. Tedy jak píše @DavidMatějka , vytvoř si 4 samostatné třídy. Co formulář, to samostatná továrnička.

  • Anotace @inject můžeš odstranit, jelikož už používáš constructor.
  • Dědit od Nette\Object také není potřeba.

Editoval Tomáš Votruba (11. 9. 2015 11:44)

Milan Obrtlík
Člen | 50
+
0
-

Myslím, že továrna pro každý form toto nevyřeší (moje chyba, neuvedl v předchozí ukázce kódu všechny formuláře, hlavně tento zákeřný formulář)

public function formAddProductSucceeded(Form $form, $values) {
        $categories = $this->categoryManager->getAncestorsOfCategory($values->category);
        $product = $this->productManager->addProduct($values, $categories);
        $this->imageStorage->saveIcon($values->icon, $product->id);
        foreach ($values->images as $image) {
            $row = $this->imageManager->add($product->id);
            $this->imageStorage->save($image, $row->image_id); //->save($image, $filename)
        }
    }

Nejdřív zjistím všechny nadřazené kategorie pomocí catagoryManageru,
potom si uložím produkt do všech nadřazených kategorií (aby by byl produkt „i5“ vidět v kategoriích intel, procesory, domácí počítače apod.) pomocí productManageru.
Dále si pomocí imageStorage uložím ikonku produktu.
A nakonec si uložím všechny obrázky k produktu do databáze pomocí imageManageru a do složky www/images/… pomocí už zmiňovaného imageStorage. Tím jsem vyřešil i kolize názvů obrázků, protože názvy souborů generuje databáze.
Kvůli tomuto formuláři potřebuju právě všechny čtyři managery v jedné továrně.

Tak a teď teprve doufám, že to není velká prasárna, v tomto si nejsu vůbec jistý.

Editoval Milan Obrtlík (11. 9. 2015 11:51)

jiri.pudil
Nette Blogger | 1034
+
+2
-

Tak pokud budeš mít na každý formulář samostatnou továrnu a jeden holt vyžaduje více závislostí, tak si v té jedné továrně řekneš o všechny, v tom nevidím problém :) Další možný krok je uklidit to pak právě do fasády, tzn. uděláš si třídu třeba ProductFacade, do které celou tuhle logiku včetně závislostí schováš, a ve zpracování formuláře už pak pracuješ jenom s tou fasádou