2012-01-20 2 views
3

Моих моделей выглядеть примерно так:рельсов создания модели с несколько belongs_to с attr_accessible

class User < ActiveRecord::Base 
    attr_accessible: :name 

    has_many :reviews 
end 

class Product < ActiveRecord::Base 
    attr_accessible: :name 

    has_many :reviews 
end 

class Review < ActiveRecord::Base 
    attr_accessible: :comment 

    belongs_to :user  
    belongs_to :product 
    validates :user_id, :presence => true 
    validates :product_id, :presence => true 
end 

Я пытаюсь выяснить, что лучший способ заключается в создании нового обзора, при условии, что: user_id и: product_id не являются доступными. Обычно я просто создаю обзор через ассоциацию (@ user.reviews.create), чтобы установить: user_id автоматически, но в этом случае я не уверен, как также установить product_id.

Мое понимание состоит в том, что если я сделаю @ user.reviews.create (params), все параметры без attr_accessible будут проигнорированы.

+0

Чем больше я думаю об этом, тем больше кажется, что product_id должен быть attr_accessible в классе Review, так как пользователю нужно будет выбрать продукт, просматриваемый из веб-формы. –

ответ

1

Кажется, вы хотели бы реализовать взаимосвязь «многие-ко-многим» между моделью «Пользователь и продукт», а модель «Обзор» служит в качестве таблицы соединений для соединения двух с добавленной строкой комментария. Это можно сделать, поскольку в Rails существует много связей. Начните с чтения Rails Guides on Associations.

При настройке Review модели, добавить внешние ключи для User и Product:

rails generate model review user_id:integer product_id:integer 

И создали свои ассоциации следующим образом:

class User < ActiveRecord::Base 
    has_many :reviews 
    has_many :products, through: :reviews 
end 

class Product < ActiveRecord::Base 
    has_many :reviews 
    has_many :users, through: :reviews 
end 

class Review < ActiveRecord::Base 
    # has comment string attribute 
    belongs_to :user 
    belongs_to :product 
end 

Это позволит вам совершать звонки такие as:

user.products << Product.first 
user.reviews.first.comment = 'My first comment!' 

как бы вы создать обзор:

@user = current_user 
product = Product.find(params[:id]) 
@user.reviews.create(product: product) 
+0

На самом деле я не думаю, что мне нужны «has_many: продукты через:: отзывы» и «has_many: пользователи через:: обзоры», так как мне не нужны отношения «многие-ко-многим» между продуктами и пользователи. Мне просто нужен пользователь, чтобы иметь возможность просматривать продукт, поэтому каждый обзор должен принадлежать пользователю и продукту. Вот бит sytax в вашем ответе. Я не понимаю: @ user.reviews.create (product: product) Будет ли это заполнять product_id, хотя product_id не attr_accessible? –

2

Вы можете сделать:

@user.reviews.create(params[:new_review])

... или аналогичный. Вы можете также использовать вложенные атрибуты:

class User < ActiveRecord::Base 
    has_many :reviews 
    accepts_nested_attributes_for :reviews 
    ... 

См «Вложенные атрибуты Примеры» на http://api.rubyonrails.org/classes/ActionView/Helpers/FormHelper.html.

+0

Привет, Пол. Можете ли вы объяснить, откуда появились параметры [: new_review] из вашего первого предложения? –

+0

Из поля fields_for или всего лишь набор входов с ручным кодированием (т. Е. Text_field_tag ​​вместо f.text_field). Другими словами, сверните свои собственные поля обзора. Вероятно, вам нужны вложенные атрибуты: fields_for + accepts_nested_attributes_for. –