Merge pull request #170 from FundingGates/master

Support optional types for computed attributes
This commit is contained in:
Steve Klabnik 2013-03-08 09:11:29 -08:00
commit e76a16486f
3 changed files with 27 additions and 6 deletions

View File

@ -252,6 +252,20 @@ class PostSerializer < ActiveModel::Serializer
end end
``` ```
The type of a computed attribute (like :full_name above) is not easily
calculated without some sophisticated static code analysis. To specify the
type of a computed attribute:
```ruby
class PersonSerializer < ActiveModel::Serializer
attributes :first_name, :last_name, {:full_name => :string}
def full_name
"#{object.first_name} #{object.last_name}"
end
end
```
If you would like the key in the outputted JSON to be different from its name If you would like the key in the outputted JSON to be different from its name
in ActiveRecord, you can use the `:key` option to customize it: in ActiveRecord, you can use the `:key` option to customize it:

View File

@ -82,7 +82,9 @@ module ActiveModel
end end
def attribute(attr, options={}) def attribute(attr, options={})
self._attributes = _attributes.merge(attr => options[:key] || attr.to_s.gsub(/\?$/, '').to_sym) self._attributes = _attributes.merge(attr.is_a?(Hash) ? attr : {attr => options[:key] || attr.to_s.gsub(/\?$/, '').to_sym})
attr = attr.keys[0] if attr.is_a? Hash
unless method_defined?(attr) unless method_defined?(attr)
define_method attr do define_method attr do
@ -184,8 +186,12 @@ module ActiveModel
attrs[key] = column.type attrs[key] = column.type
else else
# Computed attribute (method on serializer or model). We cannot # Computed attribute (method on serializer or model). We cannot
# infer the type, so we put nil. # infer the type, so we put nil, unless specified in the attribute declaration
attrs[key] = nil if name != key
attrs[name] = key
else
attrs[key] = nil
end
end end
end end

View File

@ -563,16 +563,17 @@ class SerializerTest < ActiveModel::TestCase
# Computed attributes (not real columns or associations). # Computed attributes (not real columns or associations).
def can_edit; end def can_edit; end
def can_view; end
def drafts; end def drafts; end
attributes :name, :age, :can_edit attributes :name, :age, {:can_edit => :boolean}, :can_view
has_many :posts, :serializer => Class.new has_many :posts, :serializer => Class.new
has_many :drafts, :serializer => Class.new has_many :drafts, :serializer => Class.new
has_one :parent, :serializer => Class.new has_one :parent, :serializer => Class.new
end end
assert_equal serializer.schema, { assert_equal serializer.schema, {
:attributes => { :name => :string, :age => :integer, :can_edit => nil }, :attributes => { :name => :string, :age => :integer, :can_edit => :boolean, :can_view => nil },
:associations => { :associations => {
:posts => { :has_many => :posts }, :posts => { :has_many => :posts },
:drafts => nil, :drafts => nil,
@ -1076,7 +1077,7 @@ class SerializerTest < ActiveModel::TestCase
:name => 'logo.png', :name => 'logo.png',
:url => 'http://example.com/logo.png', :url => 'http://example.com/logo.png',
:attachable => { :attachable => {
:type => :email, :type => :email,
:id => 1 :id => 1
}}, }},
:emails => [{ :emails => [{