القضبان لديها الكثير من خلال مربعات الاختيار متعددة الأشكال

StackOverflow https://stackoverflow.com/questions/4200540

سؤال

هذا هو حقا يسقطني! :(

أحاول إنشاء نموذج نموذج متداخل لنموذج المستخدم الخاص بي مع قائمة مربعات الاختيار فيه حيث يمكن فحص متاجر متعددة أو عدم فحصها لإدارة المتاجر من خلال التوظيف النموذجي.

class Staffing < ActiveRecord::Base
  # Associations
  belongs_to :user
  belongs_to :staffable, :polymorphic => true
  belongs_to :store,     :class_name => "Store",
                         :foreign_key => "staffable_id"
end

class User < ActiveRecord::Base
  # Includes
  acts_as_authentic

  # Associations
  has_many :staffings, :dependent => :destroy
  has_many :stores, :through => :staffings

  # Nested Attributes
  accepts_nested_attributes_for :staffings, :allow_destroy => true
end

class Store < ActiveRecord::Base
  # Associations
  has_many :staffings, :as => :staffable, :dependent => :destroy
  has_many :users, :through => :staffings
end


# Users Controller
def create
  @user = User.new(params[:user])
  flash.now[:notice] = "#{@user.name} was successfully created." if @user.save
  respond_with @user
end


def update
  @user = User.find(params[:id])
  params[:user][:store_ids] ||= []
  @user.update_attributes(params[:user])
  flash.now[:notice] = "#{@user.name} was successfully updated."
  respond_with @user
end

لأغراض في متناول اليد ، يمكن تجاهل الجمعية الأخرى القابلة للموظفين. إنه نموذج مشابه كنت أرغب في النهاية في إدارته إلى جانب المتجر ، لكن أول شيء أول منذ أن شعرت بالذهول كما هو.

# User Form
- for store in Store.all
  %p
    = check_box_tag "user[store_ids][]", store.id, @user.stores.include?(store)
    = store.nickname

يرسل معاملاتي على هذا النحو:

{"utf8"=>"✓",
 "authenticity_token"=>"blub-blub-blub=",
 "user"=>{"login"=>"hey.buddy",
 "email"=>"test@hey.net",
 "role"=>"admin",
 "hq"=>"1",
 "password"=>"[FILTERED]",
 "password_confirmation"=>"[FILTERED]",
 "store_ids"=>["3",
 "4"]}}

ثم خطأ!

Mysql2::Error: Column 'staffable_type' cannot be null: INSERT INTO `staffings` (`created_at`, `staffable_id`, `staffable_type`, `updated_at`, `user_id`) VALUES ('2010-11-17 00:30:24', 3, NULL, '2010-11-17 00:30:24', 102)

أعلم أنه يجب علي بناء staffable_type كـ "متجر" ولكني كنت أحاول طوال اليوم-ما هي الحيلة؟

لدي أعمدة قابلة للموظفين (ومعرف) تم تعيينها على: null => false ولكن هذا لا يمكن أن يكون سبب هذا لأن هذا يجب أن يتم تقويمه في وحدة التحكم قبل ضرب DB على أي حال.

لماذا لا يعمل أدناه في تصنيري:

@user.staffings.each do |s|
  s.staffable_type = 'Store'
end

أو:

@user.store_ids.each do |i|
  s = @user.staffings.build
  s.staffable_type = 'Store'
  s.staffable_id = i
end

إذا حاولت أشياء كثيرة مماثلة لما سبق دون جدوى. أي مساعدة سيكون موضع تقدير كبير.

شكرا على وقتك!

هل كانت مفيدة؟

المحلول

حسنًا ، لقد اعتقدت هذا. أنا أجيب هنا حتى أتمكن من مساعدة شخص ما في يوم من الأيام ، لكن المشكلة كانت إشرافًا أساسيًا على الفرق بين العديد من الجمعيات وينتمي وينتمي إلى العديد من الجمعيات.

أنت إذا كنت ترغب في التعامل مع مربعات الاختيار أو قوائم متعددة التصنيف في A لديها الكثير من خلال ، لا توجد طريقة "_IDS" التي تم إنشاؤها لك من قبل الجمعية وتحتاج إلى كتابة واحدة لنفسك.

انظر مقالة بول باري هنا:http://paulbarry.com/articles/2007/10/24/has_many-through-checkboxes

يمكن أن تكون الأشياء متعددة الأشكال معقدة ، ولكن إذا كنت عالقًا جيدًا ، فربما تعود خطوة إلى الوراء وتأكد من أنه ليس شيئًا أكثر أساسية في العبث بك- لقد عملت بالنسبة لي!

فيما يلي الكود الذي تم تعديله من مدونة بول حول كيفية التعامل مع هذا إذا كنت تتعامل مع متعدد الأشكال لديه الكثير من خلال (في الأساس تحتاج فقط إلى استخدام تجزئة السمات وكتابة سمة polymorphic_type الخاصة بك):

attr_accessor :store_ids
after_save :update_stores

#after_save callback to handle group_ids
def update_stores
  unless store_ids.nil?
    self.staffings.each do |staffing|
      staffing.destroy unless store_ids.include?(staffing.staffable_id.to_s)
      store_ids.delete(staffing.staffable_id.to_s)
    end 
    store_ids.each do |s|
      self.staffings.create(attributes = {:staffable_id => s, :staffable_type => 'Store'}) unless s.blank?
    end
    reload
    self.store_ids = nil
  end
end 
مرخصة بموجب: CC-BY-SA مع الإسناد
لا تنتمي إلى StackOverflow
scroll top