Добавить столбец массива в Rails
Как вы объявляете столбец массива в Rails?
Деталь
У меня есть следующая модель
rails generate model User address:text
но я хочу модель, которая может хранить несколько адресов для каждого пользователя. Следующее объявление дает мне ошибку
rails generate model User address[]:text
Как вы объявляете столбец массива в Rails?
Ответы
Ответ 1
Вы можете использовать следующие шаги
rails g migration add_subjects_to_book subjects:text
И файл миграции:
class AddSubjectsToBook < ActiveRecord::Migration
def change
add_column :books, :subjects, :text, array: true, default: []
end
end
Мы можем проверить это сейчас:
2.1.2 :001 > b = Book.create
(0.2ms) BEGIN
SQL (2.0ms) INSERT INTO "books" ("created_at", "updated_at") VALUES ($1, $2) RETURNING "id" [["created_at", "2014-10-17 08:21:17.870437"], ["updated_at", "2014-10-17 08:21:17.870437"]]
(0.5ms) COMMIT
=> #<Book id: "39abef75-56af-4ad5-8065-6b4d58729ee0", title: nil, created_at: "2014-10-17 08:21:17", updated_at: "2014-10-17 08:21:17", description: {}, metadata: {}, subjects: []>
2.1.2 :002 > b.subjects.class
=> Array
Если вы хотите добавить массив при создании таблицы, вы можете сделать следующее
create_table :products do |t|
t.string :name, null: false
t.references :category, null: false
t.text :tags, array: true, default: []
end
Ответ 2
Если вы используете Postgres, то в этом посте http://blog.plataformatec.com.br/2014/07/rails-4-and-postgresql-arrays/ предлагается использовать параметр array: true
в сценарии миграции:
create_table :users do |t|
# other columns
t.text : addresses, array: true, default: []
end
Если вы не используете Postgres, этот ответ может быть полезен: Хранение массивов в базе данных: JSON против сериализованного массива
Ответ 3
Примеры с использованием array: true
требуют Postgres или какой-либо другой базы данных, способной работать с массивами. Для MySQL используйте универсальную сериализацию, которая позволяет хранить любой столбец произвольного типа.
Миграция базы данных:
create_table :users do |t|
t.text :addresses, default: [].to_yaml
...
end
Класс с атрибутом массива:
class User < ActiveRecord::Migration
serialize :addresses, Array
end
Используя атрибут:
u = User.new
u.update_attributes addresses: ["123 Evergreen", "246 Main"]
Обычные предостережения относятся к хранению массивов в базе данных. Это идет вразрез с реляционными базами данных и затрудняет, замедляет или делает невозможным такие вещи, как поиск отдельного элемента. Тем не менее, это может быть хорошим решением для базового хранилища, пока вам не понадобятся эти вещи.