Statická analýza kódu po aktualizaci knihoven na Nette 3 při lvl 5+ hlásí chyby

- Spock
 - Člen | 8
 
Statická analýza kódu (https://github.com/…hpstan-nette) hlásí:
pro
	$form = new Form();
	...
	$form->addText('address', 'Ulice a číslo popisné:*')
			->setOption('id', 'address')
			->setOption('class', 'font-weight-bold')
			**->addConditionOn($form['transportRequest'], $form::EQUAL, true)**
			->addRule($form::FILLED, 'Zadejte vaší ulici a číslo popisné');
Chybu (možná souvisí s chybou viz níže):
Parameter #1 $control of method Nette\Forms\Controls\BaseControl::addConditionOn() expects
         Nette\Forms\IControl, Nette\ComponentModel\IComponent given.
a
pro form v komponentě (extends \Nette\Application\UI\Control)
	$form->onSuccess[] = [$this, 'processForm'];
Chybu:
Array (array<(callable(Nette\Forms\Form, array): void)|(callable(Nette\Forms\Form,
         Nette\Forms\ArrayHash): void)>) does not accept
         array($this(App\Components\Newsletter\NewsletterForm), 'processForm').
Nápady, proč tak najednou? (Nette/Utils mam nově na 3.0)
A jak to má být správně?

- Pavel Janda
 - Člen | 977
 
@Spock
1,
$transportRequestControl = $form->add.......;
$form->addText('address', 'Ulice a číslo popisné:*')
        ->setOption('id', 'address')
        ->setOption('class', 'font-weight-bold')
        **->addConditionOn($transportRequestControl, $form::EQUAL, true)**
        ->addRule($form::FILLED, 'Zadejte vaší ulici a číslo popisné');
Je tomu tak proto, že $form[‚cokoliv‘] vrací dle definice
IComponent, kdežto první parametr metody
addConditionOn přijímá striktněji IControl.
Stačí, když tam prdneš ten formulářový prvek tak, jak jsem to
zmínil výše..
2,
Mohl bys ukázat tu metodu processForm?

- Spock
 - Člen | 8
 
ad1) Super, fachá dobře (pro ostatní konkrétněji):
		$transportRequestControl = $form->addCheckbox('transportRequest', 'Chci nabídku na dopravu (v případě vlastní dopravy odškrtněte)');
		$transportRequestControl->addCondition($form::EQUAL, true)
			->toggle('address')
			->toggle('city')
			->toggle('zip')
			->toggle('weNeedInformation')
			->toggle('deliveryPhone')
			->toggle('deliveryNote');
		$form->addText('address', 'Ulice a číslo popisné:*')
			->setOption('id', 'address')
			->setOption('class', 'font-weight-bold')
			->addConditionOn($transportRequestControl, $form::EQUAL, true)
			->addRule($form::FILLED, 'Zadejte vaší ulici a číslo popisné');
2,
Mohl bys ukázat tu metodu
processForm?
	public function processForm($form)
	{
		$values = $form->getValues();
		if ($values->spamControl) {
			...
			$this->onSave($this);
		} else {
			$this->flashMessage('Objednávka/poptávka nebyla odeslána - blokováno antispamem', 'danger');
		}
	}
					Editoval Spock (28. 5. 2019 9:25)

- Pavel Janda
 - Člen | 977
 
@Spock Zkus toto:
public function processForm(Form $form, ArrayHash $values): void
{
}
					Editoval Pavel Janda (28. 5. 2019 15:05)

- CZechBoY
 - Člen | 3608
 
pravda, s jednim parametrem ten phpdoc nepočítá :(
https://github.com/…rms/Form.php#L85
zkusim zjistit jestli se to dá nějak fixnout
Editoval CZechBoY (28. 5. 2019 12:17)

- Pavel Janda
 - Člen | 977
 
@CZechBoY To je podle mě v pořádku. Když strict types tak strict types.. ale chápu, že jen 1 parametr by mohli lidé někdy preferovat.
Editoval Pavel Janda (28. 5. 2019 15:04)

- Spock
 - Člen | 8
 
Druhý parametr by asi nevadil, jen aby pak do budoucna nebyl deprecated. :-)
Nicméně to stejně háže:
  Line   app/Components/Checkout/CheckoutForm.php
 ------ ------------------------------------------------------------------------------------
  177    Array (array<(callable(Nette\Forms\Form, array): void)|(callable(Nette\Forms\Form,
         Nette\Forms\ArrayHash): void)>) does not accept
         array($this(App\Components\Checkout\CheckoutForm), 'processForm').
use Nette\Forms\Form;
use Nette\Utils\ArrayHash;
		...
		$form->onSuccess[] = [$this, 'processForm'];
		return $form;
	}
	public function processForm(Form $form, ArrayHash $values): void
	{
		//$values = $form->getValues();
		if ($values->spamControl) {
			...
Pokud použiji dle docu Nette\Forms\ArrayHash:
	public function processForm(Form $form, \Nette\Forms\ArrayHash $values): void
Hodí to prozměnu:
  Line   app/Components/Checkout/CheckoutForm.php
 ------ ---------------------------------------------------------------------------------------------
  181    Parameter $values of method App\Components\Checkout\CheckoutForm::processForm() has invalid
         typehint type Nette\Forms\ArrayHash.
  185    Access to property $spamControl on an unknown class Nette\Forms\ArrayHash.
  ...    Access to property ............ on an unknown class Nette\Forms\ArrayHash.
  ...    Access to property ............ on an unknown class Nette\Forms\ArrayHash.
  ...    Access to property ............ on an unknown class Nette\Forms\ArrayHash.
  ...
Tzn krom povinného parametru tam bude chyba zřejmě v use v Forms/Form.php, kde chybí:
use Nette\Utils\ArrayHash;
Je to tak? Může to někdo opravit?
A případně udělat druhý parametr volitelný?

- jiri.pudil
 - Nette Blogger | 1034
 
→ https://github.com/…rms/pull/223
A když už jsme u toho, půjde tam připsat něco, co by přidalo podporu vlastních mapped types?
class MappedValues {
	public string $name;
}
$form = new Nette\Forms\Form();
$form–>addText('name', 'Name');
$form->setMappedType(MappedValues::class);
$form->onSuccess[] = function (Form $form, MappedValues $values) {};
Array (array<(callable(Nette\Forms\Form, array): void)|(callable(Nette\Forms\Form, Nette\Utils\ArrayHash): void)>) does not accept Closure(Nette\Forms\Form, MappedValues): void.
Experimentoval jsem s callable(Form, object) nebo s
class MappedValues extends ArrayHash, ale nedošel jsem k ničemu
funkčnímu.
→ https://github.com/…s/issues/224
Editoval jiri.pudil (29. 5. 2019 12:13)