Peter Nixey
Peter Nixey

Reputation: 16565

How do you use the rspec have_selector method to verify XML?

I want to do some basic checking to ensure that an XML sitemap is being produced correctly but have_selector doesn't seem to be able to detect tags:

require 'spec_helper'

describe SitemapController do

  render_views

  before(:all) do
    # code to generate factory data
    # ...
  end

  # illustrating the problem
  it "should be able detect nodes that are definitely present" do
    get :index
    response.should have_selector('url')
  end
end

Every time I run the test I get the following error:

RSpec::Expectations::ExpectationNotMetError: expected css "url" to return something

The sitemap is being produced and when I debug the RSpec test and look at the response object I can see xml content:

ruby-1.9.2-p180 :001 > response.body
 => "<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n<urlset xmlns=\"http://www.sitemaps.org/schemas/sitemap/0.9\">\n  <url>\n    <loc>http://test.host/panel ... 

My sitemap is produced by the SitemapController and the view is located in views/sitemap/index.builder.xml.

Why isn't have_selector kicking in?

Upvotes: 6

Views: 3261

Answers (3)

Andrew France
Andrew France

Reputation: 4879

As far as I can tell the have_selector (or have_xpath) can only come from Webrat or Capybara. You're right in your comment to John that you don't need a browser simulator to test the API.

You may be invoking Webrat or Capybara by mistake as they use visit instead of get AFAIK. So the variables they match against may never have been populated by the page and so will always return false.

Rails should handle the XML document natively if the response content-type is correctly set to XML. Try using the assert_tag or assert_content test helper as a basic check.

I would just use Nokogiri to parse the XHTML and run normal RSpec tests against that:

xml = Nokogiri::XML(response.body)
xml.css("expression").size.should == 1

Upvotes: 1

John
John

Reputation: 30185

Capybara doesn't support XML responses. It always uses Nokogiri::HTML to parse the content, which produces unexpected results when given XML.

Adding XML support has been requested but was rejected by Capybara's maintainer.

Upvotes: 3

David Chelimsky
David Chelimsky

Reputation: 9000

Use should have_xpath('//url') instead. have_selector is for CSS.

See the Capybara README for more info.

Upvotes: 2

Related Questions