Commit 977f08cf authored by Robert Lyon's avatar Robert Lyon Committed by Gerrit Code Review

Merge "Bug 1575512: Better way to check if a page is ready for behat tests"

parents 2335e999 f27e5ebf
......@@ -266,11 +266,9 @@ jQuery(function($) {
}
function changemenu() {
isPageRendering = true;
selectedmenu = $('#menuselect').val();
getitems();
getadminfiles();
isPageRendering = false;
}
var selectedmenu = 'loggedoutmenu';
......
......@@ -408,34 +408,6 @@ EOF;
}
public static function get_instance_config_javascript(BlockInstance $instance) {
return <<<EOF
jQuery(function($) {
$('#instconf_tagselect').on('change', function() {
// Need a small delay so that MultipleSelection.prototype.update will
// fire before updatetagbuttons
setTimeout(updatetagbuttons, 1000);
});
updatetagbuttons();
function updatetagbuttons() {
$('#instconf_tagselect_container ul button').on('click', function(e) {
e.stopPropagation();
e.preventDefault();
var li = $(this).parent();
var new_data = jQuery.grep($('#instconf_tagselect').select2('data'), function (value) {
if (value['id'] == li[0].title) {
$("#instconf_tagselect option[value='" + value['id'] + "']").remove();
$('#instconf_tagselect').trigger('change');
}
});
});
}
});
EOF;
}
public static function instance_config_validate(Pieform $form, $values) {
if (empty($values['tagselect'])) {
......
......@@ -14,7 +14,6 @@ function Slideshow(id, count) {
$j("#description_" + id + "_" + this.current).css('display', 'none');
}
$j(this.id).height($j(this.id + " img:eq(" + this.current + ")").height() + 10);
isPageRendering = true;
$j(this.id + " img:eq(" + this.current + ")").fadeOut(500, function() {
var extraheight = 0;
self.current = to;
......@@ -24,7 +23,6 @@ function Slideshow(id, count) {
}
$j(self.id).height($j(self.id + " img:eq(" + self.current + ")").height() + extraheight + 10);
$j(self.id + " img:eq(" + self.current + ")").fadeIn(500);
isPageRendering = false;
});
$j(this.id + ' td.control span').removeClass('disabled');
if (to == 0) {
......
......@@ -44,6 +44,7 @@ var FileBrowser = (function($) {
};
this.submitform = function () {
window.isRequestProcessing = true;
// for some reason tinymce throws error when use native submit..
// introducing custom event and catching it in pieform solves the problem...
// TODO: fileuploader should be refactored in a nicer way
......
......@@ -230,30 +230,17 @@ function displayMessage(message, type, hideprevmsg) {
jQuery('#messages').append(message);
if (hideprevmsg || typeof(hideprevmsg) === 'undefined') {
isPageRendering = true;
oldmessage.fadeOut(200, function() {
$j(this).remove();
isPageRendering = false;
});
}
}
/**
* This variable determines the completeness of a json request
* = true if the request is still in progress
*/
var isRequestStillProcessing = false;
/**
* This variable determines the completeness of a page rendering
* = true if the rendering is still in progress
*/
var isPageRendering = false;
/**
* Display a nice little loading notification
*/
function processingStart(msg) {
window.isRequestProcessing = true;
if (!msg) {
msg = get_string('loading');
}
......@@ -265,8 +252,6 @@ function processingStart(msg) {
'</div>'
);
jQuery('.loading-box .loading-message').text(msg);
isRequestStillProcessing = true;
}
/**
......@@ -275,8 +260,8 @@ function processingStart(msg) {
function processingStop() {
setTimeout(function() {
jQuery('.loading-box').addClass('hidden');
isRequestStillProcessing = false;
}, 100); //give users enough time to see the loading indicator
window.isRequestProcessing = false;
}
/**
......@@ -338,6 +323,7 @@ function sendjsonrequest(url, data, method, successcallback, errorcallback, quie
request.done(function(data) {
var error = data.error;
// It may take a while to render the page after AJAX requests
if (typeof(data.message) === 'object' && data.message !== null) {
data = data.message;
}
......
......@@ -214,6 +214,13 @@
function attachAccordion(){
// Update the status of a collapsible block category by adding/removing class 'expanded'
$j('div#content-editor-foldable div.block-category-title').on('click', function() {
// Collapse all other expanded category
$j(this).parent().find('div.expanded').toggleClass('expanded');
$j(this).toggleClass('expanded');
});
contentEditor.find('.btn-accordion').accordion({
icons: false,
heightStyle: 'content',
......@@ -221,7 +228,10 @@
active: false,
header: ".block-category-title",
activate: function(event, ui) {
var active = $(this).find('.ui-state-active');
// When all animation is off ($j.fx.off == true)
// We can not rely on the class 'ui-state-active' as it is only
// added when accordion widget animation functions are activated
var active = $(this).find('.expanded');
if (active.length) {
var category = active.next('div'),
categoryid = category.attr('id'),
......@@ -244,6 +254,7 @@
}
}
});
}
function attachToolbarToggle (){
......
......@@ -22,6 +22,18 @@ require_once(get_config('docroot') . 'lib/activity.php');
require_once(get_config('docroot') . 'lib/file.php');
require_once(get_config('docroot') . 'webservice/lib.php');
// If we are running behat tests, we only run cron via the behat step:
// I trigger (the )?cron
if (defined('BEHAT_TEST')) {
if (php_sapi_name() == 'cli') {
die_info("Can not run cron from command line when behat environment is enabled");
}
$behattrigger = param_boolean('behattrigger', false);
if (!$behattrigger) {
die_info("Missing or disabled behattrigger. When behat environment is enabled, cron can only triggered using the step: I trigger (the )?cron");
}
}
// Check if we have come via browser and have the right urlsecret
// Note: if your crontab hits this file via curl/http thenyou will need
// to add the urlsecret there for the cron to work.
......
......@@ -988,7 +988,14 @@ class Pieform {/*{{{*/
exit;
}
echo <<<EOF
<html><head><script type="application/javascript">function sendResult() { parent.pieformHandlers["{$this->name}"]($result); }</script></head><body onload="sendResult(); "></body></html>
<html>
<head><script type="application/javascript">
function sendResult() {
parent.pieformHandlers["{$this->name}"]($result);
}
</script></head>
<body onload="sendResult();"></body>
</html>
EOF;
exit;
}/*}}}*/
......
......@@ -133,6 +133,7 @@ var PieformManager = (function($) {
}(jQuery));
PieformManager = new PieformManager();
/**
* Handles the javascript side of pieforms - submitting the form via a hidden
* iframe and dealing with the result
......@@ -189,6 +190,8 @@ var Pieform = (function($) {
window.location = data.location;
return;
}
// The pieform is rendering
window.isPieformRendering = true;
if (typeof(data.replaceHTML) == 'string') {
PieformManager.signal('onreply', self.data.name);
......@@ -264,6 +267,9 @@ var Pieform = (function($) {
&& self.data.postSubmitCallback != '') {
window[self.data.postSubmitCallback]($('#' + self.data.name)[0], self.clickedButton, e);
}
// The pieform rendering is done.
window.isPieformRendering = false;
}
};
......
......@@ -269,6 +269,17 @@ function smarty($javascript = array(), $headers = array(), $pagestrings = array(
$pagestrings['mahara'] = isset($pagestrings['mahara']) ? $pagestrings['mahara'] : array();
$pagestrings['mahara'][] = 'attachedimage';
$tinymceinitbehatsetup = '';
$tinymcebehatsetup = '';
if (defined('BEHAT_TEST')) {
$tinymceinitbehatsetup = 'window.isEditorInitializing = false;';
$tinymcebehatsetup = <<<EOF
ed.on('PreInit', function(ed) {
window.isEditorInitializing = true;
});
EOF;
}
if ($check[$key] == 'tinymce') {
$tinymceconfig = <<<EOF
theme: "modern",
......@@ -318,7 +329,9 @@ tinyMCE.init({
cache_suffix: '?v={$CFG->cacheversion}',
{$extramceconfig}
setup: function(ed) {
{$tinymcebehatsetup}
ed.on('init', function(ed) {
{$tinymceinitbehatsetup}
if (typeof(editor_to_focus) == 'string' && ed.editorId == editor_to_focus) {
ed.focus();
}
......@@ -512,6 +525,12 @@ EOF;
$javascript_array[] = $jsroot . 'formchangechecker.js';
$javascript_array[] = $jsroot . 'textareamaxlengthchecker.js';
// Load some event handler functions for checking if all AJAX requests have completed
// when running behat tests
if (defined('BEHAT_TEST')) {
$javascript_array[] = get_config('wwwroot') . 'testing/frameworks/behat/page_status.js';
}
foreach ($jsstrings['mahara'] as $section => $tags) {
foreach ($tags as $tag) {
$strings[$tag] = get_raw_string($tag, $section);
......
......@@ -58,10 +58,7 @@ class BehatBase extends Behat\MinkExtension\Context\RawMinkContext {
/**
* The JS code to check that the page is ready.
*/
const PAGE_READY_JS = '(isRequestStillProcessing === false) &&
(isPageRendering === false) &&
(document.readyState === "complete") &&
(jQuery(".collapsing").length === 0)';
const PAGE_READY_JS = 'window.isMaharaPageReady()';
/**
* @var Escaper
......
......@@ -111,9 +111,11 @@ class BehatForms extends BehatBase {
$page = $this->getSession()->getPage();
foreach(preg_split('/,\s*/', $textValues) as $value) {
$option = $page->find('xpath', '//select[@id="' . $field . '"]//option[text()="' . $value . '"]');
$value = $option->getAttribute('value');
$value = json_encode($value);
$this->getSession()->executeScript("jQuery('#{$field} option[value=" . $value . "]').remove();");
if ($option) {
$value = $option->getAttribute('value');
$value = json_encode($value);
$this->getSession()->executeScript("jQuery('#{$field} option[value=" . $value . "]').remove();");
}
}
$this->getSession()->executeScript("jQuery('#{$field}').trigger('change');");
}
......
......@@ -1012,7 +1012,7 @@ class BehatGeneral extends BehatBase {
foreach(plugin_types() as $plugintype) {
set_field($plugintype . '_cron', 'nextrun', null);
}
$this->getSession()->visit($this->locate_path('/lib/cron.php?urlsecret=' . urlencode(get_config('urlsecret'))));
$this->getSession()->visit($this->locate_path('/lib/cron.php?behattrigger=1&urlsecret=' . urlencode(get_config('urlsecret'))));
}
/**
......
/**
*
* @package mahara
* @subpackage behat
* @author Catalyst IT Ltd
* @license http://www.gnu.org/copyleft/gpl.html GNU GPL version 3 or later
* @copyright For copyright information on Mahara, please see the README file distributed with this software.
* @copyright (C) portions from Moodle, (C) Martin Dougiamas http://dougiamas.com
*/
/**
* This variable determines the completeness of a request
* = true if the request is still in progress
*/
window.isRequestProcessing = false;
/**
* This variable determines if pieforms are rendering by their js handlers
* = true if the rendering is still in progress
*/
window.isPieformRendering = false;
/**
* This variable determines if tinyMCE is initializing
* = true if it is in progress
*/
window.isEditorInitializing = false;
/**
* This variable determines if modal window is rendering by js
* = true if the rendering is still in progress
*/
window.isModalRendering = false;
function isMaharaPageReady() {
return (window.isRequestProcessing === false)
&& (window.isPieformRendering === false)
&& (window.isEditorInitializing === false)
&& (window.isModalRendering === false)
&& (document.readyState === "complete");
}
jQuery(document).ready(function() {
/**
* Listening for ajax events
*/
jQuery(document).ajaxStart(function() {
window.isRequestProcessing = true;
});
jQuery(document).ajaxStop(function() {
window.isRequestProcessing = false;
});
/**
* Remove boostrap modal animation
*/
jQuery('.modal').removeClass('fade');
/**
* Update the page status while showing the Bootstrap's modal pop-up
*/
jQuery('.modal').on('show.bs.modal', function (event) {
window.isModalRendering = true;
});
jQuery('.modal').on('shown.bs.modal', function (event) {
window.isModalRendering = false;
});
/**
* Disable all jQuery animations e.g. fadeIn/Out(), toogle(), animation()
*/
jQuery.fx.off = true;
/**
* Disable bootstrap transitions
*/
jQuery.support.transition = false;
});
......@@ -53,6 +53,12 @@
},
{{$extraparams|safe}}
});
jQuery("#{{$id}}").on('select2:select', function(e) {
window.pageIsRendering = false;
});
jQuery("#{{$id}}").on('select2:unselect', function(e) {
window.pageIsRendering = false;
});
{{if !$inblockconfig}}
});
{{/if}}
......
@javascript @core @core_account
@javascript @core
Feature: Registration procedure
In order to check that a person can register
As an admin
......
......@@ -23,7 +23,5 @@ Scenario: Create users by csv (Bug 1426983)
And I follow "kevin01"
And I follow "Suspend or delete this user"
And I scroll to the id "delete"
# Wait for the dialog to appear
And I wait "1" seconds
And I press and confirm "Delete user"
And I should see "User deleted successfully"
......@@ -6,10 +6,10 @@ So admin can view the message in their inbox
Scenario: Checking that admin user can view messages in their mail sent from Contact us page
Given I follow "contact us"
And I set the field "Name" to "Dean"
And I set the field "Email" to "deans@catalyst.net.nz"
And I set the field "Subject" to "Whats wrong"
And I set the field "Message" to "hello world"
And I fill in "Name" with "Dean"
And I fill in "Email" with "deans@catalyst.net.nz"
And I fill in "Subject" with "Whats wrong"
And I fill in "Message" with "hello world"
# to avoid 5-second spam trap on contact.php
And I wait "5" seconds
When I click on "Send message"
......
......@@ -23,20 +23,17 @@ Scenario: Creating and deleting external links (Selenium 1426983)
Then I should see "Test Menu Link"
And I choose "Menus" in "Configure site" from administration menu
And I select "Logged-in links and resources" from "Edit:"
#And I wait until the page is ready
#And I press "Delete"
And I delete the link and resource menu item "Test Menu Link"
#And I accept the confirm popup
And I should see "Item deleted"
And I press "Save changes"
# Flicking the switches to the opposite
# Flicking the switches to the opposite
And I enable the switch "Terms and conditions"
And I disable the following switches:
| Privacy statement |
| About |
| Contact us |
And I press "Save changes"
# Checking the switches held the setting
# Checking the switches held the setting
And the following fields match these values:
| Terms and conditions | 1 |
| Privacy statement | 0 |
......
......@@ -21,7 +21,6 @@ I can create a new page from the site default portfolio page
# Add a text block
And I follow "Text"
And I press "Add"
And I wait "1" seconds
And I set the following fields to these values:
| Block title | Sample text block |
| Block content | <p>Lorem Ipsum is simply dummy text of the printing and typesetting industry. Lorem Ipsum has been the industry's standard dummy text ever since the 1500s, when an unknown printer took a galley of type and scrambled it to make a type specimen book.</p> |
......
......@@ -8,7 +8,6 @@ Scenario: Registered data that is sent (Bug 1447865)
Given I log in as "admin" with password "Kupuhipa1"
And I choose "Register" in "Admin home" from administration menu
When I expand all fieldsets
And I wait "1" seconds
Then I should see "phpversion"
And I should see "dbversion"
And I should see "osversion"
......
......@@ -7,7 +7,6 @@ So I can check the field doesn't error
Scenario: sql injection attempt on search field
Given I log in as "admin" with password "Kupuhipa1"
And I wait "1" seconds
When I set the following fields to these values:
| Search users | 'or 1=1;-- |
And I press "Go"
......
......@@ -17,14 +17,12 @@ Scenario: Making adjustments to the mathslate plugin for mahara (Bug 1472446)
| Page title | test |
| Page description | testing |
And I press "Save"
And I wait "1" seconds
And I choose "Pages and collections" in "Configure site" from administration menu
And I follow "test"
# Tinymce field adding a math equation
And I scroll to the id "feedbacktable"
And I fill in "\\[\\alpha A\\beta B\\]" in editor "Comment"
And I press "Comment"
And I wait "1" seconds
And I choose "Pages and collections" in "Configure site" from administration menu
And I follow "test"
And I should see "αAβB"
......@@ -38,7 +38,6 @@ Feature: Mahara users can create their blogs
And I click on "Page" in the dialog
And I press "Save"
And I expand "Journals" node in the "div#content-editor-foldable" "css_element"
And I wait "1" seconds
And I follow "Tagged journal entries"
And I press "Add"
And I fill in select2 input "instconf_tagselect" with "blogentry" and select "blogentry"
......
......@@ -17,14 +17,14 @@ Scenario: Clicking on the journal sub menu headings and adding first journal (Bu
When I choose "Journals" in "Configure site" from administration menu
And I follow "Create journal"
And I should see "New site journal:"
And I fill in "Title" with "Site Journal 1"
And I set the following fields to these values:
| Title | Site Journal 1 |
| Description | The first mahara institution journal |
And I click on "Create journal"
Then I should see "Site journal 1"
And I follow "Create journal"
And I fill in "Title" with "Site Journal 2"
And I set the following fields to these values:
| Title | Site Journal 2 |
| Description | The second mahara institution journal |
And I click on "Create journal"
Then I should see "Site journal 2"
......@@ -33,14 +33,14 @@ Scenario: Clicking on the journal sub menu headings and adding first journal (Bu
When I choose "Journals" in "Institutions" from administration menu
And I follow "Create journal"
And I should see "New \"Institution One\" journal:"
And I fill in "Title" with "Institution One Journal 1"
And I set the following fields to these values:
| Title | Institution One Journal 1 |
| Description | The Institution One journal |
And I click on "Create journal"
Then I should see "Institution One Journal 1"
And I follow "Create journal"
And I fill in "Title" with "Institution One Journal 2"
And I set the following fields to these values:
| Title | Institution One Journal 2 |
| Description | Another Institution One journal |
And I click on "Create journal"
Then I should see "Institution One Journal 2"
......@@ -50,8 +50,8 @@ Scenario: Clicking on the journal sub menu headings and adding first journal (Bu
And I should not see "Institution One Journal 1"
And I follow "Create journal"
And I should see "New \"Institution Two\" journal:"
And I fill in "Title" with "Institution Two Journal 1"
And I set the following fields to these values:
| Title | Institution Two Journal 1 |
| Description | The Institution Two journal |
And I click on "Create journal"
Then I should see "Institution Two Journal 1"
......@@ -59,21 +59,19 @@ Scenario: Clicking on the journal sub menu headings and adding first journal (Bu
# Try adding some journal entries to the journal
And I follow "New entry"
And I should see "New journal entry in journal \"Institution Two Journal 1\""
And I fill in "Title *" with "Journal entry 1"
And I set the following fields to these values:
| Title * | Journal entry 1 |
| Entry * | The contents of this entry |
And I click on "Save entry"
Then I should see "Journal entry saved"
And I follow "New entry"
And I fill in "Title *" with "Journal entry 2"
And I set the following fields to these values:
| Title * | Journal entry 2 |
| Entry * | The contents of this entry |
And I click on "Add a file"
And I wait "1" seconds
And I attach the file "Image1.jpg" to "File"
Then I should see "Image1.jpg" in the "table#editpost_filebrowser_selectlist" element
Then I should see "Upload of Image1.jpg complete"
When I close the dialog
And I wait "1" seconds
And I press "Save entry"
Then I should see "Journal entry 1"
And I should see "Journal entry 2"
......@@ -91,8 +89,8 @@ Scenario: Newly created user can get a copy of the journal (Bug 1472467)
| Description | Contents of site journal 1 |
And I press "Create journal"
And I follow "New entry"
And I fill in "Title *" with "Spongebob"
And I set the following fields to these values:
| Title * | Spongebob |
| Entry * | *)_4442)&@*#&^%%!+_()**&gha~gsd |
And I press "Save entry"
And I should see "Journal entry saved"
......@@ -106,14 +104,11 @@ Scenario: Newly created user can get a copy of the journal (Bug 1472467)
| Page description | hsdfhjkl78695t 8677y8 |
And I press "Save"
# Adding journal block to the page
And I wait until the page is ready
# Need to access the adding "Journal" block more directly than normal now that "Journals" is a menu item also
And I expand "Journals" node in the "div#content-editor-foldable" "css_element"
And I wait "1" seconds
And I follow "Journal" in the "div#blog" "css_element"
And I press "Add"
#And I select the radio "Site journal 1"
And I set the field "Site journal 1" to "1"
And I select the radio "Site journal 1"
And I select "Others will get their own copy of your journal" from "Block copy permission"
And I press "Save"
And I scroll to the id "main-nav"
......@@ -126,7 +121,7 @@ Scenario: Newly created user can get a copy of the journal (Bug 1472467)
And I press "Save"
# Needs to add new user now to see if they get copy of page
And I choose "Add user" in "Users" from administration menu
And I set the following fields to these values:
And I fill in the following:
| First name * | Pete |
| Last name * | Mc |
| Email * | test01@example.com |
......
......@@ -23,7 +23,6 @@ Feature: Mahara users can allow their tagged blogs tags to be copied
| Entry | This is journal entry one |
And I scroll to the base of id "editpost_tags_container"
And I fill in select2 input "editpost_tags" with "blog" and select "blog"
And I fill in select2 input "editpost_tags" with "entry" and select "entry"