Storing arrays in database using ActiveRecord
If you use serialize
then you shouldn't have to worry about how the data is stored within the text field, although it's actually YAML.
serialize
is documented in the Rails/ActiveRecord API (scroll down to the section headed "Saving arrays, hashes, and other non-mappable objects in text columns")
For display, you need a format that is understandable to users and that can be easily converted back into an array in your code. Comma- or space-delimited?
Formatting for output:
delim = ',' # or ' ' for spaces, or whatever you choose
array.join(delim)
Converting back into an array might work as follows:
num_array = nums.split(delim).map(&:to_i) # or to_f if not integers
or perhaps using String#scan?
num_array = nums.scan(/\d+/).map(&:to_i) # for positive integers
Storing arrays in database : JSON vs. serialized array
You can store Arrays and Hashes using ActiveRecord's serialize
declaration:
class Comment < ActiveRecord::Base
serialize :stuff
end
comment = Comment.new # stuff: nil
comment.stuff = ['some', 'stuff', 'as array']
comment.save
comment.stuff # => ['some', 'stuff', 'as array']
You can specify the class name that the object type should equal to (in this case Array
). This is more explicit and a bit safer. You also won't have to create the array when you assign the first value, since you'll be able to append to the existing (empty) array.
class Comment < ActiveRecord::Base
serialize :stuff, Array
end
comment = Comment.new # stuff: []
comment.stuff << 'some' << 'stuff' << 'as array'
You can even use a neater version called store: http://api.rubyonrails.org/classes/ActiveRecord/Store.html
This should handle your use case using a built in method.
how to save array to database in rails
ActiveRecord::Base.serialize.
For example:
class User < ActiveRecord::Base
serialize :scholarship
end
user = User.create(:scholarship=> { "name" => "test", "state_ids" => ["1", "2"]})
User.find(user.id).scholarship# => { "name" => "test", "state_ids" => ["1", "2"] }
How to store an array of numbers in database using rails
Please change data type decimal to text
class AddContributorsToGoals < ActiveRecord::Migration
def change
add_column :goals, :contributions, :text
end
end
Saving and retrieving an Array in Rails
You mentioned the Comment and User class extend ActiveRecord. These are models and they go in the app/models folder.
Saving arrays to the database is very straightforward as explained in the answer you linked to. All you have to do to integrate it into your project is declare which attribute you want to store Arrays in and they will be automagically serialized upon saving or updating and deserialized when you want to read them back.
You should definitely post any code you have already. I'll assume the attribute you want to serialize is in the Comment model and it's called choices
(but of course it can be anything) and it is a text field (not a string field as this might be too short if your arrays grow more than 255 characters when serialized):
# app/models/comment.rb
class Comment < ActiveRecord::Base
serialize :choices
end
That's it! Now when ever you assign a value to that attribute @comment.choices = [false, false]
it will be automatically serialized as YAML when you save and then it'll be deserialized when you read it:
class CommentController < ApplicationController
def create
@comment = Comment.new choices: [false, false, true, 'stuff', 'whatever']
end
def show
@comment = Comment.find params[:id]
@comment.choices # returns [false, false, true, 'stuff', 'whatever']
end
end
To explain what's going on "under the hood" when you save the record with an array value assigned to the choices
field ActiveRecord knows that you want to serialize it since you declared serialize :choices
in your Comment class. It will take that array value and serialize it like this:
YAML.dump(choices)
this will convert the array into this string:
"---\n- false\n- false\n- true\n- stuff\n- whatever\n"
That is the YAML representation (serialization) of the array. To read it back in (when you call comment.choices
) ActiveRecord will take the serialized string and deserialize it:
YAML.load(choices)
That will then convert the YAML string back into a Ruby array.
To summarize:
- Add a text field to your model e.g.
choices:text
when you create the migration. - Declare
serialize :choices
in your model. - Use as normal.
Hope that helps.
rails store array in to database field
What is "things". Define it to be Array or Hash or something you want that to be and then add elements to it.
stuff = MyStuff.new
stuff.things = []
stuff.things << "pen"
..
stuff.save
How to save Array in database - Rails
If you are using MySQL 5.7+ you can; it introduced a JSON data type https://dev.mysql.com/doc/refman/5.7/en/json.html
A quick read about the changes: http://lornajane.net/posts/2016/mysql-5-7-json-features
PS -- I'm a fan of the comment above -- storing values as separate rows instead of as arrays is a better option
Rails - Which datatype should I use to store an array in a datebase
There are several options here:
Because it's tags we're dealing with, you could store them as comma-seperated values, while still having a String based column:
person.tags = response['tags'].join(',') # Stores "austin,nme"
If you want to be able to query individual tags (and index them), it might be a good option to store tags individually. For this, you'll want to create a model Tag which has a many-to-many relationship to your Person class.
Last, you can serialize your array to YAML and store it as a string in the database:
# When storing
person.tags = YAML::dump(response['tags'])
# When fetching from the database
tags = YAML::load(person.tags)You can ease your job by moving this logic to Model accessors. Let's say you keep your tags under a Person model:
class Person
def tags=(value)
self.tags = YAML::dump(value)
end
def tags
YAML::load(super)
end
end
EDIT: My favourite approach would be the second one, that's mainly because I like to keep my database clean and structured. It's not bad practice to store documents (arrays, json, blobs etc.) in the database, as long as you know what you're doing and why you are doing this. See the whole NoSQL vs structured database debate. The first option I suggested might cover your needs, without added complexity.
Storing an array in the database in ruby on rails
ActiveRecord::Base.serialize. Straight from the rails docs:
class User < ActiveRecord::Base
serialize :preferences
end
user = User.create(:preferences => { "background" => "black", "display" => large })
User.find(user.id).preferences # => { "background" => "black", "display" => large }
Related Topics
Homebrew Installation on MAC Os X Failed to Connect to Raw.Githubusercontent.Com Port 443
Check If Internet Connection Exists with Ruby
Devise Login with User or Admin Models and Basecamp Style Subdomains
Ruby - Digest::Digest Is Deprecated; Use Digest
Setter Method (Assignment) with Multiple Arguments
Where Should My Non-Model/Non-Controller Code Live
How to Improve Jruby Load Time
Elegant Chained 'Or's for Tests on Same Variable in Ruby
How to Easily Parse a Url with Parameters in a Rails Test
Rails Carrierwave Base64 Image Upload
Force Browser to Download File Instead of Opening It
Use of Caret Symbol (^) in Ruby
Sinatra Clears Session on Post
How to Identify Aliased Methods in Ruby