Nefunkční $this->flassmessage() ve FormFactory
- mario85
- Člen | 22
Zdarec,
už jsem prošel skoro všechno, ale už jsem se do toho nějak zamotal.
S Nette víceméně začínám. Snažím se psát formuláře do samostatných
souborů jako komponenty, ale nedaří se mi předat zprávu zpátky. Můžete
mě, prosím, nakopnout?
App/Forms/UsersFormFactory:
<?php
namespace App\Forms;
use Nette,
Nette\Application\UI\Form,
Nette\Security\User,
App\Forms\Bs3FormRenderer,
App\Model\UserManager,
App\Presenters\UsersPresenter;
class UsersFormFactory extends Nette\Object
{
/** @var Nette\Security\User */
private $user;
/** @var App\Model\UserManager */
private $userManager;
public function __construct(User $user, UserManager $userManager)
{
$this->user = $user;
$this->userManager = $userManager;
}
/**
*
* @return Form
*/
public function create()
{
$form = new Form;
$form->setRenderer(new Bs3FormRenderer);
$form->addText('username', 'Uživatelské jméno:')
->setRequired('Vyplňte uživatelské jméno.');
$form->addText('firstname', 'Jméno:')
->setRequired('Vyplňte uživatelské jméno.');
$form->addText('surname', 'Příjmení:')
->setRequired('Vyplňte uživatelské jméno.');
$form->addText('email', 'E-mail:')
->setRequired('Vyplňte e-mail.')
->addRule(Form::EMAIL, 'E-mail není ve správném tvaru.');
$form->addPassword('password', 'Heslo: ')
->setRequired('Vyplňte heslo.');
$form->addPassword('passwordVerify', 'Heslo pro kontrolu: ')
->setRequired('Vyplňte heslo pro kontrolu.')
->addRule(Form::EQUAL, 'Hesla se neshodují!', $form['password']);
$form->addSubmit('send', 'Přidat uživatele');
$form->onSuccess[] = function (Form $form, \stdClass $values){
if (!$this->user->isInRole('administrator')) {
$this->error('Pro vytvoření, nebo editování uživatele musíte být administrátor!');
}
$userId = NULL;
if ($userId) {
try {
$user = $this->database->table('users')->get($postId);
$user->update($values);
} catch (Exception $ex) {
$this->flashMessage('Uživatel byl úspěšně změněn!', 'alert-error');
$this->redirect('show', $post->id);
}
} else {
try{
$this->userManager->insert($form->values);
}
catch (Exception $ex) {
$this->addError('Chyba!', 'error');
$this->redirect('show');
}
$this->flashMessage('Uživatel byl úspěšně vytvořen!', 'alert-success');
$this->redirect('show');
}
};
return $form;
}
}
ale hlásí to chybu: Call to undefined method App\Forms\UsersFormFactory::flashMessage()
Tuším, že bych si měl asi někde předat nějakou závislost, ale už
fakt nevím.
Díky
- Barvoj
- Člen | 60
Osobně bych to řešil přes eventy:
class UsersFormFactory extends Nette\Object
{
...
public $onFormSuccess = [];
...
/**
*
* @return Form
*/
public function create()
{
$form = new Form;
$form->setRenderer(new Bs3FormRenderer);
...
$form->onSuccess[] = function($form) {
try {
$this->userManager->insert($form->values);
$this->onFormSuccess();
} catch (...) {
...
}
}
return $form;
}
}
A presenter:
class UserPresenter extends Ui\Presenter
{
/** @inject UsersFormFactory */
public $formFactory;
public function createTomponentUsersForm()
{
$form = $this->formFactory->create();
$form->onFormSuccess[] = function() {
$this->flashMessage('Uživatel byl úspěšně vytvořen!', 'alert-success');
$this->redirect('show');
}
return $form;
}
}
Ze se ma vypsat flash message a udelat redirect neni vec formulare ale presenteru, tak ho to nech delat..
Ve formulari si vytvor public promenou pole napr $onFormSuccess a diky nette magii pak muzes zavolat methodu stejneho nazvu a nette pak zavola vsechny callbecky ulozene v poli onSuccessForm.
Stejne vlastne funguje onSuccess[] formulare…
Editoval Barvoj (28. 2. 2016 8:09)
- Oli
- Člen | 1215
Ze se ma vypsat flash message a udelat redirect neni vec formulare ale presenteru, tak ho to nech delat..
S tím úplně nesouhlasím. Redirect, pokud přesměruje sám na sebe může uplně klidně být zodpovědnost formuláře. A hlavně komponenta může mít vlastní flashMessage. FlashMessage je zodpovědností presenteru pouze pokud se jedná o „globální“ zprávu. Můžeš mít ale formulář, odesílat ho ajaxem a chtít zobrazit zprávu hned nad/pod formulářem. V takovým případě patří flashMessage tý komponentě.
Obecně máš ale pravdu, ze většinou to je zodpovědnost presenteru :-)
- Pavel Macháň
- Člen | 282
Form Factory má pouze sestavit formulář. Logiku přesuň do komponenty, která pracuje s formulářem.
- mario85
- Člen | 22
Tak jsem to celé smazal, vytvořil znova a už to víceméně běží, ale v presenteru se to sekne a hlásí Cannot read an undeclared property Nette\Application\UI\Form::$onFormSuccess. Konkrétně na řádku 62:
59: public function createComponentUsersForm()
60: {
61: $form = $this->usersForm->create();
62: $form->onFormSuccess[] = function() {
63: $this->flashMessage('Uživatel byl úspěšně vytvořen!', 'alert-success');
64: $this->redirect('show');
65: };
66: return $form;
Továrnička teď vypadá takhle:
class UsersFormFactory extends Nette\Object
{
public $onFormSuccess = [];
private $database;
public function __construct(Nette\Database\Connection $database)
{
$this->database = $database;
}
/**
*
* @return Form
*/
public function create()
{
$form = new Form;
$form->setRenderer(new Bs3FormRenderer);
$form->addText('username', 'Uživatelské jméno:')
->setRequired('Vyplňte uživatelské jméno.');
// ...
$form->addSubmit('send', 'Přidat uživatele');
$form->onSuccess[] = function($form) {
$this->onFormSuccess();
};
poradí někdo? Předem díky!