RSpec throws NoMethodError `strip' for Array when calling expectation

922 views Asked by At

I am using webmocks with much success to test some API calls in my application. One test however is failing unexpectedly. The method which is failing works fine from the console in development, but in test, the RSpec is throwing an exception.

The method tested:

class MyClass
  class << self
    . . .
    def get_internal_users 
      response = HTTParty.get(API_URL + '/internal_users.json')
      return false unless response.code == 200
      response.parsed_response.each { |user| user.symbolize_keys! }
    end

  end
end

In Rails console: MyClass.get_internal_users returns a valid array of hashes.

The test:

  describe MyClass do
    context 'admin overrides' do
        before do
        @internal_users = {"user_name"=>"test_user"},{"user_name"=>"test_user_2"}
        stub_request( :get, API_URL + '/internal_users.json')
        .to_return( :status => 200, :body => @internal_users, :headers => {})
      end

      describe "fetch internal users" do
        subject { MyClass.get_internal_users }
        it { expect {subject}.to_not raise_error }
      end
    end
  end

Running this test throws the following exception:

Failure/Error: it { expect {subject}.to_not raise_error }
       expected no Exception, got #<NoMethodError: undefined method `strip' for [{"user_name"=>"test_user"}, {"user_name"=>"test_user_2"}]:Array>

And there it is. Commenting out it { expect {subject}.to_not raise_error } causes the test to pass.

I have that same expectation all throughout my code though and it works fine. What is causing the expectation to call strip on an array?

I am using the following libraries:

  • rails-4.0.3 rspec-core-2.14.7
  • rspec-rails-2.14.1
  • rspec-mocks-2.14.6
  • rspec-expectations-2.14.5
  • httparty-0.13.0
  • webmock-1.20.4

UPDATE The issue is a conflict with what state both webmock and httparty expect the body to be in. Following the stack trace. I was able to make the error "go away" changing this method in the httparty gem:

# httparty-0.13.0/lib/httparty/parser.rb
def parse
  #body is an array, the return check is throwing the exception:
  #  return nil if body.nil? || body.strip.empty? || body == "null"
  # allow arrays:
  unless body.class == Array
   return nil if body.nil? || body.strip.empty? || body == "null"
  end

  if supports_format?
    parse_supported_format
  else
    body
  end 
end

But I'm reluctant to distribute this gem across all servers this application would be deployed to.

1

There are 1 answers

0
eggmatters On BEST ANSWER

Good thing I didn't know whether this was an httparty issue, webmock issue, rspec issue or some amalgamation of the three. I wound up tracing the request in firebug and inspecting the response headers. I had a notion that the ContentType is instructing httparty how to parse the response. Sure enough:

stub_request( :get, API_URL + '/internal_users.json')
      .to_return( :status => 200, :body => @internal_users.to_json, :headers => {'Content-Type' =>  'application/json; charset=utf-8'})

fixed it. Somebody should have caught that before I did.