Reputation: 920
I have this Javascript function which i use to append elements do my form. When the form is submitted, all elements are passed in as params.
Here's the problem. The elements that my function appends are part of a Hash. This basically works as the rails "nested-attributes".
All seems to be working fine, except when one of the "Hashs" is empty. When i delete all elements from the collection, the hash params is not passed to the controller.
Example (Imagine i appended Honda, Toyota, Hyundai using my JS function)
Cars [Honda] [Toyota] [Hyundai]
This is how the hash is set up in the JS function (every time i click the "add"):
CarsHash.name= "cars_hash"+"["+"tmp_cars"+"]"+"["+i+"]"+"car_name"
If i were to submit the form, the values would be passed as Hash to the controller like this:
cars_hash=>{tmp_cars=>"{"1"=>{car_brand=> "honda"},"2"=>{car_brand=> "toyoda"},"3"=>{car_brand=> "hyundai"}"}
However, if i decide to delete all those values from the hash (using the delete button which also has functionality stated on the JS function) and submit the form, the Hash is not even present as a param. Then, when i get to my controller and i try to populate the variable i use for iterating/inserting into my DB:
Controller
cars_hash = params[:cars_hash][tmp_cars]
It gives me this error:
undefined method `[]' for nil:NilClass
I understand, the param is not even present so its essentially nil. I tried with all this possibly options:
if not params[:cars]["tmp_cars"].blank?
if not params[:cars]["tmp_cars"].empty?
if params[:cars]["tmp_cars"].present?
if params[:cars]["tmp_cars"] != nil
But no luck. Can anyone suggest me a way to get this to work? Again, the param will only be not nil IF the hash as a value. For it to have a value, an element must be appended to the document through the JS function.
Upvotes: 0
Views: 776
Reputation: 44695
Try doing:
cars_hash = params[:cars_hash] && params[:cars_hash][tmp_cars]
I would strongly recommend installling andand
gem which is perfect for situations like this. With this gem you can wirte the code above like:
cars_hash = params[:cars_hash].andand[tmp_cars]
UPDATE:
Your code was not working because params[:cars_hash]
returned nil, on which you were trying to call []
method, and such a method is not defined for nil
object. Hence you need to check whether params[:cars_hash]
is nil or not before you call anything on it.
&&
operator have this nice property that it is not even executing the right argument whan the left argument is falsy - there is no point of doing this. Since every expression in ruby returns value of the last executed command, &&
returns whatever left expression returns if it is falsy (false
or nil
) and otherwise it runs the expression on its right side and returns its value. This is pretty common to use this &&
in this context in Ruby.
Upvotes: 1