2013-02-18 100 views
0

由於我使用'updated_at'(專門用於原子提要)的性質,我需要避免在記錄是更新時更新updated_at字段保存沒有任何更改。爲了實現這個目標我讀了,結束了以下內容:當通過has_many保存時,Rails拋出保存錯誤(參數1爲0)

module ActiveRecord 
    class Base 

    before_validation :clear_empty_strings 

    # Do not actually save the model if no changes have occurred. 
    # Specifically this prevents updated_at from being changed 
    # when the user saves the item without actually doing anything. 
    # This especially helps when synchronizing models between apps. 
    def save 

     if changed? 
      super 
     else 
      class << self 
       def record_timestamps; false; end 
      end 
      super 
      class << self 
       remove_method :record_timestamps 
      end 
     end 

    end 

    # Strips and nils strings when necessary 
    def clear_empty_strings 
     attributes.each do |column, value| 
      if self[column].is_a?(String) 
       self[column].strip.present? || self[column] = nil 
      end 
     end 
    end 

    end 
end 

能正常工作在我的所有車型,除了我的電子郵件模型。電子郵件可以有許多發件箱。發件箱基本上是一個雙列模型,它包含訂閱者(電子郵件地址:)和電子郵件(發送給訂戶的電子郵件)。當我更新發件箱的屬性,然後保存電子郵件時,我得到(保存方法中的'super'調用)保存時的(參數1 for 0)錯誤。

Email.rb

has_many :outboxes, :order => "subscriber_id", :autosave => true 

Outbox.rb

belongs_to :email, :inverse_of => :outboxes 
belongs_to :subscriber, :inverse_of => :outboxes 
validates_presence_of :subscriber_id, :email_id 
attr_accessible :subscriber_id, :email_id 

更新:我也注意到,當我改變關聯模型的 '改變' 陣列沒有被填充。

@email.outboxes.each do |out| 
    logger.info "Was: #{ out.paused }, now: #{ !free }" 
    out.paused = !free 
end unless @email.outboxes.empty? 
@email.save # Upon saving, the changed? method returns false...it should be true 

回答

0

......嘆了口氣。花了無數小時試圖找到解決方案後,我碰到了this。我是否知道'save'方法實際上需要一個論點,我早就想到了這一點。顯然看着source在這方面沒有幫助。我所要做的只是在save方法中添加一個args = {}參數,並將其傳遞給'super',並且所有內容都正在工作。保存未修改的記錄而不更新時間戳,使用時間戳保存已修改的記錄並保存關聯而沒有錯誤。

module ActiveRecord 
    class Base 

    before_validation :clear_empty_strings 

    # Do not actually save the model if no changes have occurred. 
    # Specifically this prevents updated_at from being changed 
    # when the user saves the item without actually doing anything. 
    # This especially helps when synchronizing models between apps. 
    def save(args={}) 

    if changed? 
     super args 
    else 
     class << self 
     def record_timestamps; false; end 
     end 
     super args 
     class << self 
     remove_method :record_timestamps 
     end 
    end 

    end 

    # Strips and nils strings when necessary 
    def clear_empty_strings 
    attributes.each do |column, value| 
     if self[column].is_a?(String) 
     self[column].strip.present? || self[column] = nil 
     end 
    end 
    end 
end 
相關問題