简体   繁体   English

为什么Capybara与AJAX调用后插入的新DOM元素不匹配?

[英]Why is Capybara not matching new DOM elements inserted after an AJAX call?

I'm using Rails 5, and Capybara. 我正在使用Rails 5和Capybara。 I created a simple Rails view search form. 我创建了一个简单的Rails视图搜索表单。 Upon submit, vanilla JS takes over with preventDefault and performs AJAX to get search results. 提交后,香草JS接管preventDefault并执行AJAX以获得搜索结果。 The results are then packaged into a table, and appended to the DOM. 然后将结果打包到表中,并附加到DOM。 The page works fine in development, however, capybara is not cooperating in my feature specs: 该页面在开发中运行良好,但是,capybara与我的功能规格不兼容:

expected to find css "#search_results table" but there were no matches . expected to find css "#search_results table" but there were no matches

Just as a sanity check, I matched css that was already present in my view, so Capybara can do some matching correctly, just not the JS-introduced elements. 就像进行健全性检查一样,我匹配了视图中已经存在的css,因此Capybara可以正确地进行某些匹配,而不是JS引入的元素。

I've set some standard Ruby sleep x , and wait: x in the Capybara matchers. 我已经设置了一些标准的Ruby sleep x ,然后wait: x Capybara匹配器中的wait: x Also have seen some articles with examples of custom methods to force Capybara to wait, but those require jquery which I am not using. 还看到了一些带有自定义方法示例的文章,这些示例可以强制Capybara等待,但是这些文章需要我未使用的jquery。 I expect capybara to handle this vanilla JS, but have had no luck getting it to work here. 我希望水豚能处理这种普通的JS,但没有运气可以在这里工作。 Please help. 请帮忙。

View: 视图:

<div id='media_search'>
  <%= form_for(:search, method: "get", html: {class: "navbar-form navbar-left form-inline"}) do |f| %>
   <%= f.label :search %>
   <%= f.text_field :search, id: "media_search_field", class: "form-control", placeholder: "song, album, or artist" %>
   <%= f.submit "Submit", id: "media_search_submit", class: "btn btn-default" %>
  <% end %>

  <div id='search_results'></div>
</div>    

Snippet of vanilla JS: 香草JS片段:

var ajaxSearchMedia = function (query, successCb) {
  var request = new XMLHttpRequest();
  request.open('GET', '/search?query=' + query, true);

  request.onload = function() {
    if (request.status >= 200 && request.status < 400) {
      // Success!
      var songs = JSON.parse(request.responseText);
      successCb(songs);
    } else { ...

Feature test: 功能测试:

scenario "with results" do
  visit '/'

  fill_in "media_search_field", with: "song"

  click_on "media_search_submit"

  expect(page).to have_css("#search_results table")
end

Your scenario statement isn't tagged with js: true which, if using the normal capybara configuration, means you're using the default rack-test driver which doesn't support JS. 您的方案陈述没有用js: true标记js: true ,如果使用正常的水豚配置,则表示您使用的是不支持JS的默认机架测试驱动程序。 You will need to configure tests that depend on JS behaviors to use a driver that supports JS - see https://github.com/jnicklas/capybara#selecting-the-driver . 您将需要配置依赖于JS行为的测试,以使用支持JS的驱动程序-请参阅https://github.com/jnicklas/capybara#selecting-the-driver You will also need to configure the same tests not to use transactional testing - see https://github.com/jnicklas/capybara#transactions-and-database-setup and https://github.com/DatabaseCleaner/database_cleaner#rspec-with-capybara-example 您还需要配置相同的测试以不使用事务测试-请参阅https://github.com/jnicklas/capybara#transactions-and-database-setuphttps://github.com/DatabaseCleaner/database_cleaner#rspec-带水豚的例子

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM