active_model_serializers 0.10.3 → 0.10.12
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +5 -5
- data/CHANGELOG.md +154 -2
- data/README.md +153 -15
- data/lib/action_controller/serialization.rb +11 -1
- data/lib/active_model/serializable_resource.rb +2 -0
- data/lib/active_model/serializer.rb +275 -81
- data/lib/active_model/serializer/adapter.rb +2 -0
- data/lib/active_model/serializer/adapter/attributes.rb +2 -0
- data/lib/active_model/serializer/adapter/base.rb +2 -0
- data/lib/active_model/serializer/adapter/json.rb +2 -0
- data/lib/active_model/serializer/adapter/json_api.rb +2 -0
- data/lib/active_model/serializer/adapter/null.rb +2 -0
- data/lib/active_model/serializer/array_serializer.rb +2 -0
- data/lib/active_model/serializer/association.rb +53 -14
- data/lib/active_model/serializer/attribute.rb +2 -0
- data/lib/active_model/serializer/belongs_to_reflection.rb +7 -1
- data/lib/active_model/serializer/collection_serializer.rb +8 -5
- data/lib/active_model/serializer/concerns/caching.rb +36 -23
- data/lib/active_model/serializer/error_serializer.rb +2 -0
- data/lib/active_model/serializer/errors_serializer.rb +2 -0
- data/lib/active_model/serializer/field.rb +2 -0
- data/lib/active_model/serializer/fieldset.rb +3 -1
- data/lib/active_model/serializer/has_many_reflection.rb +6 -1
- data/lib/active_model/serializer/has_one_reflection.rb +3 -1
- data/lib/active_model/serializer/lazy_association.rb +99 -0
- data/lib/active_model/serializer/link.rb +23 -0
- data/lib/active_model/serializer/lint.rb +2 -0
- data/lib/active_model/serializer/null.rb +2 -0
- data/lib/active_model/serializer/reflection.rb +122 -73
- data/lib/active_model/serializer/version.rb +3 -1
- data/lib/active_model_serializers.rb +29 -11
- data/lib/active_model_serializers/adapter.rb +3 -1
- data/lib/active_model_serializers/adapter/attributes.rb +23 -0
- data/lib/active_model_serializers/adapter/base.rb +4 -2
- data/lib/active_model_serializers/adapter/json.rb +2 -0
- data/lib/active_model_serializers/adapter/json_api.rb +44 -26
- data/lib/active_model_serializers/adapter/json_api/deserialization.rb +4 -2
- data/lib/active_model_serializers/adapter/json_api/error.rb +2 -0
- data/lib/active_model_serializers/adapter/json_api/jsonapi.rb +2 -0
- data/lib/active_model_serializers/adapter/json_api/link.rb +2 -0
- data/lib/active_model_serializers/adapter/json_api/meta.rb +2 -0
- data/lib/active_model_serializers/adapter/json_api/pagination_links.rb +42 -21
- data/lib/active_model_serializers/adapter/json_api/relationship.rb +52 -9
- data/lib/active_model_serializers/adapter/json_api/resource_identifier.rb +35 -18
- data/lib/active_model_serializers/adapter/null.rb +2 -0
- data/lib/active_model_serializers/callbacks.rb +2 -0
- data/lib/active_model_serializers/deprecate.rb +2 -0
- data/lib/active_model_serializers/deserialization.rb +2 -0
- data/lib/active_model_serializers/json_pointer.rb +2 -0
- data/lib/active_model_serializers/logging.rb +2 -0
- data/lib/active_model_serializers/lookup_chain.rb +2 -0
- data/lib/active_model_serializers/model.rb +111 -30
- data/lib/active_model_serializers/model/caching.rb +25 -0
- data/lib/active_model_serializers/railtie.rb +4 -0
- data/lib/active_model_serializers/register_jsonapi_renderer.rb +2 -0
- data/lib/active_model_serializers/serializable_resource.rb +4 -2
- data/lib/active_model_serializers/serialization_context.rb +2 -0
- data/lib/active_model_serializers/test.rb +2 -0
- data/lib/active_model_serializers/test/schema.rb +4 -2
- data/lib/active_model_serializers/test/serializer.rb +2 -0
- data/lib/generators/rails/resource_override.rb +3 -1
- data/lib/generators/rails/serializer_generator.rb +2 -0
- data/lib/grape/active_model_serializers.rb +2 -0
- data/lib/grape/formatters/active_model_serializers.rb +2 -0
- data/lib/grape/helpers/active_model_serializers.rb +2 -0
- data/lib/tasks/rubocop.rake +55 -0
- metadata +74 -291
- data/.github/ISSUE_TEMPLATE.md +0 -29
- data/.github/PULL_REQUEST_TEMPLATE.md +0 -15
- data/.gitignore +0 -35
- data/.rubocop.yml +0 -102
- data/.simplecov +0 -110
- data/.travis.yml +0 -51
- data/CODE_OF_CONDUCT.md +0 -74
- data/CONTRIBUTING.md +0 -105
- data/Gemfile +0 -56
- data/Rakefile +0 -103
- data/active_model_serializers.gemspec +0 -62
- data/appveyor.yml +0 -24
- data/bin/bench +0 -171
- data/bin/bench_regression +0 -316
- data/bin/serve_benchmark +0 -39
- data/docs/ARCHITECTURE.md +0 -125
- data/docs/README.md +0 -42
- data/docs/STYLE.md +0 -58
- data/docs/general/adapters.md +0 -247
- data/docs/general/caching.md +0 -58
- data/docs/general/configuration_options.md +0 -169
- data/docs/general/deserialization.md +0 -100
- data/docs/general/fields.md +0 -31
- data/docs/general/getting_started.md +0 -133
- data/docs/general/instrumentation.md +0 -40
- data/docs/general/key_transforms.md +0 -40
- data/docs/general/logging.md +0 -14
- data/docs/general/rendering.md +0 -294
- data/docs/general/serializers.md +0 -461
- data/docs/how-open-source-maintained.jpg +0 -0
- data/docs/howto/add_pagination_links.md +0 -138
- data/docs/howto/add_relationship_links.md +0 -137
- data/docs/howto/add_root_key.md +0 -55
- data/docs/howto/grape_integration.md +0 -42
- data/docs/howto/outside_controller_use.md +0 -65
- data/docs/howto/passing_arbitrary_options.md +0 -27
- data/docs/howto/serialize_poro.md +0 -32
- data/docs/howto/test.md +0 -154
- data/docs/howto/upgrade_from_0_8_to_0_10.md +0 -265
- data/docs/integrations/ember-and-json-api.md +0 -144
- data/docs/integrations/grape.md +0 -19
- data/docs/jsonapi/errors.md +0 -56
- data/docs/jsonapi/schema.md +0 -151
- data/docs/jsonapi/schema/schema.json +0 -366
- data/docs/rfcs/0000-namespace.md +0 -106
- data/docs/rfcs/template.md +0 -15
- data/lib/active_model/serializer/collection_reflection.rb +0 -7
- data/lib/active_model/serializer/concerns/associations.rb +0 -102
- data/lib/active_model/serializer/concerns/attributes.rb +0 -82
- data/lib/active_model/serializer/concerns/configuration.rb +0 -59
- data/lib/active_model/serializer/concerns/links.rb +0 -35
- data/lib/active_model/serializer/concerns/meta.rb +0 -29
- data/lib/active_model/serializer/concerns/type.rb +0 -25
- data/lib/active_model/serializer/singular_reflection.rb +0 -7
- data/lib/active_model_serializers/key_transform.rb +0 -74
- data/test/action_controller/adapter_selector_test.rb +0 -53
- data/test/action_controller/explicit_serializer_test.rb +0 -135
- data/test/action_controller/json/include_test.rb +0 -246
- data/test/action_controller/json_api/deserialization_test.rb +0 -112
- data/test/action_controller/json_api/errors_test.rb +0 -40
- data/test/action_controller/json_api/fields_test.rb +0 -57
- data/test/action_controller/json_api/linked_test.rb +0 -202
- data/test/action_controller/json_api/pagination_test.rb +0 -116
- data/test/action_controller/json_api/transform_test.rb +0 -181
- data/test/action_controller/lookup_proc_test.rb +0 -49
- data/test/action_controller/namespace_lookup_test.rb +0 -226
- data/test/action_controller/serialization_scope_name_test.rb +0 -229
- data/test/action_controller/serialization_test.rb +0 -472
- data/test/active_model_serializers/adapter_for_test.rb +0 -208
- data/test/active_model_serializers/json_pointer_test.rb +0 -22
- data/test/active_model_serializers/key_transform_test.rb +0 -297
- data/test/active_model_serializers/logging_test.rb +0 -77
- data/test/active_model_serializers/model_test.rb +0 -22
- data/test/active_model_serializers/railtie_test_isolated.rb +0 -63
- data/test/active_model_serializers/register_jsonapi_renderer_test_isolated.rb +0 -143
- data/test/active_model_serializers/serialization_context_test_isolated.rb +0 -71
- data/test/active_model_serializers/test/schema_test.rb +0 -130
- data/test/active_model_serializers/test/serializer_test.rb +0 -62
- data/test/active_record_test.rb +0 -9
- data/test/adapter/attributes_test.rb +0 -43
- data/test/adapter/deprecation_test.rb +0 -100
- data/test/adapter/json/belongs_to_test.rb +0 -45
- data/test/adapter/json/collection_test.rb +0 -104
- data/test/adapter/json/has_many_test.rb +0 -45
- data/test/adapter/json/transform_test.rb +0 -93
- data/test/adapter/json_api/belongs_to_test.rb +0 -155
- data/test/adapter/json_api/collection_test.rb +0 -96
- data/test/adapter/json_api/errors_test.rb +0 -76
- data/test/adapter/json_api/fields_test.rb +0 -88
- data/test/adapter/json_api/has_many_embed_ids_test.rb +0 -43
- data/test/adapter/json_api/has_many_explicit_serializer_test.rb +0 -96
- data/test/adapter/json_api/has_many_test.rb +0 -165
- data/test/adapter/json_api/has_one_test.rb +0 -80
- data/test/adapter/json_api/include_data_if_sideloaded_test.rb +0 -166
- data/test/adapter/json_api/json_api_test.rb +0 -33
- data/test/adapter/json_api/linked_test.rb +0 -413
- data/test/adapter/json_api/links_test.rb +0 -95
- data/test/adapter/json_api/pagination_links_test.rb +0 -193
- data/test/adapter/json_api/parse_test.rb +0 -137
- data/test/adapter/json_api/relationship_test.rb +0 -397
- data/test/adapter/json_api/resource_identifier_test.rb +0 -110
- data/test/adapter/json_api/resource_meta_test.rb +0 -100
- data/test/adapter/json_api/toplevel_jsonapi_test.rb +0 -82
- data/test/adapter/json_api/transform_test.rb +0 -504
- data/test/adapter/json_api/type_test.rb +0 -61
- data/test/adapter/json_test.rb +0 -46
- data/test/adapter/null_test.rb +0 -22
- data/test/adapter/polymorphic_test.rb +0 -171
- data/test/adapter_test.rb +0 -67
- data/test/array_serializer_test.rb +0 -22
- data/test/benchmark/app.rb +0 -65
- data/test/benchmark/benchmarking_support.rb +0 -67
- data/test/benchmark/bm_active_record.rb +0 -81
- data/test/benchmark/bm_adapter.rb +0 -38
- data/test/benchmark/bm_caching.rb +0 -119
- data/test/benchmark/bm_lookup_chain.rb +0 -83
- data/test/benchmark/bm_transform.rb +0 -45
- data/test/benchmark/config.ru +0 -3
- data/test/benchmark/controllers.rb +0 -83
- data/test/benchmark/fixtures.rb +0 -219
- data/test/cache_test.rb +0 -579
- data/test/collection_serializer_test.rb +0 -110
- data/test/fixtures/active_record.rb +0 -78
- data/test/fixtures/poro.rb +0 -286
- data/test/generators/scaffold_controller_generator_test.rb +0 -24
- data/test/generators/serializer_generator_test.rb +0 -74
- data/test/grape_test.rb +0 -178
- data/test/lint_test.rb +0 -49
- data/test/logger_test.rb +0 -20
- data/test/poro_test.rb +0 -9
- data/test/serializable_resource_test.rb +0 -79
- data/test/serializers/association_macros_test.rb +0 -37
- data/test/serializers/associations_test.rb +0 -370
- data/test/serializers/attribute_test.rb +0 -151
- data/test/serializers/attributes_test.rb +0 -52
- data/test/serializers/caching_configuration_test_isolated.rb +0 -170
- data/test/serializers/configuration_test.rb +0 -32
- data/test/serializers/fieldset_test.rb +0 -14
- data/test/serializers/meta_test.rb +0 -202
- data/test/serializers/options_test.rb +0 -21
- data/test/serializers/read_attribute_for_serialization_test.rb +0 -79
- data/test/serializers/root_test.rb +0 -21
- data/test/serializers/serialization_test.rb +0 -55
- data/test/serializers/serializer_for_test.rb +0 -136
- data/test/serializers/serializer_for_with_namespace_test.rb +0 -87
- data/test/support/custom_schemas/active_model_serializers/test/schema_test/my/index.json +0 -6
- data/test/support/isolated_unit.rb +0 -82
- data/test/support/rails5_shims.rb +0 -53
- data/test/support/rails_app.rb +0 -36
- data/test/support/schemas/active_model_serializers/test/schema_test/my/index.json +0 -6
- data/test/support/schemas/active_model_serializers/test/schema_test/my/show.json +0 -6
- data/test/support/schemas/custom/show.json +0 -7
- data/test/support/schemas/hyper_schema.json +0 -93
- data/test/support/schemas/render_using_json_api.json +0 -43
- data/test/support/schemas/simple_json_pointers.json +0 -10
- data/test/support/serialization_testing.rb +0 -71
- data/test/test_helper.rb +0 -58
|
@@ -0,0 +1,23 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
require 'active_model/serializer/field'
|
|
4
|
+
|
|
5
|
+
module ActiveModel
|
|
6
|
+
class Serializer
|
|
7
|
+
# Holds all the data about a serializer link
|
|
8
|
+
#
|
|
9
|
+
# @example
|
|
10
|
+
# class PostSerializer < ActiveModel::Serializer
|
|
11
|
+
# link :callback, if: :internal? do
|
|
12
|
+
# object.callback_link
|
|
13
|
+
# end
|
|
14
|
+
#
|
|
15
|
+
# def internal?
|
|
16
|
+
# instance_options[:internal] == true
|
|
17
|
+
# end
|
|
18
|
+
# end
|
|
19
|
+
#
|
|
20
|
+
class Link < Field
|
|
21
|
+
end
|
|
22
|
+
end
|
|
23
|
+
end
|
|
@@ -1,4 +1,7 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
1
3
|
require 'active_model/serializer/field'
|
|
4
|
+
require 'active_model/serializer/association'
|
|
2
5
|
|
|
3
6
|
module ActiveModel
|
|
4
7
|
class Serializer
|
|
@@ -8,12 +11,26 @@ module ActiveModel
|
|
|
8
11
|
# @example
|
|
9
12
|
# class PostSerializer < ActiveModel::Serializer
|
|
10
13
|
# has_one :author, serializer: AuthorSerializer
|
|
14
|
+
# belongs_to :boss, type: :users, foreign_key: :boss_id
|
|
11
15
|
# has_many :comments
|
|
12
16
|
# has_many :comments, key: :last_comments do
|
|
13
17
|
# object.comments.last(1)
|
|
14
18
|
# end
|
|
15
19
|
# has_many :secret_meta_data, if: :is_admin?
|
|
16
20
|
#
|
|
21
|
+
# has_one :blog do |serializer|
|
|
22
|
+
# meta count: object.roles.count
|
|
23
|
+
# serializer.cached_blog
|
|
24
|
+
# end
|
|
25
|
+
#
|
|
26
|
+
# private
|
|
27
|
+
#
|
|
28
|
+
# def cached_blog
|
|
29
|
+
# cache_store.fetch("cached_blog:#{object.updated_at}") do
|
|
30
|
+
# Blog.find(object.blog_id)
|
|
31
|
+
# end
|
|
32
|
+
# end
|
|
33
|
+
#
|
|
17
34
|
# def is_admin?
|
|
18
35
|
# current_user.admin?
|
|
19
36
|
# end
|
|
@@ -23,53 +40,122 @@ module ActiveModel
|
|
|
23
40
|
# 1) as 'comments' and named 'comments'.
|
|
24
41
|
# 2) as 'object.comments.last(1)' and named 'last_comments'.
|
|
25
42
|
#
|
|
26
|
-
# PostSerializer._reflections
|
|
27
|
-
# #
|
|
28
|
-
# # HasOneReflection.new(:author, serializer: AuthorSerializer),
|
|
29
|
-
# # HasManyReflection.new(:comments)
|
|
30
|
-
# # HasManyReflection.new(:comments, { key: :last_comments }, #<Block>)
|
|
31
|
-
# # HasManyReflection.new(:secret_meta_data, { if: :is_admin? })
|
|
32
|
-
# #
|
|
43
|
+
# PostSerializer._reflections # =>
|
|
44
|
+
# # {
|
|
45
|
+
# # author: HasOneReflection.new(:author, serializer: AuthorSerializer),
|
|
46
|
+
# # comments: HasManyReflection.new(:comments)
|
|
47
|
+
# # last_comments: HasManyReflection.new(:comments, { key: :last_comments }, #<Block>)
|
|
48
|
+
# # secret_meta_data: HasManyReflection.new(:secret_meta_data, { if: :is_admin? })
|
|
49
|
+
# # }
|
|
33
50
|
#
|
|
34
51
|
# So you can inspect reflections in your Adapters.
|
|
35
|
-
#
|
|
36
52
|
class Reflection < Field
|
|
53
|
+
attr_reader :foreign_key, :type
|
|
54
|
+
|
|
37
55
|
def initialize(*)
|
|
38
56
|
super
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
57
|
+
options[:links] = {}
|
|
58
|
+
options[:include_data_setting] = Serializer.config.include_data_default
|
|
59
|
+
options[:meta] = nil
|
|
60
|
+
@type = options.fetch(:type) do
|
|
61
|
+
class_name = options.fetch(:class_name, name.to_s.camelize.singularize)
|
|
62
|
+
class_name.underscore.pluralize.to_sym
|
|
63
|
+
end
|
|
64
|
+
@foreign_key = options.fetch(:foreign_key) do
|
|
65
|
+
if collection?
|
|
66
|
+
"#{name.to_s.singularize}_ids".to_sym
|
|
67
|
+
else
|
|
68
|
+
"#{name}_id".to_sym
|
|
69
|
+
end
|
|
70
|
+
end
|
|
42
71
|
end
|
|
43
72
|
|
|
73
|
+
# @api public
|
|
74
|
+
# @example
|
|
75
|
+
# has_one :blog do
|
|
76
|
+
# include_data false
|
|
77
|
+
# link :self, 'a link'
|
|
78
|
+
# link :related, 'another link'
|
|
79
|
+
# link :self, '//example.com/link_author/relationships/bio'
|
|
80
|
+
# id = object.profile.id
|
|
81
|
+
# link :related do
|
|
82
|
+
# "//example.com/profiles/#{id}" if id != 123
|
|
83
|
+
# end
|
|
84
|
+
# link :related do
|
|
85
|
+
# ids = object.likes.map(&:id).join(',')
|
|
86
|
+
# href "//example.com/likes/#{ids}"
|
|
87
|
+
# meta ids: ids
|
|
88
|
+
# end
|
|
89
|
+
# end
|
|
44
90
|
def link(name, value = nil, &block)
|
|
45
|
-
|
|
91
|
+
options[:links][name] = block_given? ? block : value
|
|
46
92
|
:nil
|
|
47
93
|
end
|
|
48
94
|
|
|
95
|
+
# @api public
|
|
96
|
+
# @example
|
|
97
|
+
# has_one :blog do
|
|
98
|
+
# include_data false
|
|
99
|
+
# meta(id: object.blog.id)
|
|
100
|
+
# meta liked: object.likes.any?
|
|
101
|
+
# link :self do
|
|
102
|
+
# href object.blog.id.to_s
|
|
103
|
+
# meta(id: object.blog.id)
|
|
104
|
+
# end
|
|
49
105
|
def meta(value = nil, &block)
|
|
50
|
-
|
|
106
|
+
options[:meta] = block_given? ? block : value
|
|
51
107
|
:nil
|
|
52
108
|
end
|
|
53
109
|
|
|
110
|
+
# @api public
|
|
111
|
+
# @example
|
|
112
|
+
# has_one :blog do
|
|
113
|
+
# include_data false
|
|
114
|
+
# link :self, 'a link'
|
|
115
|
+
# link :related, 'another link'
|
|
116
|
+
# end
|
|
117
|
+
#
|
|
118
|
+
# has_one :blog do
|
|
119
|
+
# include_data false
|
|
120
|
+
# link :self, 'a link'
|
|
121
|
+
# link :related, 'another link'
|
|
122
|
+
# end
|
|
123
|
+
#
|
|
124
|
+
# belongs_to :reviewer do
|
|
125
|
+
# meta name: 'Dan Brown'
|
|
126
|
+
# include_data true
|
|
127
|
+
# end
|
|
128
|
+
#
|
|
129
|
+
# has_many :tags, serializer: TagSerializer do
|
|
130
|
+
# link :self, '//example.com/link_author/relationships/tags'
|
|
131
|
+
# include_data :if_sideloaded
|
|
132
|
+
# end
|
|
54
133
|
def include_data(value = true)
|
|
55
|
-
|
|
134
|
+
options[:include_data_setting] = value
|
|
56
135
|
:nil
|
|
57
136
|
end
|
|
58
137
|
|
|
138
|
+
def collection?
|
|
139
|
+
false
|
|
140
|
+
end
|
|
141
|
+
|
|
142
|
+
def include_data?(include_slice)
|
|
143
|
+
include_data_setting = options[:include_data_setting]
|
|
144
|
+
case include_data_setting
|
|
145
|
+
when :if_sideloaded then include_slice.key?(options.fetch(:key, name))
|
|
146
|
+
when true then true
|
|
147
|
+
when false then false
|
|
148
|
+
else fail ArgumentError, "Unknown include_data_setting '#{include_data_setting.inspect}'"
|
|
149
|
+
end
|
|
150
|
+
end
|
|
151
|
+
|
|
59
152
|
# @param serializer [ActiveModel::Serializer]
|
|
60
153
|
# @yield [ActiveModel::Serializer]
|
|
61
154
|
# @return [:nil, associated resource or resource collection]
|
|
62
|
-
# @example
|
|
63
|
-
# has_one :blog do |serializer|
|
|
64
|
-
# serializer.cached_blog
|
|
65
|
-
# end
|
|
66
|
-
#
|
|
67
|
-
# def cached_blog
|
|
68
|
-
# cache_store.fetch("cached_blog:#{object.updated_at}") do
|
|
69
|
-
# Blog.find(object.blog_id)
|
|
70
|
-
# end
|
|
71
|
-
# end
|
|
72
155
|
def value(serializer, include_slice)
|
|
156
|
+
# NOTE(BF): This method isn't thread-safe because the _reflections class attribute is not thread-safe
|
|
157
|
+
# Therefore, when we build associations from reflections, we dup the entire reflection instance.
|
|
158
|
+
# Better solutions much appreciated!
|
|
73
159
|
@object = serializer.object
|
|
74
160
|
@scope = serializer.scope
|
|
75
161
|
|
|
@@ -83,6 +169,11 @@ module ActiveModel
|
|
|
83
169
|
end
|
|
84
170
|
end
|
|
85
171
|
|
|
172
|
+
# @api private
|
|
173
|
+
def foreign_key_on
|
|
174
|
+
:related
|
|
175
|
+
end
|
|
176
|
+
|
|
86
177
|
# Build association. This method is used internally to
|
|
87
178
|
# build serializer's association by its reflection.
|
|
88
179
|
#
|
|
@@ -103,61 +194,19 @@ module ActiveModel
|
|
|
103
194
|
# comments_reflection.build_association(post_serializer, foo: 'bar')
|
|
104
195
|
#
|
|
105
196
|
# @api private
|
|
106
|
-
#
|
|
107
197
|
def build_association(parent_serializer, parent_serializer_options, include_slice = {})
|
|
108
|
-
|
|
109
|
-
|
|
110
|
-
|
|
111
|
-
|
|
112
|
-
|
|
113
|
-
|
|
114
|
-
serializer_class = parent_serializer.class.serializer_for(association_value, reflection_options)
|
|
115
|
-
reflection_options[:include_data] = include_data?(include_slice)
|
|
116
|
-
reflection_options[:links] = @_links
|
|
117
|
-
reflection_options[:meta] = @_meta
|
|
118
|
-
|
|
119
|
-
if serializer_class
|
|
120
|
-
serializer = catch(:no_serializer) do
|
|
121
|
-
serializer_class.new(
|
|
122
|
-
association_value,
|
|
123
|
-
serializer_options(parent_serializer, parent_serializer_options, reflection_options)
|
|
124
|
-
)
|
|
125
|
-
end
|
|
126
|
-
if serializer.nil?
|
|
127
|
-
reflection_options[:virtual_value] = association_value.try(:as_json) || association_value
|
|
128
|
-
else
|
|
129
|
-
reflection_options[:serializer] = serializer
|
|
130
|
-
end
|
|
131
|
-
elsif !association_value.nil? && !association_value.instance_of?(Object)
|
|
132
|
-
reflection_options[:virtual_value] = association_value
|
|
133
|
-
end
|
|
134
|
-
|
|
135
|
-
block = nil
|
|
136
|
-
Association.new(name, reflection_options, block)
|
|
198
|
+
association_options = {
|
|
199
|
+
parent_serializer: parent_serializer,
|
|
200
|
+
parent_serializer_options: parent_serializer_options,
|
|
201
|
+
include_slice: include_slice
|
|
202
|
+
}
|
|
203
|
+
Association.new(self, association_options)
|
|
137
204
|
end
|
|
138
205
|
|
|
139
206
|
protected
|
|
140
207
|
|
|
208
|
+
# used in instance exec
|
|
141
209
|
attr_accessor :object, :scope
|
|
142
|
-
|
|
143
|
-
private
|
|
144
|
-
|
|
145
|
-
def include_data?(include_slice)
|
|
146
|
-
if @_include_data == :if_sideloaded
|
|
147
|
-
include_slice.key?(name)
|
|
148
|
-
else
|
|
149
|
-
@_include_data
|
|
150
|
-
end
|
|
151
|
-
end
|
|
152
|
-
|
|
153
|
-
def serializer_options(parent_serializer, parent_serializer_options, reflection_options)
|
|
154
|
-
serializer = reflection_options.fetch(:serializer, nil)
|
|
155
|
-
|
|
156
|
-
serializer_options = parent_serializer_options.except(:serializer)
|
|
157
|
-
serializer_options[:serializer] = serializer if serializer
|
|
158
|
-
serializer_options[:serializer_context_class] = parent_serializer.class
|
|
159
|
-
serializer_options
|
|
160
|
-
end
|
|
161
210
|
end
|
|
162
211
|
end
|
|
163
212
|
end
|
|
@@ -1,3 +1,5 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
1
3
|
require 'active_model'
|
|
2
4
|
require 'active_support'
|
|
3
5
|
require 'active_support/core_ext/object/with_options'
|
|
@@ -5,16 +7,19 @@ require 'active_support/core_ext/string/inflections'
|
|
|
5
7
|
require 'active_support/json'
|
|
6
8
|
module ActiveModelSerializers
|
|
7
9
|
extend ActiveSupport::Autoload
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
10
|
+
eager_autoload do
|
|
11
|
+
autoload :Model
|
|
12
|
+
autoload :Callbacks
|
|
13
|
+
autoload :SerializableResource
|
|
14
|
+
autoload :SerializationContext
|
|
15
|
+
autoload :Logging
|
|
16
|
+
autoload :Test
|
|
17
|
+
autoload :Adapter
|
|
18
|
+
autoload :JsonPointer
|
|
19
|
+
autoload :Deprecate
|
|
20
|
+
autoload :LookupChain
|
|
21
|
+
autoload :Deserialization
|
|
22
|
+
end
|
|
18
23
|
|
|
19
24
|
class << self; attr_accessor :logger; end
|
|
20
25
|
self.logger = ActiveSupport::TaggedLogging.new(ActiveSupport::Logger.new(STDOUT))
|
|
@@ -38,8 +43,21 @@ module ActiveModelSerializers
|
|
|
38
43
|
@default_include_directive ||= JSONAPI::IncludeDirective.new(config.default_includes, allow_wildcard: true)
|
|
39
44
|
end
|
|
40
45
|
|
|
46
|
+
def self.silence_warnings
|
|
47
|
+
original_verbose = $VERBOSE
|
|
48
|
+
$VERBOSE = nil
|
|
49
|
+
yield
|
|
50
|
+
ensure
|
|
51
|
+
$VERBOSE = original_verbose
|
|
52
|
+
end
|
|
53
|
+
|
|
54
|
+
def self.eager_load!
|
|
55
|
+
super
|
|
56
|
+
ActiveModel::Serializer.eager_load!
|
|
57
|
+
end
|
|
58
|
+
|
|
41
59
|
require 'active_model/serializer/version'
|
|
42
60
|
require 'active_model/serializer'
|
|
43
61
|
require 'active_model/serializable_resource'
|
|
44
|
-
require 'active_model_serializers/railtie' if defined?(::Rails)
|
|
62
|
+
require 'active_model_serializers/railtie' if defined?(::Rails::Railtie)
|
|
45
63
|
end
|
|
@@ -1,3 +1,5 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
1
3
|
module ActiveModelSerializers
|
|
2
4
|
module Adapter
|
|
3
5
|
UnknownAdapterError = Class.new(ArgumentError)
|
|
@@ -35,7 +37,7 @@ module ActiveModelSerializers
|
|
|
35
37
|
|
|
36
38
|
# @return [Array<Symbol>] list of adapter names
|
|
37
39
|
def adapters
|
|
38
|
-
adapter_map.keys.sort
|
|
40
|
+
adapter_map.keys.sort!
|
|
39
41
|
end
|
|
40
42
|
|
|
41
43
|
# Adds an adapter 'klass' with 'name' to the 'adapter_map'
|
|
@@ -1,6 +1,13 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
1
3
|
module ActiveModelSerializers
|
|
2
4
|
module Adapter
|
|
3
5
|
class Attributes < Base
|
|
6
|
+
def initialize(*)
|
|
7
|
+
super
|
|
8
|
+
instance_options[:fieldset] ||= ActiveModel::Serializer::Fieldset.new(fields_to_fieldset(instance_options.delete(:fields)))
|
|
9
|
+
end
|
|
10
|
+
|
|
4
11
|
def serializable_hash(options = nil)
|
|
5
12
|
options = serialization_options(options)
|
|
6
13
|
options[:fields] ||= instance_options[:fields]
|
|
@@ -8,6 +15,22 @@ module ActiveModelSerializers
|
|
|
8
15
|
|
|
9
16
|
self.class.transform_key_casing!(serialized_hash, instance_options)
|
|
10
17
|
end
|
|
18
|
+
|
|
19
|
+
private
|
|
20
|
+
|
|
21
|
+
def fields_to_fieldset(fields)
|
|
22
|
+
return fields if fields.nil?
|
|
23
|
+
resource_fields = []
|
|
24
|
+
relationship_fields = {}
|
|
25
|
+
fields.each do |field|
|
|
26
|
+
case field
|
|
27
|
+
when Symbol, String then resource_fields << field
|
|
28
|
+
when Hash then relationship_fields.merge!(field)
|
|
29
|
+
else fail ArgumentError, "Unknown conversion of fields to fieldset: '#{field.inspect}' in '#{fields.inspect}'"
|
|
30
|
+
end
|
|
31
|
+
end
|
|
32
|
+
relationship_fields.merge!(serializer.json_key.to_sym => resource_fields)
|
|
33
|
+
end
|
|
11
34
|
end
|
|
12
35
|
end
|
|
13
36
|
end
|
|
@@ -1,4 +1,6 @@
|
|
|
1
|
-
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
require 'case_transform'
|
|
2
4
|
|
|
3
5
|
module ActiveModelSerializers
|
|
4
6
|
module Adapter
|
|
@@ -31,7 +33,7 @@ module ActiveModelSerializers
|
|
|
31
33
|
# @param options [Object] serializable resource options
|
|
32
34
|
# @return [Symbol] the default transform for the adapter
|
|
33
35
|
def self.transform_key_casing!(value, options)
|
|
34
|
-
|
|
36
|
+
CaseTransform.send(transform(options), value)
|
|
35
37
|
end
|
|
36
38
|
|
|
37
39
|
def self.cache_key
|
|
@@ -1,3 +1,5 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
1
3
|
# {http://jsonapi.org/format/ JSON API specification}
|
|
2
4
|
# rubocop:disable Style/AsciiComments
|
|
3
5
|
# TODO: implement!
|
|
@@ -22,14 +24,16 @@ module ActiveModelSerializers
|
|
|
22
24
|
module Adapter
|
|
23
25
|
class JsonApi < Base
|
|
24
26
|
extend ActiveSupport::Autoload
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
27
|
+
eager_autoload do
|
|
28
|
+
autoload :Jsonapi
|
|
29
|
+
autoload :ResourceIdentifier
|
|
30
|
+
autoload :Link
|
|
31
|
+
autoload :PaginationLinks
|
|
32
|
+
autoload :Meta
|
|
33
|
+
autoload :Error
|
|
34
|
+
autoload :Deserialization
|
|
35
|
+
autoload :Relationship
|
|
36
|
+
end
|
|
33
37
|
|
|
34
38
|
def self.default_key_transform
|
|
35
39
|
:dash
|
|
@@ -257,7 +261,8 @@ module ActiveModelSerializers
|
|
|
257
261
|
|
|
258
262
|
def process_relationships(serializer, include_slice)
|
|
259
263
|
serializer.associations(include_slice).each do |association|
|
|
260
|
-
|
|
264
|
+
# TODO(BF): Process relationship without evaluating lazy_association
|
|
265
|
+
process_relationship(association.lazy_association.serializer, include_slice[association.key])
|
|
261
266
|
end
|
|
262
267
|
end
|
|
263
268
|
|
|
@@ -294,20 +299,8 @@ module ActiveModelSerializers
|
|
|
294
299
|
|
|
295
300
|
# {http://jsonapi.org/format/#document-resource-objects Document Resource Objects}
|
|
296
301
|
def resource_object_for(serializer, include_slice = {})
|
|
297
|
-
resource_object = serializer
|
|
298
|
-
resource_object = ResourceIdentifier.new(serializer, instance_options).as_json
|
|
302
|
+
resource_object = data_for(serializer, include_slice)
|
|
299
303
|
|
|
300
|
-
requested_fields = fieldset && fieldset.fields_for(resource_object[:type])
|
|
301
|
-
attributes = attributes_for(serializer, requested_fields)
|
|
302
|
-
resource_object[:attributes] = attributes if attributes.any?
|
|
303
|
-
resource_object
|
|
304
|
-
end
|
|
305
|
-
|
|
306
|
-
requested_associations = fieldset.fields_for(resource_object[:type]) || '*'
|
|
307
|
-
relationships = relationships_for(serializer, requested_associations, include_slice)
|
|
308
|
-
resource_object[:relationships] = relationships if relationships.any?
|
|
309
|
-
|
|
310
|
-
links = links_for(serializer)
|
|
311
304
|
# toplevel_links
|
|
312
305
|
# definition:
|
|
313
306
|
# allOf
|
|
@@ -321,7 +314,10 @@ module ActiveModelSerializers
|
|
|
321
314
|
# prs:
|
|
322
315
|
# https://github.com/rails-api/active_model_serializers/pull/1247
|
|
323
316
|
# https://github.com/rails-api/active_model_serializers/pull/1018
|
|
324
|
-
|
|
317
|
+
if (links = links_for(serializer)).any?
|
|
318
|
+
resource_object ||= {}
|
|
319
|
+
resource_object[:links] = links
|
|
320
|
+
end
|
|
325
321
|
|
|
326
322
|
# toplevel_meta
|
|
327
323
|
# alias meta
|
|
@@ -331,12 +327,33 @@ module ActiveModelSerializers
|
|
|
331
327
|
# {
|
|
332
328
|
# :'git-ref' => 'abc123'
|
|
333
329
|
# }
|
|
334
|
-
meta = meta_for(serializer)
|
|
335
|
-
|
|
330
|
+
if (meta = meta_for(serializer)).present?
|
|
331
|
+
resource_object ||= {}
|
|
332
|
+
resource_object[:meta] = meta
|
|
333
|
+
end
|
|
336
334
|
|
|
337
335
|
resource_object
|
|
338
336
|
end
|
|
339
337
|
|
|
338
|
+
def data_for(serializer, include_slice)
|
|
339
|
+
data = serializer.fetch(self) do
|
|
340
|
+
resource_object = ResourceIdentifier.new(serializer, instance_options).as_json
|
|
341
|
+
break nil if resource_object.nil?
|
|
342
|
+
|
|
343
|
+
requested_fields = fieldset && fieldset.fields_for(resource_object[:type])
|
|
344
|
+
attributes = attributes_for(serializer, requested_fields)
|
|
345
|
+
resource_object[:attributes] = attributes if attributes.any?
|
|
346
|
+
resource_object
|
|
347
|
+
end
|
|
348
|
+
data.tap do |resource_object|
|
|
349
|
+
next if resource_object.nil?
|
|
350
|
+
# NOTE(BF): the attributes are cached above, separately from the relationships, below.
|
|
351
|
+
requested_associations = fieldset.fields_for(resource_object[:type]) || '*'
|
|
352
|
+
relationships = relationships_for(serializer, requested_associations, include_slice)
|
|
353
|
+
resource_object[:relationships] = relationships if relationships.any?
|
|
354
|
+
end
|
|
355
|
+
end
|
|
356
|
+
|
|
340
357
|
# {http://jsonapi.org/format/#document-resource-object-relationships Document Resource Object Relationship}
|
|
341
358
|
# relationships
|
|
342
359
|
# definition:
|
|
@@ -467,7 +484,8 @@ module ActiveModelSerializers
|
|
|
467
484
|
# }.reject! {|_,v| v.nil? }
|
|
468
485
|
def links_for(serializer)
|
|
469
486
|
serializer._links.each_with_object({}) do |(name, value), hash|
|
|
470
|
-
|
|
487
|
+
next if value.excluded?(serializer)
|
|
488
|
+
result = Link.new(serializer, value.block).as_json
|
|
471
489
|
hash[name] = result if result
|
|
472
490
|
end
|
|
473
491
|
end
|