icn
icn

Reputation: 17876

Rails 5.2.3 converting all params datatype to string when testing using rspec

I am using rails 5.2.3 and testing using rspec-rails (3.8.2), when I send request to rails like this

  let(:params) do
    {
      down_payment: 10_000,
      asking_price: 100_000,
      payment_schedule: 'weekly',
      amortization_period: 5
    }
  end
  it 'works' do
    get :calculate, params: params, format: :json
    expect(response.status).to eq 200
  end

I also tried

  it 'works' do
    get :calculate, params: params, as: :json
    expect(response.status).to eq 200
  end

in rails all integers get converted to string like this

<ActionController::Parameters {"amortization_period"=>"5", "asking_price"=>"100000", "down_payment"=>"10000", "payment_schedule"=>"weekly", "format"=>"json", "controller"=>"payment_amount", "action"=>"calculate", "payment_amount"=>{}} permitted: false>

But if I use curl to send a request I can see integer not being converted to string.

curl -X GET -H "Content-Type: application/json"  -d ‘{"asking_price": 100000 ,"payment_schedule": "monthly", "down_payment": 10000, "amortization_period": 5  }' http://localhost:3000/payment-amount

Thanks for any help!

Upvotes: 3

Views: 2056

Answers (4)

dugong
dugong

Reputation: 4431

Beware, it is not format: :json but as: :json. I overlooked that.

Upvotes: 0

Ayer
Ayer

Reputation: 140

After a lot of tries, I found the solution to this issue. If you pass the params converted with to_json and pass 'CONTENT_TYPE' => 'application/json' as env, integers will be passed to the controller.

let(:params) do
  {
    down_payment: 10_000,
    asking_price: 100_000,
    payment_schedule: 'weekly',
    amortization_period: 5
  }
end

it 'works' do
  post '/', params.to_json, 'CONTENT_TYPE' => 'application/json'
end

This will work as expected.

Upvotes: 1

nikolayp
nikolayp

Reputation: 17929

Just add as: :json format to your requests

post(graphql_path, params: params, as: :json)

Upvotes: 1

Tom Lord
Tom Lord

Reputation: 28305

JSON payloads can contain five value types: string, number, integer, boolean and null.

HTTP query strings are, by contrast, only strings.

By default, request specs use the encoding specified in the HTTP spec - i.e. all parameters are strings. This is why you see the parameters get converted.

If your production system is sending JSON, you need to tell the test to do so too - e.g. by adding as: :json as you did above.

Upvotes: 4

Related Questions