active_model_serializers_custom 0.10.90
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 +7 -0
- data/.github/ISSUE_TEMPLATE.md +29 -0
- data/.github/PULL_REQUEST_TEMPLATE.md +15 -0
- data/.gitignore +35 -0
- data/.rubocop.yml +109 -0
- data/.simplecov +110 -0
- data/.travis.yml +63 -0
- data/CHANGELOG.md +727 -0
- data/CODE_OF_CONDUCT.md +74 -0
- data/CONTRIBUTING.md +105 -0
- data/Gemfile +74 -0
- data/MIT-LICENSE +22 -0
- data/README.md +305 -0
- data/Rakefile +76 -0
- data/active_model_serializers.gemspec +64 -0
- data/appveyor.yml +28 -0
- data/bin/bench +171 -0
- data/bin/bench_regression +316 -0
- data/bin/rubocop +38 -0
- data/bin/serve_benchmark +39 -0
- data/docs/README.md +41 -0
- data/docs/STYLE.md +58 -0
- data/docs/general/adapters.md +269 -0
- data/docs/general/caching.md +58 -0
- data/docs/general/configuration_options.md +185 -0
- data/docs/general/deserialization.md +100 -0
- data/docs/general/fields.md +31 -0
- data/docs/general/getting_started.md +133 -0
- data/docs/general/instrumentation.md +40 -0
- data/docs/general/key_transforms.md +40 -0
- data/docs/general/logging.md +21 -0
- data/docs/general/rendering.md +293 -0
- data/docs/general/serializers.md +495 -0
- data/docs/how-open-source-maintained.jpg +0 -0
- data/docs/howto/add_pagination_links.md +138 -0
- data/docs/howto/add_relationship_links.md +140 -0
- data/docs/howto/add_root_key.md +62 -0
- data/docs/howto/grape_integration.md +42 -0
- data/docs/howto/outside_controller_use.md +66 -0
- data/docs/howto/passing_arbitrary_options.md +27 -0
- data/docs/howto/serialize_poro.md +73 -0
- data/docs/howto/test.md +154 -0
- data/docs/howto/upgrade_from_0_8_to_0_10.md +265 -0
- data/docs/integrations/ember-and-json-api.md +147 -0
- data/docs/integrations/grape.md +19 -0
- data/docs/jsonapi/errors.md +56 -0
- data/docs/jsonapi/schema.md +151 -0
- data/docs/jsonapi/schema/schema.json +366 -0
- data/docs/rfcs/0000-namespace.md +106 -0
- data/docs/rfcs/template.md +15 -0
- data/lib/action_controller/serialization.rb +76 -0
- data/lib/active_model/serializable_resource.rb +13 -0
- data/lib/active_model/serializer.rb +418 -0
- data/lib/active_model/serializer/adapter.rb +26 -0
- data/lib/active_model/serializer/adapter/attributes.rb +17 -0
- data/lib/active_model/serializer/adapter/base.rb +20 -0
- data/lib/active_model/serializer/adapter/json.rb +17 -0
- data/lib/active_model/serializer/adapter/json_api.rb +17 -0
- data/lib/active_model/serializer/adapter/null.rb +17 -0
- data/lib/active_model/serializer/array_serializer.rb +14 -0
- data/lib/active_model/serializer/association.rb +91 -0
- data/lib/active_model/serializer/attribute.rb +27 -0
- data/lib/active_model/serializer/belongs_to_reflection.rb +13 -0
- data/lib/active_model/serializer/collection_serializer.rb +90 -0
- data/lib/active_model/serializer/concerns/caching.rb +304 -0
- data/lib/active_model/serializer/error_serializer.rb +16 -0
- data/lib/active_model/serializer/errors_serializer.rb +34 -0
- data/lib/active_model/serializer/field.rb +92 -0
- data/lib/active_model/serializer/fieldset.rb +33 -0
- data/lib/active_model/serializer/has_many_reflection.rb +12 -0
- data/lib/active_model/serializer/has_one_reflection.rb +9 -0
- 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 +152 -0
- data/lib/active_model/serializer/null.rb +19 -0
- data/lib/active_model/serializer/reflection.rb +212 -0
- data/lib/active_model/serializer/version.rb +7 -0
- data/lib/active_model_serializers.rb +63 -0
- data/lib/active_model_serializers/adapter.rb +100 -0
- data/lib/active_model_serializers/adapter/attributes.rb +15 -0
- data/lib/active_model_serializers/adapter/base.rb +85 -0
- data/lib/active_model_serializers/adapter/json.rb +23 -0
- data/lib/active_model_serializers/adapter/json_api.rb +535 -0
- data/lib/active_model_serializers/adapter/json_api/deserialization.rb +215 -0
- data/lib/active_model_serializers/adapter/json_api/error.rb +98 -0
- data/lib/active_model_serializers/adapter/json_api/jsonapi.rb +51 -0
- data/lib/active_model_serializers/adapter/json_api/link.rb +85 -0
- data/lib/active_model_serializers/adapter/json_api/meta.rb +39 -0
- data/lib/active_model_serializers/adapter/json_api/pagination_links.rb +90 -0
- data/lib/active_model_serializers/adapter/json_api/relationship.rb +106 -0
- data/lib/active_model_serializers/adapter/json_api/resource_identifier.rb +68 -0
- data/lib/active_model_serializers/adapter/null.rb +11 -0
- data/lib/active_model_serializers/callbacks.rb +57 -0
- data/lib/active_model_serializers/deprecate.rb +56 -0
- data/lib/active_model_serializers/deserialization.rb +17 -0
- data/lib/active_model_serializers/json_pointer.rb +16 -0
- data/lib/active_model_serializers/logging.rb +124 -0
- data/lib/active_model_serializers/lookup_chain.rb +82 -0
- data/lib/active_model_serializers/model.rb +132 -0
- data/lib/active_model_serializers/railtie.rb +52 -0
- data/lib/active_model_serializers/register_jsonapi_renderer.rb +80 -0
- data/lib/active_model_serializers/serializable_resource.rb +84 -0
- data/lib/active_model_serializers/serialization_context.rb +41 -0
- data/lib/active_model_serializers/test.rb +9 -0
- data/lib/active_model_serializers/test/schema.rb +140 -0
- data/lib/active_model_serializers/test/serializer.rb +127 -0
- data/lib/generators/rails/USAGE +6 -0
- data/lib/generators/rails/resource_override.rb +12 -0
- data/lib/generators/rails/serializer_generator.rb +38 -0
- data/lib/generators/rails/templates/serializer.rb.erb +8 -0
- data/lib/grape/active_model_serializers.rb +18 -0
- data/lib/grape/formatters/active_model_serializers.rb +34 -0
- data/lib/grape/helpers/active_model_serializers.rb +19 -0
- data/lib/tasks/rubocop.rake +55 -0
- data/test/action_controller/adapter_selector_test.rb +64 -0
- data/test/action_controller/explicit_serializer_test.rb +137 -0
- data/test/action_controller/json/include_test.rb +248 -0
- data/test/action_controller/json_api/deserialization_test.rb +114 -0
- data/test/action_controller/json_api/errors_test.rb +42 -0
- data/test/action_controller/json_api/fields_test.rb +68 -0
- data/test/action_controller/json_api/linked_test.rb +204 -0
- data/test/action_controller/json_api/pagination_test.rb +126 -0
- data/test/action_controller/json_api/transform_test.rb +191 -0
- data/test/action_controller/lookup_proc_test.rb +51 -0
- data/test/action_controller/namespace_lookup_test.rb +239 -0
- data/test/action_controller/serialization_scope_name_test.rb +237 -0
- data/test/action_controller/serialization_test.rb +480 -0
- data/test/active_model_serializers/adapter_for_test.rb +210 -0
- data/test/active_model_serializers/json_pointer_test.rb +24 -0
- data/test/active_model_serializers/logging_test.rb +79 -0
- data/test/active_model_serializers/model_test.rb +144 -0
- data/test/active_model_serializers/railtie_test_isolated.rb +70 -0
- data/test/active_model_serializers/register_jsonapi_renderer_test_isolated.rb +163 -0
- data/test/active_model_serializers/serialization_context_test_isolated.rb +73 -0
- data/test/active_model_serializers/test/schema_test.rb +133 -0
- data/test/active_model_serializers/test/serializer_test.rb +64 -0
- data/test/active_record_test.rb +11 -0
- data/test/adapter/attributes_test.rb +42 -0
- data/test/adapter/deprecation_test.rb +102 -0
- data/test/adapter/json/belongs_to_test.rb +47 -0
- data/test/adapter/json/collection_test.rb +106 -0
- data/test/adapter/json/has_many_test.rb +55 -0
- data/test/adapter/json/transform_test.rb +95 -0
- data/test/adapter/json_api/belongs_to_test.rb +157 -0
- data/test/adapter/json_api/collection_test.rb +98 -0
- data/test/adapter/json_api/errors_test.rb +78 -0
- data/test/adapter/json_api/fields_test.rb +98 -0
- data/test/adapter/json_api/has_many_explicit_serializer_test.rb +98 -0
- data/test/adapter/json_api/has_many_test.rb +175 -0
- data/test/adapter/json_api/has_one_test.rb +82 -0
- data/test/adapter/json_api/include_data_if_sideloaded_test.rb +215 -0
- data/test/adapter/json_api/json_api_test.rb +35 -0
- data/test/adapter/json_api/linked_test.rb +415 -0
- data/test/adapter/json_api/links_test.rb +112 -0
- data/test/adapter/json_api/pagination_links_test.rb +208 -0
- data/test/adapter/json_api/parse_test.rb +139 -0
- data/test/adapter/json_api/relationship_test.rb +399 -0
- data/test/adapter/json_api/resource_meta_test.rb +102 -0
- data/test/adapter/json_api/toplevel_jsonapi_test.rb +84 -0
- data/test/adapter/json_api/transform_test.rb +514 -0
- data/test/adapter/json_api/type_test.rb +195 -0
- data/test/adapter/json_test.rb +48 -0
- data/test/adapter/null_test.rb +24 -0
- data/test/adapter/polymorphic_test.rb +220 -0
- data/test/adapter_test.rb +69 -0
- data/test/array_serializer_test.rb +24 -0
- data/test/benchmark/app.rb +67 -0
- data/test/benchmark/benchmarking_support.rb +69 -0
- data/test/benchmark/bm_active_record.rb +83 -0
- data/test/benchmark/bm_adapter.rb +40 -0
- data/test/benchmark/bm_caching.rb +121 -0
- data/test/benchmark/bm_lookup_chain.rb +85 -0
- data/test/benchmark/bm_transform.rb +47 -0
- data/test/benchmark/config.ru +3 -0
- data/test/benchmark/controllers.rb +85 -0
- data/test/benchmark/fixtures.rb +221 -0
- data/test/cache_test.rb +717 -0
- data/test/collection_serializer_test.rb +129 -0
- data/test/fixtures/active_record.rb +115 -0
- data/test/fixtures/poro.rb +227 -0
- data/test/generators/scaffold_controller_generator_test.rb +26 -0
- data/test/generators/serializer_generator_test.rb +77 -0
- data/test/grape_test.rb +198 -0
- data/test/lint_test.rb +51 -0
- data/test/logger_test.rb +22 -0
- data/test/poro_test.rb +11 -0
- data/test/serializable_resource_test.rb +81 -0
- data/test/serializers/association_macros_test.rb +39 -0
- data/test/serializers/associations_test.rb +520 -0
- data/test/serializers/attribute_test.rb +155 -0
- data/test/serializers/attributes_test.rb +54 -0
- data/test/serializers/caching_configuration_test_isolated.rb +172 -0
- data/test/serializers/configuration_test.rb +34 -0
- data/test/serializers/fieldset_test.rb +16 -0
- data/test/serializers/meta_test.rb +204 -0
- data/test/serializers/options_test.rb +34 -0
- data/test/serializers/read_attribute_for_serialization_test.rb +81 -0
- data/test/serializers/reflection_test.rb +481 -0
- data/test/serializers/root_test.rb +23 -0
- data/test/serializers/serialization_test.rb +57 -0
- data/test/serializers/serializer_for_test.rb +138 -0
- data/test/serializers/serializer_for_with_namespace_test.rb +90 -0
- data/test/support/custom_schemas/active_model_serializers/test/schema_test/my/index.json +6 -0
- data/test/support/isolated_unit.rb +86 -0
- data/test/support/rails5_shims.rb +55 -0
- data/test/support/rails_app.rb +40 -0
- data/test/support/schemas/active_model_serializers/test/schema_test/my/index.json +6 -0
- data/test/support/schemas/active_model_serializers/test/schema_test/my/show.json +6 -0
- data/test/support/schemas/custom/show.json +7 -0
- data/test/support/schemas/hyper_schema.json +93 -0
- data/test/support/schemas/render_using_json_api.json +43 -0
- data/test/support/schemas/simple_json_pointers.json +10 -0
- data/test/support/serialization_testing.rb +81 -0
- data/test/test_helper.rb +72 -0
- metadata +622 -0
|
@@ -0,0 +1,39 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
require 'test_helper'
|
|
4
|
+
|
|
5
|
+
module ActiveModel
|
|
6
|
+
class Serializer
|
|
7
|
+
class AssociationMacrosTest < ActiveSupport::TestCase
|
|
8
|
+
class AuthorSummarySerializer < ActiveModel::Serializer; end
|
|
9
|
+
|
|
10
|
+
class AssociationsTestSerializer < Serializer
|
|
11
|
+
belongs_to :author, serializer: AuthorSummarySerializer
|
|
12
|
+
has_many :comments
|
|
13
|
+
has_one :category
|
|
14
|
+
end
|
|
15
|
+
|
|
16
|
+
def before_setup
|
|
17
|
+
@reflections = AssociationsTestSerializer._reflections.values
|
|
18
|
+
end
|
|
19
|
+
|
|
20
|
+
def test_has_one_defines_reflection
|
|
21
|
+
has_one_reflection = HasOneReflection.new(:category, {})
|
|
22
|
+
|
|
23
|
+
assert_includes(@reflections, has_one_reflection)
|
|
24
|
+
end
|
|
25
|
+
|
|
26
|
+
def test_has_many_defines_reflection
|
|
27
|
+
has_many_reflection = HasManyReflection.new(:comments, {})
|
|
28
|
+
|
|
29
|
+
assert_includes(@reflections, has_many_reflection)
|
|
30
|
+
end
|
|
31
|
+
|
|
32
|
+
def test_belongs_to_defines_reflection
|
|
33
|
+
belongs_to_reflection = BelongsToReflection.new(:author, serializer: AuthorSummarySerializer)
|
|
34
|
+
|
|
35
|
+
assert_includes(@reflections, belongs_to_reflection)
|
|
36
|
+
end
|
|
37
|
+
end
|
|
38
|
+
end
|
|
39
|
+
end
|
|
@@ -0,0 +1,520 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
require 'test_helper'
|
|
4
|
+
module ActiveModel
|
|
5
|
+
class Serializer
|
|
6
|
+
class AssociationsTest < ActiveSupport::TestCase
|
|
7
|
+
class ModelWithoutSerializer < ::Model
|
|
8
|
+
attributes :id, :name
|
|
9
|
+
end
|
|
10
|
+
|
|
11
|
+
def setup
|
|
12
|
+
@author = Author.new(name: 'Steve K.')
|
|
13
|
+
@author.bio = nil
|
|
14
|
+
@author.roles = []
|
|
15
|
+
@blog = Blog.new(name: 'AMS Blog')
|
|
16
|
+
@post = Post.new(title: 'New Post', body: 'Body')
|
|
17
|
+
@tag = ModelWithoutSerializer.new(id: 'tagid', name: '#hashtagged')
|
|
18
|
+
@comment = Comment.new(id: 1, body: 'ZOMG A COMMENT')
|
|
19
|
+
@post.comments = [@comment]
|
|
20
|
+
@post.tags = [@tag]
|
|
21
|
+
@post.blog = @blog
|
|
22
|
+
@comment.post = @post
|
|
23
|
+
@comment.author = nil
|
|
24
|
+
@post.author = @author
|
|
25
|
+
@author.posts = [@post]
|
|
26
|
+
|
|
27
|
+
@post_serializer = PostSerializer.new(@post, custom_options: true)
|
|
28
|
+
@author_serializer = AuthorSerializer.new(@author)
|
|
29
|
+
@comment_serializer = CommentSerializer.new(@comment)
|
|
30
|
+
end
|
|
31
|
+
|
|
32
|
+
def test_has_many_and_has_one
|
|
33
|
+
@author_serializer.associations.each do |association|
|
|
34
|
+
key = association.key
|
|
35
|
+
serializer = association.lazy_association.serializer
|
|
36
|
+
|
|
37
|
+
case key
|
|
38
|
+
when :posts
|
|
39
|
+
assert_equal true, association.include_data?
|
|
40
|
+
assert_kind_of(ActiveModelSerializers.config.collection_serializer, serializer)
|
|
41
|
+
when :bio
|
|
42
|
+
assert_equal true, association.include_data?
|
|
43
|
+
assert_nil serializer
|
|
44
|
+
when :roles
|
|
45
|
+
assert_equal true, association.include_data?
|
|
46
|
+
assert_kind_of(ActiveModelSerializers.config.collection_serializer, serializer)
|
|
47
|
+
else
|
|
48
|
+
flunk "Unknown association: #{key}"
|
|
49
|
+
end
|
|
50
|
+
end
|
|
51
|
+
end
|
|
52
|
+
|
|
53
|
+
def test_has_many_with_no_serializer
|
|
54
|
+
post_serializer_class = Class.new(ActiveModel::Serializer) do
|
|
55
|
+
attributes :id
|
|
56
|
+
has_many :tags
|
|
57
|
+
end
|
|
58
|
+
post_serializer_class.new(@post).associations.each do |association|
|
|
59
|
+
key = association.key
|
|
60
|
+
serializer = association.lazy_association.serializer
|
|
61
|
+
|
|
62
|
+
assert_equal :tags, key
|
|
63
|
+
assert_nil serializer
|
|
64
|
+
assert_equal [{ id: 'tagid', name: '#hashtagged' }].to_json, association.virtual_value.to_json
|
|
65
|
+
end
|
|
66
|
+
end
|
|
67
|
+
|
|
68
|
+
def test_serializer_options_are_passed_into_associations_serializers
|
|
69
|
+
association = @post_serializer
|
|
70
|
+
.associations
|
|
71
|
+
.detect { |assoc| assoc.key == :comments }
|
|
72
|
+
|
|
73
|
+
comment_serializer = association.lazy_association.serializer.first
|
|
74
|
+
class << comment_serializer
|
|
75
|
+
def custom_options
|
|
76
|
+
instance_options
|
|
77
|
+
end
|
|
78
|
+
end
|
|
79
|
+
assert comment_serializer.custom_options.fetch(:custom_options)
|
|
80
|
+
end
|
|
81
|
+
|
|
82
|
+
def test_belongs_to
|
|
83
|
+
@comment_serializer.associations.each do |association|
|
|
84
|
+
key = association.key
|
|
85
|
+
serializer = association.lazy_association.serializer
|
|
86
|
+
|
|
87
|
+
case key
|
|
88
|
+
when :post
|
|
89
|
+
assert_kind_of(PostSerializer, serializer)
|
|
90
|
+
when :author
|
|
91
|
+
assert_nil serializer
|
|
92
|
+
else
|
|
93
|
+
flunk "Unknown association: #{key}"
|
|
94
|
+
end
|
|
95
|
+
|
|
96
|
+
assert_equal true, association.include_data?
|
|
97
|
+
end
|
|
98
|
+
end
|
|
99
|
+
|
|
100
|
+
def test_belongs_to_with_custom_method
|
|
101
|
+
assert(
|
|
102
|
+
@post_serializer.associations.any? do |association|
|
|
103
|
+
association.key == :blog
|
|
104
|
+
end
|
|
105
|
+
)
|
|
106
|
+
end
|
|
107
|
+
|
|
108
|
+
def test_associations_inheritance
|
|
109
|
+
inherited_klass = Class.new(PostSerializer)
|
|
110
|
+
|
|
111
|
+
assert_equal(PostSerializer._reflections, inherited_klass._reflections)
|
|
112
|
+
end
|
|
113
|
+
|
|
114
|
+
def test_associations_inheritance_with_new_association
|
|
115
|
+
inherited_klass = Class.new(PostSerializer) do
|
|
116
|
+
has_many :top_comments, serializer: CommentSerializer
|
|
117
|
+
end
|
|
118
|
+
|
|
119
|
+
assert(
|
|
120
|
+
PostSerializer._reflections.values.all? do |reflection|
|
|
121
|
+
inherited_klass._reflections.values.include?(reflection)
|
|
122
|
+
end
|
|
123
|
+
)
|
|
124
|
+
|
|
125
|
+
assert(
|
|
126
|
+
inherited_klass._reflections.values.any? do |reflection|
|
|
127
|
+
reflection.name == :top_comments
|
|
128
|
+
end
|
|
129
|
+
)
|
|
130
|
+
end
|
|
131
|
+
|
|
132
|
+
def test_associations_custom_keys
|
|
133
|
+
serializer = PostWithCustomKeysSerializer.new(@post)
|
|
134
|
+
|
|
135
|
+
expected_association_keys = serializer.associations.map(&:key)
|
|
136
|
+
|
|
137
|
+
assert expected_association_keys.include? :reviews
|
|
138
|
+
assert expected_association_keys.include? :writer
|
|
139
|
+
assert expected_association_keys.include? :site
|
|
140
|
+
end
|
|
141
|
+
|
|
142
|
+
class BelongsToBlogModel < ::Model
|
|
143
|
+
attributes :id, :title
|
|
144
|
+
associations :blog
|
|
145
|
+
end
|
|
146
|
+
class BelongsToBlogModelSerializer < ActiveModel::Serializer
|
|
147
|
+
type :posts
|
|
148
|
+
belongs_to :blog
|
|
149
|
+
end
|
|
150
|
+
|
|
151
|
+
def test_belongs_to_doesnt_load_record
|
|
152
|
+
attributes = { id: 1, title: 'Belongs to Blog', blog: Blog.new(id: 5) }
|
|
153
|
+
post = BelongsToBlogModel.new(attributes)
|
|
154
|
+
class << post
|
|
155
|
+
def blog
|
|
156
|
+
fail 'should use blog_id'
|
|
157
|
+
end
|
|
158
|
+
|
|
159
|
+
def blog_id
|
|
160
|
+
5
|
|
161
|
+
end
|
|
162
|
+
end
|
|
163
|
+
|
|
164
|
+
actual =
|
|
165
|
+
begin
|
|
166
|
+
original_option = BelongsToBlogModelSerializer.config.jsonapi_use_foreign_key_on_belongs_to_relationship
|
|
167
|
+
BelongsToBlogModelSerializer.config.jsonapi_use_foreign_key_on_belongs_to_relationship = true
|
|
168
|
+
serializable(post, adapter: :json_api, serializer: BelongsToBlogModelSerializer).as_json
|
|
169
|
+
ensure
|
|
170
|
+
BelongsToBlogModelSerializer.config.jsonapi_use_foreign_key_on_belongs_to_relationship = original_option
|
|
171
|
+
end
|
|
172
|
+
expected = { data: { id: '1', type: 'posts', relationships: { blog: { data: { id: '5', type: 'blogs' } } } } }
|
|
173
|
+
|
|
174
|
+
assert_equal expected, actual
|
|
175
|
+
end
|
|
176
|
+
|
|
177
|
+
class ExternalBlog < Blog
|
|
178
|
+
attributes :external_id
|
|
179
|
+
end
|
|
180
|
+
class BelongsToExternalBlogModel < ::Model
|
|
181
|
+
attributes :id, :title, :external_blog_id
|
|
182
|
+
associations :external_blog
|
|
183
|
+
end
|
|
184
|
+
class BelongsToExternalBlogModelSerializer < ActiveModel::Serializer
|
|
185
|
+
type :posts
|
|
186
|
+
belongs_to :external_blog
|
|
187
|
+
|
|
188
|
+
def external_blog_id
|
|
189
|
+
object.external_blog.external_id
|
|
190
|
+
end
|
|
191
|
+
end
|
|
192
|
+
|
|
193
|
+
def test_belongs_to_allows_id_overwriting
|
|
194
|
+
attributes = {
|
|
195
|
+
id: 1,
|
|
196
|
+
title: 'Title',
|
|
197
|
+
external_blog: ExternalBlog.new(id: 5, external_id: 6)
|
|
198
|
+
}
|
|
199
|
+
post = BelongsToExternalBlogModel.new(attributes)
|
|
200
|
+
|
|
201
|
+
actual =
|
|
202
|
+
begin
|
|
203
|
+
original_option = BelongsToExternalBlogModelSerializer.config.jsonapi_use_foreign_key_on_belongs_to_relationship
|
|
204
|
+
BelongsToExternalBlogModelSerializer.config.jsonapi_use_foreign_key_on_belongs_to_relationship = true
|
|
205
|
+
serializable(post, adapter: :json_api, serializer: BelongsToExternalBlogModelSerializer).as_json
|
|
206
|
+
ensure
|
|
207
|
+
BelongsToExternalBlogModelSerializer.config.jsonapi_use_foreign_key_on_belongs_to_relationship = original_option
|
|
208
|
+
end
|
|
209
|
+
expected = { data: { id: '1', type: 'posts', relationships: { :'external-blog' => { data: { id: '6', type: 'external-blogs' } } } } }
|
|
210
|
+
|
|
211
|
+
assert_equal expected, actual
|
|
212
|
+
end
|
|
213
|
+
|
|
214
|
+
class InlineAssociationTestPostSerializer < ActiveModel::Serializer
|
|
215
|
+
has_many :comments
|
|
216
|
+
has_many :comments, key: :last_comments do
|
|
217
|
+
object.comments.last(1)
|
|
218
|
+
end
|
|
219
|
+
end
|
|
220
|
+
|
|
221
|
+
def test_virtual_attribute_block
|
|
222
|
+
comment1 = ::ARModels::Comment.create!(contents: 'first comment')
|
|
223
|
+
comment2 = ::ARModels::Comment.create!(contents: 'last comment')
|
|
224
|
+
post = ::ARModels::Post.create!(
|
|
225
|
+
title: 'inline association test',
|
|
226
|
+
body: 'etc',
|
|
227
|
+
comments: [comment1, comment2]
|
|
228
|
+
)
|
|
229
|
+
actual = serializable(post, adapter: :attributes, serializer: InlineAssociationTestPostSerializer).as_json
|
|
230
|
+
expected = {
|
|
231
|
+
comments: [
|
|
232
|
+
{ id: 1, contents: 'first comment' },
|
|
233
|
+
{ id: 2, contents: 'last comment' }
|
|
234
|
+
],
|
|
235
|
+
last_comments: [
|
|
236
|
+
{ id: 2, contents: 'last comment' }
|
|
237
|
+
]
|
|
238
|
+
}
|
|
239
|
+
|
|
240
|
+
assert_equal expected, actual
|
|
241
|
+
ensure
|
|
242
|
+
::ARModels::Post.delete_all
|
|
243
|
+
::ARModels::Comment.delete_all
|
|
244
|
+
end
|
|
245
|
+
|
|
246
|
+
class NamespacedResourcesTest < ActiveSupport::TestCase
|
|
247
|
+
class ResourceNamespace
|
|
248
|
+
class Post < ::Model
|
|
249
|
+
associations :comments, :author, :description
|
|
250
|
+
end
|
|
251
|
+
class Comment < ::Model; end
|
|
252
|
+
class Author < ::Model; end
|
|
253
|
+
class Description < ::Model; end
|
|
254
|
+
class PostSerializer < ActiveModel::Serializer
|
|
255
|
+
has_many :comments
|
|
256
|
+
belongs_to :author
|
|
257
|
+
has_one :description
|
|
258
|
+
end
|
|
259
|
+
class CommentSerializer < ActiveModel::Serializer; end
|
|
260
|
+
class AuthorSerializer < ActiveModel::Serializer; end
|
|
261
|
+
class DescriptionSerializer < ActiveModel::Serializer; end
|
|
262
|
+
end
|
|
263
|
+
|
|
264
|
+
def setup
|
|
265
|
+
@comment = ResourceNamespace::Comment.new
|
|
266
|
+
@author = ResourceNamespace::Author.new
|
|
267
|
+
@description = ResourceNamespace::Description.new
|
|
268
|
+
@post = ResourceNamespace::Post.new(comments: [@comment],
|
|
269
|
+
author: @author,
|
|
270
|
+
description: @description)
|
|
271
|
+
@post_serializer = ResourceNamespace::PostSerializer.new(@post)
|
|
272
|
+
end
|
|
273
|
+
|
|
274
|
+
def test_associations_namespaced_resources
|
|
275
|
+
@post_serializer.associations.each do |association|
|
|
276
|
+
case association.key
|
|
277
|
+
when :comments
|
|
278
|
+
assert_instance_of(ResourceNamespace::CommentSerializer, association.lazy_association.serializer.first)
|
|
279
|
+
when :author
|
|
280
|
+
assert_instance_of(ResourceNamespace::AuthorSerializer, association.lazy_association.serializer)
|
|
281
|
+
when :description
|
|
282
|
+
assert_instance_of(ResourceNamespace::DescriptionSerializer, association.lazy_association.serializer)
|
|
283
|
+
else
|
|
284
|
+
flunk "Unknown association: #{key}"
|
|
285
|
+
end
|
|
286
|
+
end
|
|
287
|
+
end
|
|
288
|
+
end
|
|
289
|
+
|
|
290
|
+
class AssociationsNamespacedSerializersTest < ActiveSupport::TestCase
|
|
291
|
+
class Post < ::Model
|
|
292
|
+
associations :comments, :author, :description
|
|
293
|
+
|
|
294
|
+
def latest_comments
|
|
295
|
+
comments[0..3]
|
|
296
|
+
end
|
|
297
|
+
end
|
|
298
|
+
class Comment < ::Model; end
|
|
299
|
+
class Author < ::Model; end
|
|
300
|
+
class Description < ::Model; end
|
|
301
|
+
|
|
302
|
+
class ResourceNamespace
|
|
303
|
+
class PostSerializer < ActiveModel::Serializer
|
|
304
|
+
has_many :comments, namespace: ResourceNamespace
|
|
305
|
+
has_many :latest_comments, namespace: ResourceNamespace
|
|
306
|
+
belongs_to :author, namespace: ResourceNamespace
|
|
307
|
+
has_one :description, namespace: ResourceNamespace
|
|
308
|
+
end
|
|
309
|
+
class CommentSerializer < ActiveModel::Serializer; end
|
|
310
|
+
class AuthorSerializer < ActiveModel::Serializer; end
|
|
311
|
+
class DescriptionSerializer < ActiveModel::Serializer; end
|
|
312
|
+
end
|
|
313
|
+
|
|
314
|
+
def setup
|
|
315
|
+
@comment = Comment.new
|
|
316
|
+
@author = Author.new
|
|
317
|
+
@description = Description.new
|
|
318
|
+
@post = Post.new(comments: [@comment],
|
|
319
|
+
author: @author,
|
|
320
|
+
description: @description)
|
|
321
|
+
@post_serializer = ResourceNamespace::PostSerializer.new(@post)
|
|
322
|
+
end
|
|
323
|
+
|
|
324
|
+
def test_associations_namespaced_serializers
|
|
325
|
+
@post_serializer.associations.each do |association|
|
|
326
|
+
case association.key
|
|
327
|
+
when :comments, :latest_comments
|
|
328
|
+
assert_instance_of(ResourceNamespace::CommentSerializer, association.lazy_association.serializer.first)
|
|
329
|
+
when :author
|
|
330
|
+
assert_instance_of(ResourceNamespace::AuthorSerializer, association.lazy_association.serializer)
|
|
331
|
+
when :description
|
|
332
|
+
assert_instance_of(ResourceNamespace::DescriptionSerializer, association.lazy_association.serializer)
|
|
333
|
+
else
|
|
334
|
+
flunk "Unknown association: #{key}"
|
|
335
|
+
end
|
|
336
|
+
end
|
|
337
|
+
end
|
|
338
|
+
end
|
|
339
|
+
|
|
340
|
+
class NestedSerializersTest < ActiveSupport::TestCase
|
|
341
|
+
class Post < ::Model
|
|
342
|
+
associations :comments, :author, :description
|
|
343
|
+
end
|
|
344
|
+
class Comment < ::Model; end
|
|
345
|
+
class Author < ::Model; end
|
|
346
|
+
class Description < ::Model; end
|
|
347
|
+
class PostSerializer < ActiveModel::Serializer
|
|
348
|
+
has_many :comments
|
|
349
|
+
class CommentSerializer < ActiveModel::Serializer; end
|
|
350
|
+
belongs_to :author
|
|
351
|
+
class AuthorSerializer < ActiveModel::Serializer; end
|
|
352
|
+
has_one :description
|
|
353
|
+
class DescriptionSerializer < ActiveModel::Serializer; end
|
|
354
|
+
end
|
|
355
|
+
|
|
356
|
+
def setup
|
|
357
|
+
@comment = Comment.new
|
|
358
|
+
@author = Author.new
|
|
359
|
+
@description = Description.new
|
|
360
|
+
@post = Post.new(comments: [@comment],
|
|
361
|
+
author: @author,
|
|
362
|
+
description: @description)
|
|
363
|
+
@post_serializer = PostSerializer.new(@post)
|
|
364
|
+
end
|
|
365
|
+
|
|
366
|
+
def test_associations_namespaced_resources
|
|
367
|
+
@post_serializer.associations.each do |association|
|
|
368
|
+
case association.key
|
|
369
|
+
when :comments
|
|
370
|
+
assert_instance_of(PostSerializer::CommentSerializer, association.lazy_association.serializer.first)
|
|
371
|
+
when :author
|
|
372
|
+
assert_instance_of(PostSerializer::AuthorSerializer, association.lazy_association.serializer)
|
|
373
|
+
when :description
|
|
374
|
+
assert_instance_of(PostSerializer::DescriptionSerializer, association.lazy_association.serializer)
|
|
375
|
+
else
|
|
376
|
+
flunk "Unknown association: #{key}"
|
|
377
|
+
end
|
|
378
|
+
end
|
|
379
|
+
end
|
|
380
|
+
|
|
381
|
+
# rubocop:disable Metrics/AbcSize
|
|
382
|
+
def test_conditional_associations
|
|
383
|
+
model = Class.new(::Model) do
|
|
384
|
+
attributes :true, :false
|
|
385
|
+
associations :something
|
|
386
|
+
end.new(true: true, false: false)
|
|
387
|
+
|
|
388
|
+
scenarios = [
|
|
389
|
+
{ options: { if: :true }, included: true },
|
|
390
|
+
{ options: { if: :false }, included: false },
|
|
391
|
+
{ options: { unless: :false }, included: true },
|
|
392
|
+
{ options: { unless: :true }, included: false },
|
|
393
|
+
{ options: { if: 'object.true' }, included: true },
|
|
394
|
+
{ options: { if: 'object.false' }, included: false },
|
|
395
|
+
{ options: { unless: 'object.false' }, included: true },
|
|
396
|
+
{ options: { unless: 'object.true' }, included: false },
|
|
397
|
+
{ options: { if: -> { object.true } }, included: true },
|
|
398
|
+
{ options: { if: -> { object.false } }, included: false },
|
|
399
|
+
{ options: { unless: -> { object.false } }, included: true },
|
|
400
|
+
{ options: { unless: -> { object.true } }, included: false },
|
|
401
|
+
{ options: { if: -> (s) { s.object.true } }, included: true },
|
|
402
|
+
{ options: { if: -> (s) { s.object.false } }, included: false },
|
|
403
|
+
{ options: { unless: -> (s) { s.object.false } }, included: true },
|
|
404
|
+
{ options: { unless: -> (s) { s.object.true } }, included: false }
|
|
405
|
+
]
|
|
406
|
+
|
|
407
|
+
scenarios.each do |s|
|
|
408
|
+
serializer = Class.new(ActiveModel::Serializer) do
|
|
409
|
+
belongs_to :something, s[:options]
|
|
410
|
+
|
|
411
|
+
def true
|
|
412
|
+
true
|
|
413
|
+
end
|
|
414
|
+
|
|
415
|
+
def false
|
|
416
|
+
false
|
|
417
|
+
end
|
|
418
|
+
end
|
|
419
|
+
|
|
420
|
+
hash = serializable(model, serializer: serializer).serializable_hash
|
|
421
|
+
assert_equal(s[:included], hash.key?(:something), "Error with #{s[:options]}")
|
|
422
|
+
end
|
|
423
|
+
end
|
|
424
|
+
|
|
425
|
+
def test_illegal_conditional_associations
|
|
426
|
+
exception = assert_raises(TypeError) do
|
|
427
|
+
Class.new(ActiveModel::Serializer) do
|
|
428
|
+
belongs_to :x, if: nil
|
|
429
|
+
end
|
|
430
|
+
end
|
|
431
|
+
|
|
432
|
+
assert_match(/:if should be a Symbol, String or Proc/, exception.message)
|
|
433
|
+
end
|
|
434
|
+
end
|
|
435
|
+
|
|
436
|
+
class InheritedSerializerTest < ActiveSupport::TestCase
|
|
437
|
+
class PostSerializer < ActiveModel::Serializer
|
|
438
|
+
belongs_to :author
|
|
439
|
+
has_many :comments
|
|
440
|
+
belongs_to :blog
|
|
441
|
+
end
|
|
442
|
+
|
|
443
|
+
class InheritedPostSerializer < PostSerializer
|
|
444
|
+
belongs_to :author, polymorphic: true
|
|
445
|
+
has_many :comments, key: :reviews
|
|
446
|
+
end
|
|
447
|
+
|
|
448
|
+
class AuthorSerializer < ActiveModel::Serializer
|
|
449
|
+
has_many :posts
|
|
450
|
+
has_many :roles
|
|
451
|
+
has_one :bio
|
|
452
|
+
end
|
|
453
|
+
|
|
454
|
+
class InheritedAuthorSerializer < AuthorSerializer
|
|
455
|
+
has_many :roles, polymorphic: true
|
|
456
|
+
has_one :bio, polymorphic: true
|
|
457
|
+
end
|
|
458
|
+
|
|
459
|
+
def setup
|
|
460
|
+
@author = Author.new(name: 'Steve K.')
|
|
461
|
+
@post = Post.new(title: 'New Post', body: 'Body')
|
|
462
|
+
@post_serializer = PostSerializer.new(@post)
|
|
463
|
+
@author_serializer = AuthorSerializer.new(@author)
|
|
464
|
+
@inherited_post_serializer = InheritedPostSerializer.new(@post)
|
|
465
|
+
@inherited_author_serializer = InheritedAuthorSerializer.new(@author)
|
|
466
|
+
@author_associations = @author_serializer.associations.to_a.sort_by(&:name)
|
|
467
|
+
@inherited_author_associations = @inherited_author_serializer.associations.to_a.sort_by(&:name)
|
|
468
|
+
@post_associations = @post_serializer.associations.to_a
|
|
469
|
+
@inherited_post_associations = @inherited_post_serializer.associations.to_a
|
|
470
|
+
end
|
|
471
|
+
|
|
472
|
+
test 'an author serializer must have [posts,roles,bio] associations' do
|
|
473
|
+
expected = [:posts, :roles, :bio].sort
|
|
474
|
+
result = @author_serializer.associations.map(&:name).sort
|
|
475
|
+
assert_equal(result, expected)
|
|
476
|
+
end
|
|
477
|
+
|
|
478
|
+
test 'a post serializer must have [author,comments,blog] associations' do
|
|
479
|
+
expected = [:author, :comments, :blog].sort
|
|
480
|
+
result = @post_serializer.associations.map(&:name).sort
|
|
481
|
+
assert_equal(result, expected)
|
|
482
|
+
end
|
|
483
|
+
|
|
484
|
+
test 'a serializer inheriting from another serializer can redefine has_many and has_one associations' do
|
|
485
|
+
expected = [:roles, :bio].sort
|
|
486
|
+
result = (@inherited_author_associations.map(&:reflection) - @author_associations.map(&:reflection)).map(&:name)
|
|
487
|
+
assert_equal(result, expected)
|
|
488
|
+
assert_equal [true, false, true], @inherited_author_associations.map(&:polymorphic?)
|
|
489
|
+
assert_equal [false, false, false], @author_associations.map(&:polymorphic?)
|
|
490
|
+
end
|
|
491
|
+
|
|
492
|
+
test 'a serializer inheriting from another serializer can redefine belongs_to associations' do
|
|
493
|
+
assert_equal [:author, :comments, :blog], @post_associations.map(&:name)
|
|
494
|
+
assert_equal [:author, :comments, :blog, :comments], @inherited_post_associations.map(&:name)
|
|
495
|
+
|
|
496
|
+
refute @post_associations.detect { |assoc| assoc.name == :author }.polymorphic?
|
|
497
|
+
assert @inherited_post_associations.detect { |assoc| assoc.name == :author }.polymorphic?
|
|
498
|
+
|
|
499
|
+
refute @post_associations.detect { |assoc| assoc.name == :comments }.key?
|
|
500
|
+
original_comment_assoc, new_comments_assoc = @inherited_post_associations.select { |assoc| assoc.name == :comments }
|
|
501
|
+
refute original_comment_assoc.key?
|
|
502
|
+
assert_equal :reviews, new_comments_assoc.key
|
|
503
|
+
|
|
504
|
+
original_blog = @post_associations.detect { |assoc| assoc.name == :blog }
|
|
505
|
+
inherited_blog = @inherited_post_associations.detect { |assoc| assoc.name == :blog }
|
|
506
|
+
original_parent_serializer = original_blog.lazy_association.association_options.delete(:parent_serializer)
|
|
507
|
+
inherited_parent_serializer = inherited_blog.lazy_association.association_options.delete(:parent_serializer)
|
|
508
|
+
assert_equal PostSerializer, original_parent_serializer.class
|
|
509
|
+
assert_equal InheritedPostSerializer, inherited_parent_serializer.class
|
|
510
|
+
end
|
|
511
|
+
|
|
512
|
+
test 'a serializer inheriting from another serializer can have an additional association with the same name but with different key' do
|
|
513
|
+
expected = [:author, :comments, :blog, :reviews].sort
|
|
514
|
+
result = @inherited_post_serializer.associations.map(&:key).sort
|
|
515
|
+
assert_equal(result, expected)
|
|
516
|
+
end
|
|
517
|
+
end
|
|
518
|
+
end
|
|
519
|
+
end
|
|
520
|
+
end
|