DEV Community

Flávia Bastos
Flávia Bastos

Posted on • Originally published at flaviabastos.ca on

3

How to permit nested parameters in Rails

The context

Rails 5 introduced a big change in how it handles ActionController::Parameters (the parameters that you get on your Controllers): before Rails 5, if you called your params you would get a hash back and after Rails 5, you get a ActionController::Parameters object. You can see that by calling params.inspect and if you call .to_h on these parameters you should be good to go.

However, you might get an empty hash when calling .to_h on some parameters because they were not explicitly permitted – see the result of inspecting my params (note the “permitted: false” at the very end):

<ActionController::Parameters {"friends" => {"park" => "Doggoland", "dogs"=>[{"id"=>73, "name"=>"Milou", "household"=>"Tintin"}, {"id"=>74, "name"=>"Snoopy", "household"=>"Charlie Brown"}]}} permitted: false>
Enter fullscreen mode Exit fullscreen mode

Permitting params was showing up back in Rails 4 when Strong Parameters were introduced as part of security features and this blog post goes through some examples of why just calling .to_h might be an issue now that Rails 5 returns objects instead.

Permitting parameters

One good way to permit some parameters is by creating a private helper function in your controller that will explicitly permit the parameters you want:

private def nice\_params params.permit(:id, :name, :email).to\_h end
Enter fullscreen mode Exit fullscreen mode

When accessing your params, instead of params[:name], you use nice_params[:name].

Permitting nested parameters

Things get a little more complicated when you have a nested data structure. The documentation only gets one level deep and I had something more complicated than that. Let’s use the following as an example:

{"friends" => { "park" => "Doggoland", "dogs"=>[{"id"=>73, "name"=>"Milou", "household"=>"Tintin"}, {"id"=>74, "name"=>"Snoopy", "household"=>"Charlie Brown"}] } }
Enter fullscreen mode Exit fullscreen mode

My nice_params function looks like this:

def nice\_params params.permit( friends: [:park, dogs: [:id, :name, :household]] ).to\_h end
Enter fullscreen mode Exit fullscreen mode

One very important thing to notice is that the nested list must be placed last!

I hope this helps someone else with deep nested params. 😅


If you found this helpful, let me know on Twitter!

The post How to permit nested parameters in Rails_ was originally published at _flaviabastos.ca

Sentry image

See why 4M developers consider Sentry, “not bad.”

Fixing code doesn’t have to be the worst part of your day. Learn how Sentry can help.

Learn more

Top comments (0)

A Workflow Copilot. Tailored to You.

Pieces.app image

Our desktop app, with its intelligent copilot, streamlines coding by generating snippets, extracting code from screenshots, and accelerating problem-solving.

Read the docs