MOBILE-4110 behat: Clean up js calls
parent
c8b16035fe
commit
52259b421f
|
@ -96,7 +96,7 @@ class behat_app extends behat_app_helper {
|
|||
public function i_wait_the_app_to_restart() {
|
||||
// Wait window to reload.
|
||||
$this->spin(function() {
|
||||
if ($this->js('window.behat.hasInitialized()')) {
|
||||
if ($this->runtime_js('hasInitialized()')) {
|
||||
// Behat runtime shouldn't be initialized after reload.
|
||||
throw new DriverException('Window is not reloading properly.');
|
||||
}
|
||||
|
@ -114,18 +114,18 @@ class behat_app extends behat_app_helper {
|
|||
* @Then /^I should( not)? find (".+")( inside the .+)? in the app$/
|
||||
* @param bool $not Whether assert that the element was not found
|
||||
* @param string $locator Element locator
|
||||
* @param string $containerName Container name
|
||||
* @param string $container Container name
|
||||
*/
|
||||
public function i_find_in_the_app(bool $not, string $locator, string $containerName = '') {
|
||||
public function i_find_in_the_app(bool $not, string $locator, string $container = '') {
|
||||
$locator = $this->parse_element_locator($locator);
|
||||
if (!empty($containerName)) {
|
||||
preg_match('/^ inside the (.+)$/', $containerName, $matches);
|
||||
$containerName = $matches[1];
|
||||
if (!empty($container)) {
|
||||
preg_match('/^ inside the (.+)$/', $container, $matches);
|
||||
$container = $matches[1];
|
||||
}
|
||||
$containerName = json_encode($containerName);
|
||||
$options = json_encode(['containerName' => $container]);
|
||||
|
||||
$this->spin(function() use ($not, $locator, $containerName) {
|
||||
$result = $this->js("return window.behat.find($locator, { containerName: $containerName });");
|
||||
$this->spin(function() use ($not, $locator, $options) {
|
||||
$result = $this->runtime_js("find($locator, $options)");
|
||||
|
||||
if ($not && $result === 'OK') {
|
||||
throw new DriverException('Error, found an element that should not be found');
|
||||
|
@ -151,7 +151,7 @@ class behat_app extends behat_app_helper {
|
|||
$locator = $this->parse_element_locator($locator);
|
||||
|
||||
$this->spin(function() use ($locator) {
|
||||
$result = $this->js("return window.behat.scrollTo($locator);");
|
||||
$result = $this->runtime_js("scrollTo($locator)");
|
||||
|
||||
if ($result !== 'OK') {
|
||||
throw new DriverException('Error finding element - ' . $result);
|
||||
|
@ -174,7 +174,7 @@ class behat_app extends behat_app_helper {
|
|||
*/
|
||||
public function i_load_more_items_in_the_app(bool $not = false) {
|
||||
$this->spin(function() use ($not) {
|
||||
$result = $this->js('return await window.behat.loadMoreItems();');
|
||||
$result = $this->runtime_js('loadMoreItems()');
|
||||
|
||||
if ($not && $result !== 'ERROR: All items are already loaded.') {
|
||||
throw new DriverException('It should not have been possible to load more items');
|
||||
|
@ -199,7 +199,7 @@ class behat_app extends behat_app_helper {
|
|||
public function i_swipe_in_the_app(string $direction) {
|
||||
$method = 'swipe' . ucwords($direction);
|
||||
|
||||
$this->js("window.behat.getAngularInstance('ion-content', 'CoreSwipeNavigationDirective').$method()");
|
||||
$this->runtime_js("getAngularInstance('ion-content', 'CoreSwipeNavigationDirective').$method()");
|
||||
|
||||
$this->wait_for_pending_js();
|
||||
|
||||
|
@ -218,7 +218,7 @@ class behat_app extends behat_app_helper {
|
|||
$locator = $this->parse_element_locator($locator);
|
||||
|
||||
$this->spin(function() use ($locator, $not) {
|
||||
$result = $this->js("return window.behat.isSelected($locator);");
|
||||
$result = $this->runtime_js("isSelected($locator)");
|
||||
|
||||
switch ($result) {
|
||||
case 'YES':
|
||||
|
@ -325,7 +325,7 @@ class behat_app extends behat_app_helper {
|
|||
$this->login($username);
|
||||
}
|
||||
|
||||
$mycoursesfound = $this->js("return window.behat.find({ text: 'My courses', selector: 'ion-tab-button'});");
|
||||
$mycoursesfound = $this->runtime_js("find({ text: 'My courses', selector: 'ion-tab-button'})");
|
||||
|
||||
if ($mycoursesfound !== 'OK') {
|
||||
// My courses not present enter from Dashboard.
|
||||
|
@ -381,7 +381,7 @@ class behat_app extends behat_app_helper {
|
|||
*/
|
||||
public function i_press_the_standard_button_in_the_app(string $button) {
|
||||
$this->spin(function() use ($button) {
|
||||
$result = $this->js("return await window.behat.pressStandard('$button');");
|
||||
$result = $this->runtime_js("pressStandard('$button')");
|
||||
|
||||
if ($result !== 'OK') {
|
||||
throw new DriverException('Error pressing standard button - ' . $result);
|
||||
|
@ -419,7 +419,7 @@ class behat_app extends behat_app_helper {
|
|||
],
|
||||
]);
|
||||
|
||||
$this->js("window.behat.notificationClicked($notification)");
|
||||
$this->zone_js("pushNotifications.notificationClicked($notification)", true);
|
||||
$this->wait_for_pending_js();
|
||||
}
|
||||
|
||||
|
@ -507,7 +507,7 @@ class behat_app extends behat_app_helper {
|
|||
*/
|
||||
public function i_close_the_popup_in_the_app() {
|
||||
$this->spin(function() {
|
||||
$result = $this->js("return window.behat.closePopup();");
|
||||
$result = $this->runtime_js('closePopup()');
|
||||
|
||||
if ($result !== 'OK') {
|
||||
throw new DriverException('Error closing popup - ' . $result);
|
||||
|
@ -545,7 +545,7 @@ class behat_app extends behat_app_helper {
|
|||
$locator = $this->parse_element_locator($locator);
|
||||
|
||||
$this->spin(function() use ($locator) {
|
||||
$result = $this->js("return await window.behat.press($locator);");
|
||||
$result = $this->runtime_js("press($locator)");
|
||||
|
||||
if ($result !== 'OK') {
|
||||
throw new DriverException('Error pressing item - ' . $result);
|
||||
|
@ -588,7 +588,7 @@ class behat_app extends behat_app_helper {
|
|||
$locator = $this->parse_element_locator($locator);
|
||||
|
||||
$this->spin(function() use ($not, $locator) {
|
||||
$result = $this->js("return window.behat.find($locator, { onlyClickable: true });");
|
||||
$result = $this->runtime_js("find($locator, { onlyClickable: true })");
|
||||
|
||||
if ($not && $result === 'OK') {
|
||||
throw new DriverException('Error, found a clickable element that should not be found');
|
||||
|
@ -622,14 +622,14 @@ class behat_app extends behat_app_helper {
|
|||
|
||||
$this->spin(function() use ($selectedtext, $selected, $locator) {
|
||||
// Don't do anything if the item is already in the expected state.
|
||||
$result = $this->js("return window.behat.isSelected($locator);");
|
||||
$result = $this->runtime_js("isSelected($locator)");
|
||||
|
||||
if ($result === $selected) {
|
||||
return true;
|
||||
}
|
||||
|
||||
// Press element.
|
||||
$result = $this->js("return await window.behat.press($locator);");
|
||||
$result = $this->runtime_js("press($locator)");
|
||||
|
||||
if ($result !== 'OK') {
|
||||
throw new DriverException('Error pressing element - ' . $result);
|
||||
|
@ -638,7 +638,7 @@ class behat_app extends behat_app_helper {
|
|||
// Check that it worked as expected.
|
||||
$this->wait_for_pending_js();
|
||||
|
||||
$result = $this->js("return window.behat.isSelected($locator);");
|
||||
$result = $this->runtime_js("isSelected($locator)");
|
||||
|
||||
switch ($result) {
|
||||
case 'YES':
|
||||
|
@ -672,7 +672,7 @@ class behat_app extends behat_app_helper {
|
|||
$value = addslashes_js($value);
|
||||
|
||||
$this->spin(function() use ($field, $value) {
|
||||
$result = $this->js("return await window.behat.setField(\"$field\", \"$value\");");
|
||||
$result = $this->runtime_js("setField('$field', '$value')");
|
||||
|
||||
if ($result !== 'OK') {
|
||||
throw new DriverException('Error setting field - ' . $result);
|
||||
|
@ -711,7 +711,7 @@ class behat_app extends behat_app_helper {
|
|||
*/
|
||||
public function the_header_should_be_in_the_app(string $text) {
|
||||
$this->spin(function() use ($text) {
|
||||
$result = $this->js('return window.behat.getHeader();');
|
||||
$result = $this->runtime_js('getHeader()');
|
||||
|
||||
if (substr($result, 0, 3) !== 'OK:') {
|
||||
throw new DriverException('Error getting header - ' . $result);
|
||||
|
@ -792,7 +792,7 @@ class behat_app extends behat_app_helper {
|
|||
* @When I run cron tasks in the app
|
||||
*/
|
||||
public function i_run_cron_tasks_in_the_app() {
|
||||
$this->js('await window.behat.forceSyncExecution()');
|
||||
$this->zone_js('cronDelegate.forceSyncExecution()');
|
||||
$this->wait_for_pending_js();
|
||||
}
|
||||
|
||||
|
@ -802,7 +802,7 @@ class behat_app extends behat_app_helper {
|
|||
* @When I wait loading to finish in the app
|
||||
*/
|
||||
public function i_wait_loading_to_finish_in_the_app() {
|
||||
$this->js('await window.behat.waitLoadingToFinish()');
|
||||
$this->runtime_js('waitLoadingToFinish()');
|
||||
$this->wait_for_pending_js();
|
||||
}
|
||||
|
||||
|
@ -824,7 +824,7 @@ class behat_app extends behat_app_helper {
|
|||
$this->getSession()->switchToWindow($names[1]);
|
||||
}
|
||||
|
||||
$this->js('window.close();');
|
||||
$this->js('window.close()');
|
||||
$this->getSession()->switchToWindow($names[0]);
|
||||
}
|
||||
|
||||
|
@ -836,7 +836,7 @@ class behat_app extends behat_app_helper {
|
|||
* @throws DriverException If the navigator.online mode is not available
|
||||
*/
|
||||
public function i_switch_offline_mode(string $offline) {
|
||||
$this->js("window.behat.network.setForceOffline($offline);");
|
||||
$this->runtime_js("network.setForceOffline($offline)");
|
||||
}
|
||||
|
||||
}
|
||||
|
|
|
@ -313,12 +313,12 @@ class behat_app_helper extends behat_base {
|
|||
|
||||
try {
|
||||
// Init Behat JavaScript runtime.
|
||||
$initoptions = json_encode([
|
||||
'skipOnBoarding' => $options['skiponboarding'] ?? true,
|
||||
'configOverrides' => $this->appconfig,
|
||||
]);
|
||||
|
||||
$initOptions = new StdClass();
|
||||
$initOptions->skipOnBoarding = $options['skiponboarding'] ?? true;
|
||||
$initOptions->configOverrides = $this->appconfig;
|
||||
|
||||
$this->js('window.behat.init(' . json_encode($initOptions) . ');');
|
||||
$this->runtime_js("init($initoptions)");
|
||||
} catch (Exception $error) {
|
||||
throw new DriverException('Moodle App not running or not running on Automated mode.');
|
||||
}
|
||||
|
@ -456,7 +456,7 @@ class behat_app_helper extends behat_base {
|
|||
|
||||
$res = $this->evaluate_script("Promise.resolve($script)
|
||||
.then(result => window.$promisevariable = result)
|
||||
.catch(error => window.$promisevariable = 'Async code rejected: ' + error?.message);");
|
||||
.catch(error => window.$promisevariable = 'Async code rejected: ' + error?.message)");
|
||||
|
||||
do {
|
||||
if (microtime(true) - $start > $timeout) {
|
||||
|
@ -465,15 +465,42 @@ class behat_app_helper extends behat_base {
|
|||
|
||||
// 0.1 seconds.
|
||||
usleep(100000);
|
||||
} while (!$this->evaluate_script("return '$promisevariable' in window;"));
|
||||
} while (!$this->evaluate_script("'$promisevariable' in window"));
|
||||
|
||||
$result = $this->evaluate_script("return window.$promisevariable;");
|
||||
$result = $this->evaluate_script("window.$promisevariable");
|
||||
|
||||
$this->evaluate_script("delete window.$promisevariable;");
|
||||
$this->evaluate_script("delete window.$promisevariable");
|
||||
|
||||
if (is_string($result) && strrpos($result, 'Async code rejected:') === 0) {
|
||||
throw new DriverException($result);
|
||||
}
|
||||
|
||||
return $result;
|
||||
}
|
||||
|
||||
/**
|
||||
* Evaluate and execute methods from the Behat runtime.
|
||||
*
|
||||
* @param string $script
|
||||
* @return mixed Result.
|
||||
*/
|
||||
protected function runtime_js(string $script) {
|
||||
return $this->js("window.behat.$script");
|
||||
}
|
||||
|
||||
/**
|
||||
* Evaluate and execute methods from the Behat runtime inside the Angular zone.
|
||||
*
|
||||
* @param string $script
|
||||
* @param bool $blocking
|
||||
* @return mixed Result.
|
||||
*/
|
||||
protected function zone_js(string $script, bool $blocking = false) {
|
||||
$blockingjson = json_encode($blocking);
|
||||
|
||||
return $this->runtime_js("runInZone(() => window.behat.$script, $blockingjson)");
|
||||
}
|
||||
|
||||
/**
|
||||
* Opens a custom URL for automatic login and redirect from the Moodle App (and waits to finish.)
|
||||
*
|
||||
|
@ -548,8 +575,7 @@ class behat_app_helper extends behat_base {
|
|||
* @param string $successXPath The XPath of the element to lookat after navigation.
|
||||
*/
|
||||
protected function handle_url(string $customurl, string $successXPath = '') {
|
||||
// Instead of using evaluate_async_script, we wait for the path to load.
|
||||
$result = $this->js("return await window.behat.handleCustomURL('$customurl');");
|
||||
$result = $this->zone_js("customUrlSchemes.handleCustomURL('$customurl')");
|
||||
|
||||
if ($result !== 'OK') {
|
||||
throw new DriverException('Error handling url - ' . $result);
|
||||
|
|
|
@ -178,7 +178,7 @@ class performance_measure implements behat_app_listener {
|
|||
* @return int Current time in milliseconds.
|
||||
*/
|
||||
private function now(): int {
|
||||
return $this->driver->evaluateScript('Date.now();');
|
||||
return $this->driver->evaluateScript('Date.now()');
|
||||
}
|
||||
|
||||
/**
|
||||
|
|
|
@ -14,17 +14,14 @@
|
|||
|
||||
import { TestingBehatDomUtils } from './behat-dom';
|
||||
import { TestingBehatBlocking } from './behat-blocking';
|
||||
import { CoreCustomURLSchemes } from '@services/urlschemes';
|
||||
import { CoreCustomURLSchemes, CoreCustomURLSchemesProvider } from '@services/urlschemes';
|
||||
import { CoreLoginHelperProvider } from '@features/login/services/login-helper';
|
||||
import { CoreConfig } from '@services/config';
|
||||
import { EnvironmentConfig } from '@/types/config';
|
||||
import { makeSingleton, NgZone } from '@singletons';
|
||||
import { CoreNetwork, CoreNetworkService } from '@services/network';
|
||||
import {
|
||||
CorePushNotifications,
|
||||
CorePushNotificationsNotificationBasicData,
|
||||
} from '@features/pushnotifications/services/pushnotifications';
|
||||
import { CoreCronDelegate } from '@services/cron';
|
||||
import { CorePushNotifications, CorePushNotificationsProvider } from '@features/pushnotifications/services/pushnotifications';
|
||||
import { CoreCronDelegate, CoreCronDelegateService } from '@services/cron';
|
||||
import { CoreLoadingComponent } from '@components/loading/loading';
|
||||
import { CoreComponentsRegistry } from '@singletons/components-registry';
|
||||
import { CoreDom } from '@singletons/dom';
|
||||
|
@ -40,10 +37,22 @@ export class TestingBehatRuntimeService {
|
|||
|
||||
protected initialized = false;
|
||||
|
||||
get cronDelegate(): CoreCronDelegateService {
|
||||
return CoreCronDelegate.instance;
|
||||
}
|
||||
|
||||
get customUrlSchemes(): CoreCustomURLSchemesProvider {
|
||||
return CoreCustomURLSchemes.instance;
|
||||
}
|
||||
|
||||
get network(): CoreNetworkService {
|
||||
return CoreNetwork.instance;
|
||||
}
|
||||
|
||||
get pushNotifications(): CorePushNotificationsProvider {
|
||||
return CorePushNotifications.instance;
|
||||
}
|
||||
|
||||
/**
|
||||
* Init behat functions and set options like skipping onboarding.
|
||||
*
|
||||
|
@ -78,53 +87,25 @@ export class TestingBehatRuntimeService {
|
|||
}
|
||||
|
||||
/**
|
||||
* Handles a custom URL.
|
||||
* Run an operation inside the angular zone and return result.
|
||||
*
|
||||
* @param url Url to open.
|
||||
* @param operation Operation callback.
|
||||
* @return OK if successful, or ERROR: followed by message.
|
||||
*/
|
||||
async handleCustomURL(url: string): Promise<string> {
|
||||
async runInZone(operation: () => unknown, blocking: boolean = false): Promise<string> {
|
||||
const blockKey = blocking && TestingBehatBlocking.block();
|
||||
|
||||
try {
|
||||
await NgZone.run(async () => {
|
||||
await CoreCustomURLSchemes.handleCustomURL(url);
|
||||
});
|
||||
await NgZone.run(operation);
|
||||
|
||||
return 'OK';
|
||||
} catch (error) {
|
||||
return 'ERROR: ' + error.message;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Function called when a push notification is clicked. Redirect the user to the right state.
|
||||
*
|
||||
* @param data Notification data.
|
||||
* @return Promise resolved when done.
|
||||
*/
|
||||
async notificationClicked(data: CorePushNotificationsNotificationBasicData): Promise<void> {
|
||||
const blockKey = TestingBehatBlocking.block();
|
||||
|
||||
try {
|
||||
await NgZone.run(async () => {
|
||||
await CorePushNotifications.notificationClicked(data);
|
||||
});
|
||||
} finally {
|
||||
TestingBehatBlocking.unblock(blockKey);
|
||||
blockKey && TestingBehatBlocking.unblock(blockKey);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Force execution of synchronization cron tasks without waiting for the scheduled time.
|
||||
* Please notice that some tasks may not be executed depending on the network connection and sync settings.
|
||||
*
|
||||
* @return Promise resolved if all handlers are executed successfully, rejected otherwise.
|
||||
*/
|
||||
async forceSyncExecution(): Promise<void> {
|
||||
await NgZone.run(async () => {
|
||||
await CoreCronDelegate.forceSyncExecution();
|
||||
});
|
||||
}
|
||||
|
||||
/**
|
||||
* Wait all controlled components to be rendered.
|
||||
*
|
||||
|
|
Loading…
Reference in New Issue