2

属性を持つDocumentTypeモデルがあります。extensions私のフォームでは、人々がそれらの拡張機能をフォームに挿入できるようにしています。

保存する前にその入力を解析し、無効なオプションを取り除き、それを配列に変換して、Rails にシリアル化できるようにしたいと考えています。

私は次のコードを持っていますが、ユーザーが配列ではなくフォームに入力しただけで終わります:

class DocumentType < ActiveRecord::Base
  serialize :extensions

  before_save :process_extensions

  def process_extensions
    self.extensions = [*self.extensions.gsub(/[^a-z ]+/i, '').split(' ')].uniq
  end
end
4

2 に答える 2

11

何が起こっているのかを理解する鍵は、シリアル化がいつ発生するかを知ることです。activerecord のserialization.rbを調べると、write_attribute で呼び出される type_cast_attribute_for_write をオーバーライドすることでシリアライゼーションの魔法が発生することがわかります。つまり、属性の割り当て時です。だからあなたがするとき:

document_type.extensions = something

何かがシリアライズされ、拡張属性に書き込まれます。それは保存が行われる前の方法です。実際、属性をシリアル化するために document_type で save を呼び出す必要さえありません。

私が知っている最善の回避策はextensions=、DocumentType をオーバーライドすることです。何かのようなもの:

def extensions=(value)
  value = [*value.gsub(/[^a-z ]+/i, '').split(' ')].uniq
  write_attribute :extensions, value
end
于 2013-07-23T20:00:04.150 に答える
-1

extensionsモデルがRailsによって検証されている間にの値がシリアル化され、process_extensions後で(モデルが保存される前に)メソッドが呼び出され、期待どおりに動作しないため、この追加が信じられます

代わりに before_validate を使用してみてください

before_validate :process_extensions

于 2013-07-23T19:25:30.307 に答える