ChrisJ
ChrisJ

Reputation: 2792

Capybara (poltergeist) cannot find checkbox in form

I cannot get Capybara for find a checkbox element.

I've tried all the usual ways:

find_field
check
find
click_on

It's as if the element isn't there. If I select the parent element, and look at it's innerHTML the checkbox is included:

(byebug) all(:css, '.checkbox.form-group').last['innerHTML']
\n    <input type=\"checkbox\" id=\"google_agreed_to_terms_at\" value=\"1\" required=\"true\" ng-model=\"agreed_to_terms\" required-notification=\"Please agree to the terms and conditions\" class=\"ng-pristine ng-untouched ng-empty ng-invalid ng-invalid-required\" bs-validation=\"\">\

but selecting the child elements it's not there:

(byebug) all(:css, '.checkbox.form-group').last.all :xpath, './*'
[#<Capybara::Node::Element tag="label" 
path="//HTML[1]/BODY[1]/DIV[2]/DIV[1]/DIV[2]/FORM[1]/DIV[1]/LABEL[1]">]

I feel like I'm going mad.

Here's the relevant code (copied from save_and_open_page)

<div class="checkbox form-group">
  <input type="checkbox" id="agreed_to_terms_at" value="1" required="true" ng-model="agreed_to_terms" required-notification="Please agree to the terms and conditions" class="ng-pristine ng-untouched ng-empty ng-invalid ng-invalid-required" bs-validation="">
  <label class="label-light" for="agreed_to_terms_at">
     I have read and agree to the terms</label>
</div>

I thought maybe rails was generating slightly non-compliant HTML, so I've gone to writing the checkbox by hand, but it didn't help.

What's going on here?

Upvotes: 0

Views: 389

Answers (2)

Thomas Walpole
Thomas Walpole

Reputation: 49870

The checkbox is hidden to allow for uniform styling across all browsers. Since you have a label element correctly associated you can tell check to click the label instead of the actual checkbox

check('agreed_to_terms_at', allow_label_click: true)

which will click the checkbox if visible and if not it will click the label. If you want it to only click the label you can do

find(:label, 'I have read and agree').click

Or

find(:label, for:'agreed_to_terms_at').click

Upvotes: 3

ChrisJ
ChrisJ

Reputation: 2792

Due to CSS styling, the checkbox element was being hidden and the label used to present it. So the element was getting skipped over by capybara's default behaviour to ignore hidden elements.

I worked around it using

find('#agreed_to_terms_at', :visible => false).trigger('click')

Upvotes: 0

Related Questions