User モデルのフィールドのリストがあります ( Userbelongs_toLocationと belongs_to Company):
approval_fields = [:email, :location => [:first_name, :last_name], :company => [:name, :address]]
このコードでレコードを更新しようとしたときに、ユーザーのすべての変更を収集したい:
user.update_attributes(params[:user])
私はこれのために醜いコードを書きました:
# Collects changed fields and returns hash of changes:
# Example: approval_fields = [:email, :location => [:first_name, :last_name]]
#          res = _collect_approval_changes(approval_fields)
#          res # => {'email' => 'new_value@change.com',
#                    'location_attributes' => {'first_name' => 'NewFirstName', 'last_name' => 'NewLastName'}}
def _collect_approval_changes(approval_fields)
  changes = {}
  approval_fields.each do |f|
    if f.is_a?(Hash)
      key = f.keys.first
      next unless self.public_send(key) # skip this association if associated object is nil
      changes["#{key}_attributes"] ||= {}
      f[key].each do |v|
        if self.public_send(key).public_send("#{v}_changed?")
          changes["#{key}_attributes"][v.to_s] = self.public_send(key).read_attribute(v)
        end
      end
      changes.delete("#{key}_attributes") if changes["#{key}_attributes"].blank?
    else
      changes[f.to_s] = self.read_attribute(f) if self.public_send("#{f}_changed?")
    end
  end
  changes
end
このメソッドをリファクタリングする方法についてアドバイスをいただけますか? ありがとうございました!