Casper.js/Phantom.js not submitting data - forms

I'm using Casper.js to automate submitting a form. The form's onSubmit method returns false and runs some javascript (onclick callback) before sending the data, so I have to use clickLabel, instead of fill. The data is prepopulated, I just have to click the Submit button. When I use Casper to do clickLabel('Submit'), the data isn't submitted. What am I doing wrong?
Edit - here's the markup of the label:
<a class="green_btn white font_18 arrow_btn_pad rad_5" onclick="$.shactivity.eoiPremiumSubmit('expressval');return false;" href="javascript:void(0);">
<span class="fl cursor_p">Submit</span>
<span class="white_right_arrow mar_l_7 block fl mar_t_6 cursor_p"></span>
</a>

clickLabel invokes click in your case with the XPath selector of //*[text()='Submit']. click in turn will try dispatch mousefown and click events on the span with the Submit text. But the span won't have any such event handlers on it since this is what the parent link is for. The above XPath selector won't select the actual Link which is a parent of the span element.
You need to click the actual link to trigger the action:
casper.click(".green_btn.white.font_18.arrow_btn_pad.rad_5");
or with an XPath expression to select the parent based on the text:
var x = require('casper').selectXPath;
casper.click(x("//*[text()='Submit']/.."));

Related

Protractor can't find element by binding

I'm trying to find a element by binding, the problem is that the the element is an toast.
I'm using:
element(by.css('.btn-primary3')).click()
To simulate the click. As a result the toast does appear in the browser during the test.
Then I'm trying to store the element in a variable and test if the text value of the toast is equal to the expected value.
var toast = element(by.binding('toast.toast.title'));
expect(toast.getText()).toEqual('Inloggen mislukt');
But here the error pops up.
Failed: No element found using locator: by.binding("toast.toast.tile")
When I check the toast element in the the Chrome dev tools it shows up like this,
<div data-ng-repeat="toast in activeToasts">
<span data-ng-bind="toast.toast.title" class="ng-binding"> Inloggen mislukt</span>
</div>
I think the problem comes from the fact that that the span containing the binding doesn't exist on the dom when the page is loaded. It gets created when the button is clicked.
If this is the case, wait for the presence of the element after clicking the button:
element(by.css('.btn-primary3')).click();
var toast = element(by.binding('toast.toast.title'));
browser.wait(EC.presenceOf(toast), 5000);
expect(toast.getText()).toEqual('Inloggen mislukt');
May you should try:
<div data-ng-repeat="toast in activeToasts">
<span data-ng-bind="toast.toast.title" class="ng-binding"> Inloggen mislukt</span>
</div>

How to send multiple forms with one button in Contao?

I have a question about the wrappers/accordeons. I now have multiple wrappers and in each wrapper there is a form. Now, I want one sendbutton on the end of the page. The sendbutton which will send all the forms that have been filled in at once.
How can I do that?
I don't know why you want to break input into different forms and then submit them again at once. Would it not make sense to use one form and submit the data and process it the way you want using the processFormData hook? may be because you want the accordion to group you form fields. Let me help you this way:
Create your form in the format shown below. Make sure the form has a tabless layout to be able to use fieldsets.
Create a fieldset without a label. You may add the class ce_accordion just in case you have some styling attached to it.
Create a field of type html and add the following markup.
<div class="toggler">Form 1 headline here</div>
Create another field with the following markup
<div class="toggler">
Now create your input fields from here. for example a text field,textares.
Create a field of type html to close html markup created in step 3
</div>
Create a fieldset wrapper end here.
The above steps can be repeated as many as how many groups of fields you want to create in an accordion.
Now create you submit button here and it will send all your data the way you want.
Just a by the way:
If some one submits a form in a wrapper that is closed, how will he know which wrapper has error fields?
$(document).ready(function() {
$(".ce_accordion").each(function(index,el) {
if($(this).find("p.error")){
$(this).addClass("hasErrors");
$(this).find("div.toggler").addClass("active").attr("aria-expanded","true");
}
});
​});​
You can now add a style for .hasErrors rule

Lock/unlock form with toggle

I'm looking for a way to have a button toggeling the field of my form. When "locking" the form with the toggle button no data can be typed. When "unlocking" data should be allowed to be typed. What I want to achieve with this is simple avoiding users to accidentally type.
I found the code below and it works. Only problem is that it only applies to one input field. I want it to work on more that one.
<input type="checkbox" id="yourBox">
<input type="text" id="yourText">
<script>
document.getElementById('yourBox').onchange = function() {
document.getElementById('yourText').disabled = this.checked;
};
</script>
Mark the fields you want to disable with a CSS class, and then use jQuery to disable them.
jQuery - Disable Form Fields
If you want a pure Javascript solution, just repeat this line
document.getElementById('yourText').disabled = this.checked;
for each field.
Or, you can do something like this this: How to Get Element By Class in JavaScript?. Note that you can assign multiple CSS classes to the same field, so assign another class to identify those fields that need to be disabled.

jQuery on() click event handler with dynamic data crashing

Here's a simplified example of what I'm trying to achieve: http://jsfiddle.net/easLc/
HTML
<div class="bar">
<div class="apple"> apple</div>
<div class="banana"> banana</div>
<div class="citrus"> citrus </div>
</div>
jQuery
function showAlert(event) {
inventory = event.data.inventory;
alert(inventory);
}
fruits = ["apple", "banana", "citrus"];
inventory = [13, 45, 99];
for (i in fruits) {
$(".bar ."+fruits[i]).on("click", {inventory:inventory[i]},showAlert);
}
The inventory data I'm passing to the handler is dynamic, not static like the example. I'm getting the inventory data from asynchronous calls. After each time the inventory data is updated, I want to pass this data to the handler instead of have the handler get that information again.
What I'm noticing is on some clicks, the handler (I think) is crashing my browser. Am I creating too many handlers inadvertently? How do I see what handlers were created? Or what happens during the click event? I tried adding some console.log to the handler but I don't see them in the console.
Thanks!
Try
$(".bar ."+fruits[i]).off('click',showAlert).on("click", {inventory:inventory[i]},showAlert);
This will remove the previously bound event and rebind it... But it is hard to determine if it is the real source of the problem. You can add a console.log('text') in showAlert to see if it is being called more than once.
You can prevent multiple bindings by adding some sort of data to the element once it's been bound (a clean way would be a class, but meta-data may be preferred by standards):
$(".bar ." + fruits[i]).not(".bound").on('click', {...}).addClass('bound');

Getting "Change" event for a text field whose contents is changed by jQuery

I've made some pretty checkboxes using some pretty simple jQuery
HTML
<span class="iconElement checkBox" id="update_Check"></span>
<input type="text" id="update" name="update" value="0" class="hidden savedData" />
JS
$('.checkBox').live('click', function (e) {
if ($(this).hasClass('disabled') != true) {
$(this).toggleClass('checked')
var thisValue = parseInt($(this).next().val());
var newValue = (thisValue - 1) * (-1); // enusures the output is either 1 or 0, [ (1-1)*-1=0 and (0-1)*-1 =1 ]
$(this).next().val(newValue);
};
});
This is simply a span with a nice CSS background sprite, which when clicked changes toggles it's "checked" class, adjusting the CSS sprite from a "Tick" to an empty box. At the same time it also changes the content of a text field (hidden by CSS class 'hidden') to a 1 or a 0 to indicate whether the box is checked.
It has to have this 1 or 0 as when the data is passed to the next stage I have to have a value, an unchecked checkbox sends no value.
This all works fine!
BUT... I also need to be able to detect the "change" event of the hidden text field.
This is to be controlled by the "savedData" class.
$('.savedData').live('change', function () {
// do stuff now we know this has been changed
});
I could of course include this within the "click" event in the code above, but that's not practical for the application.
It seems that the "change" even is only trigger by elements which are changed by the keyboard or mouse, anything changed by jQuery is not being flagged.
Initially I was using hidden input type and thought that was the issue, but have changed them all to text type now and the problem is still there!
Any tips?!
It seems that the "change" even is only trigger by elements which are changed by the keyboard or mouse, anything changed by jQuery is not being flagged.
Yes, that is correct. That is precisely how this works. Only changes made by the user trigger event handlers: programmatic changes do not. The only way to trigger them is to do so yourself:
$(this).next().val(newValue).change();
The .change() triggers a change event on the element, so the handler will be called.