ILIAS  trunk Revision v11.0_alpha-2638-g80c1d007f79
FormTest.php
Go to the documentation of this file.
1 <?php
2 
19 declare(strict_types=1);
20 
21 require_once(__DIR__ . "/../../../../Base.php");
22 
30 use ILIAS\Data;
36 
37 class FixedNameSource implements NameSource
38 {
39  public string $name = "name";
40 
41  public function getNewName(): string
42  {
43  return $this->name;
44  }
45 }
46 
47 class ConcreteForm extends Form
48 {
49  public ?InputData $input_data = null;
50  protected Input\Field\Factory $input_factory;
51  protected Group $input_group;
52  protected array $inputs;
53 
54  public function __construct(Input\Field\Factory $input_factory, NameSource $name_source, array $inputs)
55  {
56  $this->input_factory = $input_factory;
57  parent::__construct($input_factory, $name_source, $inputs);
58  }
59 
61  {
62  return $this->extractRequestData($request);
63  }
64 
66  {
67  if ($this->input_data !== null) {
68  return $this->input_data;
69  }
70 
71  return parent::extractRequestData($request);
72  }
73 
74 
75  public function setInputs(array $inputs): void
76  {
77  $this->input_group = $this->input_factory->group($inputs);
78  $this->inputs = $inputs;
79  }
80 }
81 
86 {
90  protected $language;
91  protected array $inputs;
92 
93  protected function buildFactory(): Input\Container\Form\Factory
94  {
95  return new Input\Container\Form\Factory(
96  $this->buildInputFactory(),
97  new SignalGenerator()
98  );
99  }
100 
101  protected function buildInputFactory(): Input\Field\Factory
102  {
103  $df = new Data\Factory();
104  $this->language = $this->createMock(ILIAS\Language\Language::class);
105  return new Input\Field\Factory(
106  $this->createMock(\ILIAS\UI\Implementation\Component\Input\Field\Node\Factory::class),
107  $this->createMock(\ILIAS\UI\Implementation\Component\Input\UploadLimitResolver::class),
108  new SignalGenerator(),
109  $df,
110  new Refinery($df, $this->language),
111  $this->language
112  );
113  }
114 
115  protected function buildButtonFactory(): I\Button\Factory
116  {
117  return new I\Button\Factory();
118  }
119 
120  protected function buildTransformation(Closure $trafo): Transformation
121  {
122  $dataFactory = new Data\Factory();
123  $language = $this->createMock(ILIAS\Language\Language::class);
124  $refinery = new Refinery($dataFactory, $language);
125 
126  return $refinery->custom()->transformation($trafo);
127  }
128 
129  public function getUIFactory(): NoUIFactory
130  {
131  return new WithButtonNoUIFactory($this->buildButtonFactory());
132  }
133 
134  public function buildDataFactory(): Data\Factory
135  {
136  return new Data\Factory();
137  }
138 
139  public function testGetInputs(): void
140  {
141  $this->buildFactory();
142  $if = $this->buildInputFactory();
143  $name_source = new FixedNameSource();
144 
145  $inputs = [$if->text(""), $if->text("")];
146  $form = new ConcreteForm($this->buildInputFactory(), new DefNamesource(), $inputs);
147 
148  $seen_names = [];
149  $form_inputs = $form->getInputs();
150  $this->assertSameSize($inputs, $form_inputs);
151 
152  foreach ($form_inputs as $input) {
153  $name = $input->getName();
154  $name_source->name = $name;
155 
156  // name is a string
157  $this->assertIsString($name);
158 
159  // only name is attached
160  $input = array_shift($form_inputs);
161  $this->assertEquals($input->withNameFrom($name_source), $input);
162 
163  // every name can only be contained once.
164  $this->assertNotContains($name, $seen_names);
165  $seen_names[] = $name;
166  }
167  }
168 
169  public function testExtractPostData(): void
170  {
171  $form = new ConcreteForm($this->buildInputFactory(), new DefNamesource(), []);
172  $request = $this->createMock(ServerRequestInterface::class);
173  $request
174  ->expects($this->once())
175  ->method("getParsedBody")
176  ->willReturn([]);
177  $input_data = $form->_extractRequestData($request);
178  $this->assertInstanceOf(InputData::class, $input_data);
179  }
180 
181  public function testWithRequest(): void
182  {
183  $df = $this->buildDataFactory();
184  $request = $this->createMock(ServerRequestInterface::class);
185  $input_data = $this->createMock(InputData::class);
186 
187  $input_1 = $this->inputMock();
188  $input_1
189  ->expects($this->once())
190  ->method("withInput")
191  ->with($input_data)
192  ->willReturn($input_1);
193  $input_1
194  ->expects($this->once())
195  ->method("getContent")
196  ->willReturn($df->ok(0));
197 
198  $input_2 = $this->inputMock();
199  $input_2
200  ->expects($this->once())
201  ->method("withInput")
202  ->with($input_data)
203  ->willReturn($input_2);
204  $input_2
205  ->expects($this->once())
206  ->method("getContent")
207  ->willReturn($df->ok(0));
208 
209  $form = new ConcreteForm($this->buildInputFactory(), new DefNamesource(), []);
210  $form->setInputs([$input_1, $input_2]);
211  $form->input_data = $input_data;
212 
213  $form2 = $form->withRequest($request);
214 
215  $this->assertNotSame($form2, $form);
216  $this->assertInstanceOf(Form::class, $form2);
217  $this->assertEquals([$input_1, $input_2], $form2->getInputs());
218  }
219 
220  public function testWithRequestRespectsKeys(): void
221  {
222  $df = $this->buildDataFactory();
223  $request = $this->createMock(ServerRequestInterface::class);
224  $input_data = $this->createMock(InputData::class);
225 
226  $input_1 = $this->inputMock();
227  $input_1
228  ->expects($this->once())
229  ->method("withInput")
230  ->with($input_data)
231  ->willReturn($input_1);
232  $input_1
233  ->expects($this->once())
234  ->method("getContent")
235  ->willReturn($df->ok(0));
236 
237  $input_2 = $this->inputMock();
238  $input_2
239  ->expects($this->once())
240  ->method("withInput")
241  ->with($input_data)
242  ->willReturn($input_2);
243  $input_2
244  ->expects($this->once())
245  ->method("getContent")
246  ->willReturn($df->ok(0));
247 
248  $form = new ConcreteForm($this->buildInputFactory(), new DefNamesource(), []);
249  $form->setInputs(["foo" => $input_1, "bar" => $input_2]);
250  $form->input_data = $input_data;
251 
252  $form2 = $form->withRequest($request);
253 
254  $this->assertNotSame($form2, $form);
255  $this->assertInstanceOf(Form::class, $form2);
256  $this->assertEquals(["foo" => $input_1, "bar" => $input_2], $form2->getInputs());
257  }
258 
259  public function testGetData(): void
260  {
261  $df = $this->buildDataFactory();
262  $request = $this->createMock(ServerRequestInterface::class);
263  $request
264  ->expects($this->once())
265  ->method("getParsedBody")
266  ->willReturn([]);
267 
268  $input_1 = $this->inputMock();
269  $input_1
270  ->expects($this->once())
271  ->method("getContent")
272  ->willReturn($df->ok(1));
273  $input_1
274  ->expects($this->once())
275  ->method("withInput")
276  ->willReturn($input_1);
277 
278  $input_2 = $this->inputMock();
279  $input_2
280  ->expects($this->once())
281  ->method("getContent")
282  ->willReturn($df->ok(2));
283  $input_2
284  ->expects($this->once())
285  ->method("withInput")
286  ->willReturn($input_2);
287 
288  $form = new ConcreteForm($this->buildInputFactory(), new DefNamesource(), []);
289  $form->setInputs([$input_1, $input_2]);
290  $form = $form->withRequest($request);
291  $this->assertEquals([1, 2], $form->getData());
292  }
293 
294  public function testGetDataRespectsKeys(): void
295  {
296  $df = $this->buildDataFactory();
297  $request = $this->createMock(ServerRequestInterface::class);
298  $request
299  ->expects($this->once())
300  ->method("getParsedBody")
301  ->willReturn([]);
302 
303  $input_1 = $this->inputMock();
304  $input_1
305  ->expects($this->once())
306  ->method("getContent")
307  ->willReturn($df->ok(1));
308  $input_1
309  ->expects($this->once())
310  ->method("withInput")
311  ->willReturn($input_1);
312 
313  $input_2 = $this->inputMock();
314  $input_2
315  ->expects($this->once())
316  ->method("getContent")
317  ->willReturn($df->ok(2));
318  $input_2
319  ->expects($this->once())
320  ->method("withInput")
321  ->willReturn($input_2);
322 
323  $form = new ConcreteForm($this->buildInputFactory(), new DefNamesource(), []);
324  $form->setInputs(["foo" => $input_1, "bar" => $input_2]);
325  $form = $form->withRequest($request);
326  $this->assertEquals(["foo" => 1, "bar" => 2], $form->getData());
327  }
328 
329  public function testGetDataFaulty(): void
330  {
331  $df = $this->buildDataFactory();
332  $request = $this->createMock(ServerRequestInterface::class);
333  $request
334  ->expects($this->once())
335  ->method("getParsedBody")
336  ->willReturn([]);
337 
338  $input_1 = $this->inputMock();
339  $input_1
340  ->expects($this->once())
341  ->method("getContent")
342  ->willReturn($df->error("error"));
343  $input_1
344  ->expects($this->once())
345  ->method("withInput")
346  ->willReturn($input_1);
347 
348  $input_2 = $this->inputMock();
349  $input_2
350  ->expects($this->once())
351  ->method("getContent")
352  ->willReturn($df->ok(2));
353  $input_2
354  ->expects($this->once())
355  ->method("withInput")
356  ->willReturn($input_2);
357 
358  $form = new ConcreteForm($this->buildInputFactory(), new DefNamesource(), []);
359  $form->setInputs(["foo" => $input_1, "bar" => $input_2]);
360 
361  $i18n = "THERE IS SOME ERROR IN THIS GROUP";
362  $this->language
363  ->expects($this->once())
364  ->method("txt")
365  ->with("ui_error_in_group")
366  ->willReturn($i18n);
367 
368  //Todo: This is not good, this should throw an error or similar.
369  $form = $form->withRequest($request);
370  $this->assertEquals(null, null);
371  }
372 
373  public function testWithAdditionalTransformation(): void
374  {
375  $df = $this->buildDataFactory();
376  $request = $this->createMock(ServerRequestInterface::class);
377  $request
378  ->expects($this->once())
379  ->method("getParsedBody")
380  ->willReturn([]);
381 
382  $input_1 = $this->inputMock();
383  $input_1
384  ->expects($this->once())
385  ->method("getContent")
386  ->willReturn($df->ok(1));
387  $input_1
388  ->expects($this->once())
389  ->method("withInput")
390  ->willReturn($input_1);
391 
392  $input_2 = $this->inputMock();
393  $input_2
394  ->expects($this->once())
395  ->method("getContent")
396  ->willReturn($df->ok(2));
397  $input_2
398  ->expects($this->once())
399  ->method("withInput")
400  ->willReturn($input_2);
401 
402  $form = new ConcreteForm($this->buildInputFactory(), new DefNamesource(), []);
403  $form->setInputs([$input_1, $input_2]);
404 
405  $form2 = $form->withAdditionalTransformation($this->buildTransformation(function () {
406  return "transformed";
407  }));
408 
409  $this->assertNotSame($form2, $form);
410  $form2 = $form2->withRequest($request);
411 
412  $this->assertEquals("transformed", $form2->getData());
413  }
414 
415  public function testNameInputsRespectsKeys(): void
416  {
417  $if = $this->buildInputFactory();
418  $inputs = [
419  2 => $if->text(""),
420  "foo" => $if->text(""),
421  1 => $if->text(""),
422  $if->text(""),
423  ];
424  $form = new ConcreteForm($this->buildInputFactory(), new DefNamesource(), []);
425  $form->setInputs($inputs);
426  $named_inputs = $form->getInputs();
427  $this->assertEquals(array_keys($inputs), array_keys($named_inputs));
428  }
429 
433  protected function inputMock()
434  {
435  static $no = 1000;
436  return $this
437  ->getMockBuilder(Input\Field\FormInputInternal::class)
438  ->onlyMethods([
439  "getName",
440  "withDedicatedName",
441  "withNameFrom",
442  "withInput",
443  "getContent",
444  "getLabel",
445  "withLabel",
446  "getByline",
447  "withByline",
448  "isRequired",
449  "withRequired",
450  "isDisabled",
451  "withDisabled",
452  "getValue",
453  "withValue",
454  "getError",
455  "withError",
456  "withAdditionalTransformation",
457  "getUpdateOnLoadCode",
458  "getCanonicalName",
459  "withOnLoadCode",
460  "withAdditionalOnLoadCode",
461  "getOnLoadCode",
462  "withOnUpdate",
463  "appendOnUpdate",
464  "withResetTriggeredSignals",
465  "getTriggeredSignals",
466  "reduceWith"
467  ])
468  ->setMockClassName("Mock_InputNo" . ($no++))
469  ->getMock();
470  }
471 
472  public function testFormWithoutRequiredField(): void
473  {
474  $f = $this->buildFactory();
475  $if = $this->buildInputFactory();
476  $inputs = [$if->text(""), $if->text("")];
477  $form = new ConcreteForm($this->buildInputFactory(), new DefNamesource(), $inputs);
478 
479  $this->assertFalse($form->hasRequiredInputs());
480  }
481 
482  public function testFormWithRequiredField(): void
483  {
484  $f = $this->buildFactory();
485  $if = $this->buildInputFactory();
486  $inputs = [
487  $if->text("")->withRequired(true),
488  $if->text("")
489  ];
490  $form = new ConcreteForm($this->buildInputFactory(), new DefNamesource(), $inputs);
491  $this->assertTrue($form->hasRequiredInputs());
492  }
493 }
buildInputFactory()
Definition: FormTest.php:101
testGetDataFaulty()
Definition: FormTest.php:329
Transform values according to custom configuration.
testWithAdditionalTransformation()
Definition: FormTest.php:373
inputMock()
Definition: FormTest.php:433
testWithRequestRespectsKeys()
Definition: FormTest.php:220
testGetData()
Definition: FormTest.php:259
testGetDataRespectsKeys()
Definition: FormTest.php:294
Describes how Input-Elements want to interact with posted data.
Definition: InputData.php:29
Interface Observer Contains several chained tasks and infos about them.
getNewName()
Generates a unique name on every call.
Definition: FormTest.php:41
testGetInputs()
Definition: FormTest.php:139
testWithRequest()
Definition: FormTest.php:181
Test on form implementation.
Definition: FormTest.php:85
testExtractPostData()
Definition: FormTest.php:169
testFormWithRequiredField()
Definition: FormTest.php:482
__construct(Input\Field\Factory $input_factory, NameSource $name_source, array $inputs)
Definition: FormTest.php:54
array $inputs
Definition: FormTest.php:91
string $name
Definition: FormTest.php:39
array $inputs
Definition: FormTest.php:52
buildDataFactory()
Definition: FormTest.php:134
This implements commonalities between all forms.
Definition: Form.php:33
while($session_entry=$r->fetchRow(ilDBConstants::FETCHMODE_ASSOC)) return null
_extractRequestData(ServerRequestInterface $request)
Definition: FormTest.php:60
getUIFactory()
Definition: FormTest.php:129
extractRequestData(ServerRequestInterface $request)
Definition: FormTest.php:65
Builds data types.
Definition: Factory.php:35
testFormWithoutRequiredField()
Definition: FormTest.php:472
testNameInputsRespectsKeys()
Definition: FormTest.php:415
setInputs(array $inputs)
Definition: FormTest.php:75
Group $input_group
Definition: FormTest.php:51
__construct(Container $dic, ilPlugin $plugin)
This describes commonalities between all inputs.
Definition: Input.php:46
language()
description: > Example for rendring a language glyph.
Definition: language.php:41
buildButtonFactory()
Definition: FormTest.php:115
Describes a source for input names.
Definition: NameSource.php:26
This file is part of ILIAS, a powerful learning management system published by ILIAS open source e-Le...
buildFactory()
Definition: FormTest.php:93
buildTransformation(Closure $trafo)
Definition: FormTest.php:120
Input Field Factory $input_factory
Definition: FormTest.php:50