Magento 2 Documentation  2.3
Documentation for Magento 2 CMS v2.3 (December 2018)
BackendValidatorTest.php
Go to the documentation of this file.
1 <?php
7 declare(strict_types=1);
8 
10 
25 use PHPUnit\Framework\TestCase;
28 use Magento\Framework\App\Request\Http as HttpRequest;
30 use Zend\Stdlib\Parameters;
31 use Magento\Backend\Model\UrlInterface as BackendUrl;
32 use Magento\Framework\App\Response\HttpFactory as HttpResponseFactory;
33 
37 class BackendValidatorTest extends TestCase
38 {
39  private const AWARE_VALIDATION_PARAM = 'test_param';
40 
41  private const AWARE_LOCATION_VALUE = 'test1';
42 
43  private const CSRF_AWARE_MESSAGE = 'csrf_aware';
44 
48  private $mockUnawareAction;
49 
53  private $mockAwareAction;
54 
58  private $validator;
59 
63  private $request;
64 
68  private $formKey;
69 
73  private $url;
74 
78  private $auth;
79 
83  private $mockCsrfAwareAction;
84 
88  private $httpResponseFactory;
89 
93  private function createUnawareAction(): ActionInterface
94  {
95  return new class implements ActionInterface {
99  public function execute()
100  {
101  throw new NotFoundException(new Phrase('Not implemented'));
102  }
103  };
104  }
105 
109  private function createAwareAction(): AbstractAction
110  {
111  $l = self::AWARE_LOCATION_VALUE;
112  $p = self::AWARE_VALIDATION_PARAM;
113 
114  return new class($l, $p) extends AbstractAction{
115 
119  private $locationValue;
120 
124  private $param;
125 
130  public function __construct(
131  string $locationValue,
132  string $param
133  ) {
134  parent::__construct(
135  Bootstrap::getObjectManager()->get(Context::class)
136  );
137  $this->locationValue= $locationValue;
138  $this->param = $param;
139  }
140 
144  public function execute()
145  {
146  throw new NotFoundException(new Phrase('Not implemented'));
147  }
148 
152  public function _processUrlKeys()
153  {
154  if ($this->_request->getParam($this->param)) {
155  return true;
156  } else {
158  $response = $this->_response;
159  $response->setHeader('Location', $this->locationValue);
160 
161  return false;
162  }
163  }
164  };
165  }
166 
170  private function createCsrfAwareAction(): CsrfAwareActionInterface
171  {
173  ->get(ResponseInterface::class);
174  $m = self::CSRF_AWARE_MESSAGE;
175 
176  return new class ($r, $m) implements CsrfAwareActionInterface {
177 
181  private $response;
182 
186  private $message;
187 
192  public function __construct(
194  string $message
195  ) {
196  $this->response = $response;
197  $this->message = $message;
198  }
199 
203  public function execute()
204  {
205  return $this->response;
206  }
207 
211  public function createCsrfValidationException(
212  RequestInterface $request
214  return new InvalidRequestException(
215  $this->response,
216  [new Phrase($this->message)]
217  );
218  }
219 
223  public function validateForCsrf(RequestInterface $request): ?bool
224  {
225  return false;
226  }
227 
228  };
229  }
230 
234  protected function setUp()
235  {
237  $this->request = $objectManager->get(RequestInterface::class);
238  $this->validator = $objectManager->get(BackendValidator::class);
239  $this->mockUnawareAction = $this->createUnawareAction();
240  $this->mockAwareAction = $this->createAwareAction();
241  $this->formKey = $objectManager->get(FormKey::class);
242  $this->url = $objectManager->get(BackendUrl::class);
243  $this->auth = $objectManager->get(Auth::class);
244  $this->mockCsrfAwareAction = $this->createCsrfAwareAction();
245  $this->httpResponseFactory = $objectManager->get(
246  HttpResponseFactory::class
247  );
248  }
249 
254  public function testValidateWithValidKey()
255  {
256  $this->request->setMethod(HttpRequest::METHOD_GET);
257  $this->auth->login(
258  TestBootstrap::ADMIN_NAME,
259  TestBootstrap::ADMIN_PASSWORD
260  );
261  $this->request->setParams([
262  BackendUrl::SECRET_KEY_PARAM_NAME => $this->url->getSecretKey(),
263  ]);
264 
265  $this->validator->validate(
266  $this->request,
267  $this->mockUnawareAction
268  );
269  }
270 
277  public function testValidateWithInvalidKey()
278  {
279  $invalidKey = $this->url->getSecretKey() .'Invalid';
280  $this->request->setParams([
281  BackendUrl::SECRET_KEY_PARAM_NAME => $invalidKey,
282  ]);
283  $this->request->setMethod(HttpRequest::METHOD_GET);
284  $this->auth->login(
285  TestBootstrap::ADMIN_NAME,
286  TestBootstrap::ADMIN_PASSWORD
287  );
288 
289  $this->validator->validate(
290  $this->request,
291  $this->mockUnawareAction
292  );
293  }
294 
302  {
303  $this->request->setPost(
304  new Parameters(['form_key' => $this->formKey->getFormKey() .'1'])
305  );
306  $this->request->setMethod(HttpRequest::METHOD_POST);
307 
308  $this->validator->validate(
309  $this->request,
310  $this->mockUnawareAction
311  );
312  }
313 
318  public function testValidateInvalidWithAwareAction()
319  {
320  $this->request->setParams([self::AWARE_VALIDATION_PARAM => '']);
321 
323  $caught = null;
324  try {
325  $this->validator->validate(
326  $this->request,
327  $this->mockAwareAction
328  );
329  } catch (InvalidRequestException $exception) {
330  $caught = $exception;
331  }
332 
333  $this->assertNotNull($caught);
335  $response = $caught->getReplaceResult();
336  $this->assertInstanceOf(Response::class, $response);
337  $this->assertEquals(
338  self::AWARE_LOCATION_VALUE,
339  $response->getHeader('Location')->getFieldValue()
340  );
341  $this->assertNull($caught->getMessages());
342  }
343 
348  {
349  $this->request->setParams(
350  [self::AWARE_VALIDATION_PARAM => '1']
351  );
352 
353  $this->validator->validate(
354  $this->request,
355  $this->mockAwareAction
356  );
357  }
358 
363  public function testValidateWithCsrfAwareAction()
364  {
365  //Setting up request that would be valid for default validation.
366  $this->request->setMethod(HttpRequest::METHOD_GET);
367  $this->auth->login(
368  TestBootstrap::ADMIN_NAME,
369  TestBootstrap::ADMIN_PASSWORD
370  );
371  $this->request->setParams([
372  BackendUrl::SECRET_KEY_PARAM_NAME => $this->url->getSecretKey(),
373  ]);
374 
376  $caught = null;
377  try {
378  $this->validator->validate(
379  $this->request,
380  $this->mockCsrfAwareAction
381  );
382  } catch (InvalidRequestException $exception) {
383  $caught = $exception;
384  }
385 
386  //Checking that custom validation was called and invalidated
387  //valid request.
388  $this->assertNotNull($caught);
389  $this->assertCount(1, $caught->getMessages());
390  $this->assertEquals(
391  self::CSRF_AWARE_MESSAGE,
392  $caught->getMessages()[0]->getText()
393  );
394  }
395 
396  public function testInvalidAjaxRequest()
397  {
398  //Setting up AJAX request with invalid secret key.
399  $this->request->setMethod(HttpRequest::METHOD_GET);
400  $this->auth->login(
401  TestBootstrap::ADMIN_NAME,
402  TestBootstrap::ADMIN_PASSWORD
403  );
404  $this->request->setParams([
405  BackendUrl::SECRET_KEY_PARAM_NAME => 'invalid',
406  'isAjax' => '1'
407  ]);
408 
410  $caught = null;
411  try {
412  $this->validator->validate(
413  $this->request,
414  $this->mockUnawareAction
415  );
416  } catch (InvalidRequestException $exception) {
417  $caught = $exception;
418  }
419 
420  $this->assertNotNull($caught);
421  $this->assertInstanceOf(
422  ResultInterface::class,
423  $caught->getReplaceResult()
424  );
426  $result = $caught->getReplaceResult();
428  $response = $this->httpResponseFactory->create();
429  $result->renderResult($response);
430  $this->assertEmpty($response->getBody());
431  $this->assertEquals(401, $response->getHttpResponseCode());
432  }
433 }
$response
Definition: 404.php:11
$objectManager
Definition: bootstrap.php:17
$message
if(isset($opts->o)) if(! $usingStdout) $l