I am trying to save an array of strings in a column of my table users. I have this line in my migration file add_column :users, :choices, :string. This doesn't work as I am trying to store an array and not just a string, my terminal shows Unpermitted parameter: :choices. How can I store an array ?? (Obviously add_column :users, :choices, :array doesn't work.)
2 Answers
The database column really has nothing to do with the error. You define array columns by defining a type and using the array: true option as arrays are typed in most databases unlike in Ruby:
add_column :users, :choices, :string, array: true
However this is usually a bad idea as you're violating first normal form (1NF) by putting multiple values in one column and giving up all the advantages that having a discrete table has in terms of normalization, assocations, foreign keys etc. This is idea that everyone entertains when they discover array columns - but is not really a good design decision.
Unpermitted parameter: :choices is raised when you pass an ActionController::Parameters instance with an unpermitted key. It has absolutely nothing to do with the underlying database column or the attribute.
You can whitelist array columns by passing a hash key with an empty array:
params.require(:user)
.permit(:foo, :bar, choices: [])
This permits an array containing any type of permitted scalar value.
Comments
Should be as simple as this in your migration
def change
add_column :users, :choices, :string, array: true
end
Then you probaly want to prevent writing non-array types.
#app/models/users.rb
def choices=(input)
raise TypeError, 'choices must be an array' unless input.is_a?(Array)
super
end
choicesand include a foreign_key/join to theuserstable? this would act like an array, but work with all databases