16
16
use Codeception \Util \Uri ;
17
17
use Magento \FunctionalTestingFramework \DataGenerator \Handlers \CredentialStore ;
18
18
use Magento \FunctionalTestingFramework \DataGenerator \Persist \Curl \WebapiExecutor ;
19
- use Magento \FunctionalTestingFramework \Util \Protocol \CurlTransport ;
20
19
use Magento \FunctionalTestingFramework \Util \Protocol \CurlInterface ;
21
20
use Magento \FunctionalTestingFramework \Util \ConfigSanitizerUtil ;
22
21
use Yandex \Allure \Adapter \AllureException ;
22
+ use Magento \FunctionalTestingFramework \Util \Protocol \CurlTransport ;
23
+ use Symfony \Component \Process \Process ;
23
24
use Yandex \Allure \Adapter \Support \AttachmentSupport ;
24
25
use Magento \FunctionalTestingFramework \Exceptions \TestFrameworkException ;
25
26
@@ -49,14 +50,15 @@ class MagentoWebDriver extends WebDriver
49
50
50
51
/**
51
52
* List of known magento loading masks by selector
53
+ *
52
54
* @var array
53
55
*/
54
56
public static $ loadingMasksLocators = [
55
57
'//div[contains(@class, "loading-mask")] ' ,
56
58
'//div[contains(@class, "admin_data-grid-loading-mask")] ' ,
57
59
'//div[contains(@class, "admin__data-grid-loading-mask")] ' ,
58
60
'//div[contains(@class, "admin__form-loading-mask")] ' ,
59
- '//div[@data-role="spinner"] '
61
+ '//div[@data-role="spinner"] ' ,
60
62
];
61
63
62
64
/**
@@ -69,7 +71,7 @@ class MagentoWebDriver extends WebDriver
69
71
'backend_name ' ,
70
72
'username ' ,
71
73
'password ' ,
72
- 'browser '
74
+ 'browser ' ,
73
75
];
74
76
75
77
/**
@@ -116,6 +118,7 @@ class MagentoWebDriver extends WebDriver
116
118
117
119
/**
118
120
* Sanitizes config, then initializes using parent.
121
+ *
119
122
* @return void
120
123
*/
121
124
public function _initialize ()
@@ -139,6 +142,7 @@ public function _resetConfig()
139
142
140
143
/**
141
144
* Remap parent::_after, called in TestContextExtension
145
+ *
142
146
* @param TestInterface $test
143
147
* @return void
144
148
*/
@@ -149,9 +153,10 @@ public function _runAfter(TestInterface $test)
149
153
150
154
/**
151
155
* Override parent::_after to do nothing.
152
- * @return void
156
+ *
153
157
* @param TestInterface $test
154
158
* @SuppressWarnings(PHPMD)
159
+ * @return void
155
160
*/
156
161
public function _after (TestInterface $ test )
157
162
{
@@ -161,9 +166,9 @@ public function _after(TestInterface $test)
161
166
/**
162
167
* Returns URL of a host.
163
168
*
164
- * @api
165
169
* @return mixed
166
170
* @throws ModuleConfigException
171
+ * @api
167
172
*/
168
173
public function _getUrl ()
169
174
{
@@ -173,22 +178,24 @@ public function _getUrl()
173
178
"Module connection failure. The URL for client can't bre retrieved "
174
179
);
175
180
}
181
+
176
182
return $ this ->config ['url ' ];
177
183
}
178
184
179
185
/**
180
186
* Uri of currently opened page.
181
187
*
182
188
* @return string
183
- * @api
184
189
* @throws ModuleException
190
+ * @api
185
191
*/
186
192
public function _getCurrentUri ()
187
193
{
188
194
$ url = $ this ->webDriver ->getCurrentURL ();
189
195
if ($ url == 'about:blank ' ) {
190
196
throw new ModuleException ($ this , 'Current url is blank, no page was opened ' );
191
197
}
198
+
192
199
return Uri::retrieveUri ($ url );
193
200
}
194
201
@@ -257,6 +264,7 @@ public function grabFromCurrentUrl($regex = null)
257
264
if (!isset ($ matches [1 ])) {
258
265
$ this ->fail ("Nothing to grab. A regex parameter with a capture group is required. Ex: '/(foo)(bar)/' " );
259
266
}
267
+
260
268
return $ matches [1 ];
261
269
}
262
270
@@ -326,13 +334,13 @@ public function closeAdminNotification()
326
334
* @param string $select
327
335
* @param array $options
328
336
* @param boolean $requireAction
329
- * @throws \Exception
330
337
* @return void
338
+ * @throws \Exception
331
339
*/
332
340
public function searchAndMultiSelectOption ($ select , array $ options , $ requireAction = false )
333
341
{
334
- $ selectDropdown = $ select . ' .action-select.admin__action-multiselect ' ;
335
- $ selectSearchText = $ select
342
+ $ selectDropdown = $ select . ' .action-select.admin__action-multiselect ' ;
343
+ $ selectSearchText = $ select
336
344
. ' .admin__action-multiselect-search-wrap>input[data-role="advanced-select-text"] ' ;
337
345
$ selectSearchResult = $ select . ' .admin__action-multiselect-label>span ' ;
338
346
@@ -355,8 +363,8 @@ public function searchAndMultiSelectOption($select, array $options, $requireActi
355
363
* @param string $selectSearchTextField
356
364
* @param string $selectSearchResult
357
365
* @param string[] $options
358
- * @throws \Exception
359
366
* @return void
367
+ * @throws \Exception
360
368
*/
361
369
public function selectMultipleOptions ($ selectSearchTextField , $ selectSearchResult , array $ options )
362
370
{
@@ -393,8 +401,8 @@ public function waitForAjaxLoad($timeout = null)
393
401
* Wait for all JavaScript to finish executing.
394
402
*
395
403
* @param integer $timeout
396
- * @throws \Exception
397
404
* @return void
405
+ * @throws \Exception
398
406
*/
399
407
public function waitForPageLoad ($ timeout = null )
400
408
{
@@ -409,8 +417,8 @@ public function waitForPageLoad($timeout = null)
409
417
* Wait for all visible loading masks to disappear. Gets all elements by mask selector, then loops over them.
410
418
*
411
419
* @param integer $timeout
412
- * @throws \Exception
413
420
* @return void
421
+ * @throws \Exception
414
422
*/
415
423
public function waitForLoadingMaskToDisappear ($ timeout = null )
416
424
{
@@ -438,6 +446,7 @@ public function formatMoney(float $money, $locale = 'en_US.UTF-8')
438
446
$ this ->mResetLocale ();
439
447
$ prefix = substr ($ money , 0 , 1 );
440
448
$ number = substr ($ money , 1 );
449
+
441
450
return ['prefix ' => $ prefix , 'number ' => $ number ];
442
451
}
443
452
@@ -450,6 +459,7 @@ public function formatMoney(float $money, $locale = 'en_US.UTF-8')
450
459
public function parseFloat ($ floatString )
451
460
{
452
461
$ floatString = str_replace (', ' , '' , $ floatString );
462
+
453
463
return floatval ($ floatString );
454
464
}
455
465
@@ -471,6 +481,7 @@ public function mSetLocale(int $category, $locale)
471
481
472
482
/**
473
483
* Reset Locale setting.
484
+ *
474
485
* @return void
475
486
*/
476
487
public function mResetLocale ()
@@ -485,6 +496,7 @@ public function mResetLocale()
485
496
486
497
/**
487
498
* Scroll to the Top of the Page.
499
+ *
488
500
* @return void
489
501
*/
490
502
public function scrollToTopOfPage ()
@@ -493,51 +505,36 @@ public function scrollToTopOfPage()
493
505
}
494
506
495
507
/**
496
- * Takes given $command and executes it against exposed MTF CLI entry point. Returns response from server.
508
+ * Takes given $command and executes it against bin/magento or custom exposed entrypoint. Returns command output.
509
+ *
497
510
* @param string $command
498
511
* @param string $arguments
499
- * @throws TestFrameworkException
500
512
* @return string
513
+ * @throws TestFrameworkException
501
514
*/
502
515
public function magentoCLI ($ command , $ arguments = null )
503
516
{
504
- // Remove index.php if it's present in url
505
- $ baseUrl = rtrim (
506
- str_replace ('index.php ' , '' , rtrim ($ this ->config ['url ' ], '/ ' )),
507
- '/ '
508
- );
509
- $ apiURL = $ baseUrl . '/ ' . ltrim (getenv ('MAGENTO_CLI_COMMAND_PATH ' ), '/ ' );
510
-
511
- $ restExecutor = new WebapiExecutor ();
512
- $ executor = new CurlTransport ();
513
- $ executor ->write (
514
- $ apiURL ,
515
- [
516
- 'token ' => $ restExecutor ->getAuthToken (),
517
- getenv ('MAGENTO_CLI_COMMAND_PARAMETER ' ) => $ command ,
518
- 'arguments ' => $ arguments
519
- ],
520
- CurlInterface::POST ,
521
- []
522
- );
523
- $ response = $ executor ->read ();
524
- $ restExecutor ->close ();
525
- $ executor ->close ();
526
- return $ response ;
517
+ try {
518
+ return $ this ->shellExecMagentoCLI ($ command , $ arguments );
519
+ } catch (\Exception $ exception ) {
520
+ return $ this ->curlExecMagentoCLI ($ command , $ arguments );
521
+ }
527
522
}
528
523
529
524
/**
530
525
* Runs DELETE request to delete a Magento entity against the url given.
526
+ *
531
527
* @param string $url
532
- * @throws TestFrameworkException
533
528
* @return string
529
+ * @throws TestFrameworkException
534
530
*/
535
531
public function deleteEntityByUrl ($ url )
536
532
{
537
533
$ executor = new WebapiExecutor (null );
538
534
$ executor ->write ($ url , [], CurlInterface::DELETE , []);
539
535
$ response = $ executor ->read ();
540
536
$ executor ->close ();
537
+
541
538
return $ response ;
542
539
}
543
540
@@ -547,8 +544,8 @@ public function deleteEntityByUrl($url)
547
544
* @param string $selector
548
545
* @param string $dependentSelector
549
546
* @param boolean $visible
550
- * @throws \Exception
551
547
* @return void
548
+ * @throws \Exception
552
549
*/
553
550
public function conditionalClick ($ selector , $ dependentSelector , $ visible )
554
551
{
@@ -603,6 +600,7 @@ public function assertElementContainsAttribute($selector, $attribute, $value)
603
600
604
601
/**
605
602
* Sets current test to the given test, and resets test failure artifacts to null
603
+ *
606
604
* @param TestInterface $test
607
605
* @return void
608
606
*/
@@ -617,6 +615,7 @@ public function _before(TestInterface $test)
617
615
618
616
/**
619
617
* Override for codeception's default dragAndDrop to include offset options.
618
+ *
620
619
* @param string $source
621
620
* @param string $target
622
621
* @param integer $xOffset
@@ -711,6 +710,7 @@ public function _failed(TestInterface $test, $fail)
711
710
712
711
/**
713
712
* Function which saves a screenshot of the current stat of the browser
713
+ *
714
714
* @return void
715
715
*/
716
716
public function saveScreenshot ()
@@ -730,8 +730,8 @@ public function saveScreenshot()
730
730
* Go to a page and wait for ajax requests to finish
731
731
*
732
732
* @param string $page
733
- * @throws \Exception
734
733
* @return void
734
+ * @throws \Exception
735
735
*/
736
736
public function amOnPage ($ page )
737
737
{
@@ -743,8 +743,8 @@ public function amOnPage($page)
743
743
* Turn Readiness check on or off
744
744
*
745
745
* @param boolean $check
746
- * @throws \Exception
747
746
* @return void
747
+ * @throws \Exception
748
748
*/
749
749
public function skipReadinessCheck ($ check )
750
750
{
@@ -787,6 +787,7 @@ private function getJsErrors()
787
787
$ errors .= "\n" . $ jsError ;
788
788
}
789
789
}
790
+
790
791
return $ errors ;
791
792
}
792
793
@@ -824,4 +825,65 @@ public function makeScreenshot($name = null)
824
825
$ this ->debug ("Screenshot saved to $ screenName " );
825
826
AllureHelper::addAttachmentToCurrentStep ($ screenName , 'Screenshot ' );
826
827
}
828
+
829
+ /**
830
+ * Takes given $command and executes it against bin/magento executable. Returns stdout output from the command.
831
+ *
832
+ * @param string $command
833
+ * @param string $arguments
834
+ *
835
+ * @throws \RuntimeException
836
+ * @return string
837
+ */
838
+ private function shellExecMagentoCLI ($ command , $ arguments ): string
839
+ {
840
+ $ php = PHP_BINDIR ? PHP_BINDIR . DIRECTORY_SEPARATOR . 'php ' : 'php ' ;
841
+ $ binMagento = realpath (MAGENTO_BP . DIRECTORY_SEPARATOR . 'bin ' . DIRECTORY_SEPARATOR . 'magento ' );
842
+ $ command = $ php . ' -f ' . $ binMagento . ' ' . $ command . ' ' . $ arguments ;
843
+ $ process = new Process (escapeshellcmd ($ command ), MAGENTO_BP );
844
+ $ process ->setIdleTimeout (60 );
845
+ $ process ->setTimeout (0 );
846
+ $ exitCode = $ process ->run ();
847
+ if ($ exitCode !== 0 ) {
848
+ throw new \RuntimeException ($ process ->getErrorOutput ());
849
+ }
850
+
851
+ return $ process ->getOutput ();
852
+ }
853
+
854
+ /**
855
+ * Takes given $command and executes it against exposed MTF CLI entry point. Returns response from server.
856
+ *
857
+ * @param string $command
858
+ * @param string $arguments
859
+ * @return string
860
+ * @throws TestFrameworkException
861
+ */
862
+ private function curlExecMagentoCLI ($ command , $ arguments ): string
863
+ {
864
+ // Remove index.php if it's present in url
865
+ $ baseUrl = rtrim (
866
+ str_replace ('index.php ' , '' , rtrim ($ this ->config ['url ' ], '/ ' )),
867
+ '/ '
868
+ );
869
+ $ apiURL = $ baseUrl . '/ ' . ltrim (getenv ('MAGENTO_CLI_COMMAND_PATH ' ), '/ ' );
870
+
871
+ $ restExecutor = new WebapiExecutor ();
872
+ $ executor = new CurlTransport ();
873
+ $ executor ->write (
874
+ $ apiURL ,
875
+ [
876
+ 'token ' => $ restExecutor ->getAuthToken (),
877
+ getenv ('MAGENTO_CLI_COMMAND_PARAMETER ' ) => $ command ,
878
+ 'arguments ' => $ arguments ,
879
+ ],
880
+ CurlInterface::POST ,
881
+ []
882
+ );
883
+ $ response = $ executor ->read ();
884
+ $ restExecutor ->close ();
885
+ $ executor ->close ();
886
+
887
+ return $ response ;
888
+ }
827
889
}
0 commit comments