1

Since I am using Rspec to test whether my controller is working fine, I did things below:

in test_rspec.rb,

before do
  params = {
    date_begin: "2018-10-01", 
    date_end: "2018-10-05", 
    options: {country_code: "US"}
  }

  get :index, params: params, as: :json
end

it do
  expected(response).to have_http_response(200) }
end

in test_controller.rb,

def index
  puts params_checker
  render json: Test.report(params_checker[:date_begin], 
                           params_checker[:date_end],
                           params_checker[:options])
end

private
  def params_checker
    params.permit(:date_begin, :date_end, :options)
  end

when I run code with rspec command, there goes something wrong, the parameter with nested hash :options is gone! below is the output of params in terminal & some of its error info:

> {"date_begin"=>"2018-10-01", "date_end"=>"2018-10-03"}
> ArgumentError:
   wrong number of arguments (given 3, expected 2)

I search everywhere on internet and tried some of the solutions but it won`t help. I do know this error is caused by parameter missing. Could any one help me finger it out why hashes cannot be passed to controller`s params in my case?

note: I am using rails 5.1.6

4
  • 1
    1) Change options={country_code: "US"} to options: {country_code: "US"} 2) Test.report receives only 2 arguments, you are passing 3 Commented Nov 7, 2018 at 11:37
  • @chumakoff after I change options to options: {country_code: "US"}.to_s and in controller eval(params[:options]) it worked fine. but this is not a really good way to solve the problem. Commented Nov 8, 2018 at 2:02
  • Are you kidding me? You just created another problem! It must be like this: params.permit(:date_begin, :date_end, options: [:country_code]) and without .to_s Commented Nov 8, 2018 at 8:51
  • @chumakoff please see the answer below, method in comment was a temporary solution and now I replaced it with which in my answer. Commented Nov 8, 2018 at 10:30

1 Answer 1

2

After searching for lots of solutions, I got one clear way to handle it. Strong parameters handling helped me a lot.

First, if you want to pass an array or hash, whatever the parameter is, only if it is a nested parameter, you should claim it inside the params.permit() statement, and add what key is allowed to pass in [], because permit only allows scalar values to pass, and filter hashes and arrays by default if the specific parameter is not claimed. code as below:

private
  def stat_params
    params.permit(:date_begin, :date_end, options: [:country_code])
  end

Second, when using Rspec to test the controller, nested parameters will be passed as <ActionController::Parameters:xxxx>type, so you have to add to_unsafe_h statement to this specific parameter, as below:

def index
  render json: Test.report(stat_params[:date_begin],
                           stat_params[:date_end],
                           stat_params[:options].to_unsafe_h)
end

This works fine for me finally.

Sign up to request clarification or add additional context in comments.

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.