Sha256: d21178db752a5918bb22ffdd8f20ba70d407c5ca61f50bc839cfce8b3a32f668

Contents?: true

Size: 1.47 KB

Versions: 5

Compression:

Stored size: 1.47 KB

Contents

class HashField < Field
  # TODO: validate should defer to @element_type over each element
  def initialize(name, options={})
    @element_type = Field.from_options(name, 'type' => options['of'].to_s) if options['of']
    super
  end
  
  def json_action(action, value, record)
    hash = record.get_raw(name)
    
    if action == 'remove'
      value = [value] unless value.is_a?(Array)
      keys = value.collect(&:to_s)
      hash.delete_if {|key, _| keys.include?(key)}
    else
      raise "Set or merge actions on a hash must be passed a hash" unless value.is_a?(Hash)
      value = process(value, record, :from_json)
      if action == 'set'
        hash = value
      elsif action == 'merge'
        hash.merge!(value)
      end
    end
    
    record.set_raw(name, hash)
    record.changed!(name)
  end

  def typecast(value, record)
    value = {} unless value.is_a?(Hash)
    ChangeSensitiveHash.new(record, name, process(value, record, :typecast))
  end
  
  def untypecast(value, record)
    return {} if value.blank? || !value.respond_to?(:to_hash)
    process(value, record, :untypecast)
  end
  
  def from_json(value, record)
    return {} if value.blank? || !value.is_a?(Hash)
    process(value, record, :from_json)
  end
  
  
  private
    def process(hash, record, method)
      return hash.to_hash if @element_type.nil?
      hash.to_hash.each do |key, value|
        hash[key.to_s] = @element_type.send(method, value, record)
      end
    end
end

Field::TYPES['hash'] = HashField

Version data entries

5 entries across 5 versions & 1 rubygems

Version Path
yodel-0.0.7 lib/yodel/models/core/fields/hash_field.rb
yodel-0.0.4 lib/yodel/models/core/fields/hash_field.rb
yodel-0.0.3 lib/yodel/models/core/fields/hash_field.rb
yodel-0.0.2 lib/yodel/models/core/fields/hash_field.rb
yodel-0.0.1 lib/yodel/models/core/fields/hash_field.rb