Skip to content

Commit ee0283c

Browse files
committed
Simplify attributes handling.
1 parent 7bc66c5 commit ee0283c

File tree

1 file changed

+22
-44
lines changed

1 file changed

+22
-44
lines changed

lib/active_model/serializer/attributes.rb

Lines changed: 22 additions & 44 deletions
Original file line numberDiff line numberDiff line change
@@ -1,55 +1,23 @@
11
module ActiveModel
22
class Serializer
33
module Attributes
4-
# @api private
5-
class Attribute
6-
delegate :call, to: :reader
7-
8-
attr_reader :name, :reader
9-
10-
def initialize(name)
11-
@name = name
12-
@reader = :no_reader
13-
end
14-
15-
def self.build(name, block)
16-
if block
17-
AttributeBlock.new(name, block)
18-
else
19-
AttributeReader.new(name)
20-
end
21-
end
22-
end
23-
# @api private
24-
class AttributeReader < Attribute
25-
def initialize(name)
26-
super(name)
27-
@reader = ->(instance) { instance.read_attribute_for_serialization(name) }
28-
end
29-
end
30-
# @api private
31-
class AttributeBlock < Attribute
32-
def initialize(name, block)
33-
super(name)
34-
@reader = ->(instance) { instance.instance_eval(&block) }
35-
end
36-
end
37-
384
extend ActiveSupport::Concern
395

406
included do
417
with_options instance_writer: false, instance_reader: false do |serializer|
428
serializer.class_attribute :_attribute_mappings # @api private : maps attribute key names to names to names of implementing methods, @see #attribute
439
self._attribute_mappings ||= {}
10+
serializer.class_attribute :_attribute_keys # @api private : maps attribute names to keys, @see #attribute
11+
self._attribute_keys ||= {}
4412
end
4513

4614
# Return the +attributes+ of +object+ as presented
4715
# by the serializer.
4816
def attributes(requested_attrs = nil, reload = false)
4917
@attributes = nil if reload
50-
@attributes ||= self.class._attribute_mappings.each_with_object({}) do |(key, attribute_mapping), hash|
18+
@attributes ||= self.class._attribute_keys.each_with_object({}) do |(name, key), hash|
5119
next unless requested_attrs.nil? || requested_attrs.include?(key)
52-
hash[key] = attribute_mapping.call(self)
20+
hash[key] = self.class._attribute_mappings[name].call(self)
5321
end
5422
end
5523
end
@@ -58,6 +26,7 @@ module ClassMethods
5826
def inherited(base)
5927
super
6028
base._attribute_mappings = _attribute_mappings.dup
29+
base._attribute_keys = _attribute_keys.dup
6130
end
6231

6332
# @example
@@ -84,26 +53,35 @@ def attributes(*attrs)
8453
# object.edits.last(5)
8554
# end
8655
def attribute(attr, options = {}, &block)
87-
key = options.fetch(:key, attr)
88-
_attribute_mappings[key] = Attribute.build(attr, block)
56+
_attribute_keys[attr] = options.fetch(:key, attr)
57+
_attribute_mappings[attr] = _attribute_mapping(attr, block)
58+
end
59+
60+
# @api private
61+
def _attribute_mapping(name, block)
62+
if block
63+
->(instance) { instance.instance_eval(&block) }
64+
else
65+
->(instance) { instance.read_attribute_for_serialization(name) }
66+
end
8967
end
9068

9169
# @api private
92-
# names of attribute methods
70+
# keys of attributes
9371
# @see Serializer::attribute
9472
def _attributes
95-
_attribute_mappings.keys
73+
_attribute_keys.values
9674
end
9775

9876
# @api private
9977
# maps attribute value to explict key name
10078
# @see Serializer::attribute
10179
# @see Adapter::FragmentCache#fragment_serializer
10280
def _attributes_keys
103-
_attribute_mappings
104-
.each_with_object({}) do |(key, attribute_mapping), hash|
105-
next if key == attribute_mapping.name
106-
hash[attribute_mapping.name] = { key: key }
81+
_attribute_keys
82+
.each_with_object({}) do |(name, key), hash|
83+
next if key == name
84+
hash[name] = { key: key }
10785
end
10886
end
10987
end

0 commit comments

Comments
 (0)