alba 2.0.1 → 2.2.0

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.
data/benchmark/prep.rb ADDED
@@ -0,0 +1,82 @@
1
+ # --- Bundle dependencies ---
2
+
3
+ require "bundler/inline"
4
+
5
+ gemfile(true) do
6
+ source "https://rubygems.org"
7
+ git_source(:github) { |repo| "https://github.com/#{repo}.git" }
8
+
9
+ gem "active_model_serializers"
10
+ gem "activerecord", "6.1.3"
11
+ gem "alba", path: '../'
12
+ gem "benchmark-ips"
13
+ gem "benchmark-memory"
14
+ gem "blueprinter"
15
+ gem "fast_serializer_ruby"
16
+ gem "jbuilder"
17
+ gem 'turbostreamer'
18
+ gem "jserializer"
19
+ gem "multi_json"
20
+ gem "panko_serializer"
21
+ gem "pg"
22
+ gem "primalize"
23
+ gem "oj"
24
+ gem "representable"
25
+ gem "simple_ams"
26
+ gem "sqlite3"
27
+ end
28
+
29
+ # --- Test data model setup ---
30
+
31
+ require "pg"
32
+ require "active_record"
33
+ require "active_record/connection_adapters/postgresql_adapter"
34
+ require "logger"
35
+ require "oj"
36
+ require "sqlite3"
37
+ Oj.optimize_rails unless ENV['NO_OJ_OPTIMIZE_RAILS']
38
+
39
+ ActiveRecord::Base.establish_connection(adapter: "sqlite3", database: ":memory:")
40
+ # ActiveRecord::Base.logger = Logger.new($stdout)
41
+
42
+ ActiveRecord::Schema.define do
43
+ create_table :posts, force: true do |t|
44
+ t.string :body
45
+ end
46
+
47
+ create_table :comments, force: true do |t|
48
+ t.integer :post_id
49
+ t.string :body
50
+ t.integer :commenter_id
51
+ end
52
+
53
+ create_table :users, force: true do |t|
54
+ t.string :name
55
+ end
56
+ end
57
+
58
+ class Post < ActiveRecord::Base
59
+ has_many :comments
60
+ has_many :commenters, through: :comments, class_name: 'User', source: :commenter
61
+
62
+ def attributes
63
+ {id: nil, body: nil, commenter_names: commenter_names}
64
+ end
65
+
66
+ def commenter_names
67
+ commenters.pluck(:name)
68
+ end
69
+ end
70
+
71
+ class Comment < ActiveRecord::Base
72
+ belongs_to :post
73
+ belongs_to :commenter, class_name: 'User'
74
+
75
+ def attributes
76
+ {id: nil, body: nil}
77
+ end
78
+ end
79
+
80
+ class User < ActiveRecord::Base
81
+ has_many :comments
82
+ end
@@ -1,88 +1,7 @@
1
1
  # Benchmark script to run varieties of JSON serializers
2
2
  # Fetch Alba from local, otherwise fetch latest from RubyGems
3
3
 
4
- # --- Bundle dependencies ---
5
-
6
- require "bundler/inline"
7
-
8
- gemfile(true) do
9
- source "https://rubygems.org"
10
- git_source(:github) { |repo| "https://github.com/#{repo}.git" }
11
-
12
- gem "active_model_serializers"
13
- gem "activerecord", "6.1.3"
14
- gem "alba", path: '../'
15
- gem "benchmark-ips"
16
- gem "benchmark-memory"
17
- gem "blueprinter"
18
- gem "jbuilder"
19
- gem 'turbostreamer'
20
- gem "jserializer"
21
- gem "jsonapi-serializer" # successor of fast_jsonapi
22
- gem "multi_json"
23
- gem "panko_serializer"
24
- gem "pg"
25
- gem "primalize"
26
- gem "oj"
27
- gem "representable"
28
- gem "simple_ams"
29
- gem "sqlite3"
30
- end
31
-
32
- # --- Test data model setup ---
33
-
34
- require "pg"
35
- require "active_record"
36
- require "active_record/connection_adapters/postgresql_adapter"
37
- require "logger"
38
- require "oj"
39
- require "sqlite3"
40
- Oj.optimize_rails
41
-
42
- ActiveRecord::Base.establish_connection(adapter: "sqlite3", database: ":memory:")
43
- # ActiveRecord::Base.logger = Logger.new($stdout)
44
-
45
- ActiveRecord::Schema.define do
46
- create_table :posts, force: true do |t|
47
- t.string :body
48
- end
49
-
50
- create_table :comments, force: true do |t|
51
- t.integer :post_id
52
- t.string :body
53
- t.integer :commenter_id
54
- end
55
-
56
- create_table :users, force: true do |t|
57
- t.string :name
58
- end
59
- end
60
-
61
- class Post < ActiveRecord::Base
62
- has_many :comments
63
- has_many :commenters, through: :comments, class_name: 'User', source: :commenter
64
-
65
- def attributes
66
- {id: nil, body: nil, commenter_names: commenter_names}
67
- end
68
-
69
- def commenter_names
70
- commenters.pluck(:name)
71
- end
72
- end
73
-
74
- class Comment < ActiveRecord::Base
75
- belongs_to :post
76
- belongs_to :commenter, class_name: 'User'
77
-
78
- def attributes
79
- {id: nil, body: nil}
80
- end
81
- end
82
-
83
- class User < ActiveRecord::Base
84
- has_many :comments
85
- end
4
+ require_relative 'prep'
86
5
 
87
6
  # --- Alba serializers ---
88
7
 
@@ -177,70 +96,8 @@ class JserializerPostSerializer < Jserializer::Base
177
96
  end
178
97
  end
179
98
 
180
-
181
- # --- JSONAPI:Serializer serializers / (successor of fast_jsonapi) ---
182
-
183
- class JsonApiStandardCommentSerializer
184
- include JSONAPI::Serializer
185
-
186
- attribute :id
187
- attribute :body
188
- end
189
-
190
- class JsonApiStandardPostSerializer
191
- include JSONAPI::Serializer
192
-
193
- # set_type :post # optional
194
- attribute :id
195
- attribute :body
196
- attribute :commenter_names
197
-
198
- attribute :comments do |post|
199
- post.comments.map { |comment| JsonApiSameFormatCommentSerializer.new(comment) }
200
- end
201
- end
202
-
203
- # --- JSONAPI:Serializer serializers that format the code the same flat way as the other gems here ---
204
-
205
- # code to convert from JSON:API output to "flat" JSON, like the other serializers build
206
- class JsonApiSameFormatSerializer
207
- include JSONAPI::Serializer
208
-
209
- def as_json(*_options)
210
- hash = serializable_hash
211
-
212
- if hash[:data].is_a? Hash
213
- hash[:data][:attributes]
214
-
215
- elsif hash[:data].is_a? Array
216
- hash[:data].pluck(:attributes)
217
-
218
- elsif hash[:data].nil?
219
- { }
220
-
221
- else
222
- raise "unexpected data type #{hash[:data].class}"
223
- end
224
- end
225
- end
226
-
227
- class JsonApiSameFormatCommentSerializer < JsonApiSameFormatSerializer
228
- attribute :id
229
- attribute :body
230
- end
231
-
232
- class JsonApiSameFormatPostSerializer < JsonApiSameFormatSerializer
233
- attribute :id
234
- attribute :body
235
- attribute :commenter_names
236
-
237
- attribute :comments do |post|
238
- post.comments.map { |comment| JsonApiSameFormatCommentSerializer.new(comment) }
239
- end
240
- end
241
-
242
99
  # --- Panko serializers ---
243
- #
100
+
244
101
  require "panko_serializer"
245
102
 
246
103
  class PankoCommentSerializer < Panko::Serializer
@@ -259,7 +116,7 @@ class PankoPostSerializer < Panko::Serializer
259
116
  end
260
117
 
261
118
  # --- Primalize serializers ---
262
- #
119
+
263
120
  class PrimalizeCommentResource < Primalize::Single
264
121
  attributes id: integer, body: string
265
122
  end
@@ -376,8 +233,6 @@ ams = Proc.new { AMSPostSerializer.new(post, {}).to_json }
376
233
  blueprinter = Proc.new { PostBlueprint.render(post) }
377
234
  jbuilder = Proc.new { post.to_builder.target! }
378
235
  jserializer = Proc.new { JserializerPostSerializer.new(post).to_json }
379
- jsonapi = proc { JsonApiStandardPostSerializer.new(post).to_json }
380
- jsonapi_same_format = proc { JsonApiSameFormatPostSerializer.new(post).to_json }
381
236
  panko = proc { PankoPostSerializer.new.serialize_to_json(post) }
382
237
  primalize = proc { PrimalizePostResource.new(post).to_json }
383
238
  rails = Proc.new { ActiveSupport::JSON.encode(post.serializable_hash(include: :comments)) }
@@ -395,8 +250,6 @@ puts "Serializer outputs ----------------------------------"
395
250
  blueprinter: blueprinter,
396
251
  jbuilder: jbuilder, # different order
397
252
  jserializer: jserializer,
398
- jsonapi: jsonapi, # nested JSON:API format
399
- jsonapi_same_format: jsonapi_same_format,
400
253
  panko: panko,
401
254
  primalize: primalize,
402
255
  rails: rails,
@@ -417,8 +270,6 @@ Benchmark.ips do |x|
417
270
  x.report(:blueprinter, &blueprinter)
418
271
  x.report(:jbuilder, &jbuilder)
419
272
  x.report(:jserializer, &jserializer)
420
- x.report(:jsonapi, &jsonapi)
421
- x.report(:jsonapi_same_format, &jsonapi_same_format)
422
273
  x.report(:panko, &panko)
423
274
  x.report(:primalize, &primalize)
424
275
  x.report(:rails, &rails)
@@ -438,8 +289,6 @@ Benchmark.memory do |x|
438
289
  x.report(:blueprinter, &blueprinter)
439
290
  x.report(:jbuilder, &jbuilder)
440
291
  x.report(:jserializer, &jserializer)
441
- x.report(:jsonapi, &jsonapi)
442
- x.report(:jsonapi_same_format, &jsonapi_same_format)
443
292
  x.report(:panko, &panko)
444
293
  x.report(:primalize, &primalize)
445
294
  x.report(:rails, &rails)
@@ -12,7 +12,7 @@ This guide is aimed at helping ActiveModelSerializers users transition to Alba,
12
12
 
13
13
  ## Example class
14
14
 
15
- Example clsss is inherited `ActiveRecord::Base`, because [serializing PORO with AMS is pretty hard](https://github.com/rails-api/active_model_serializers/blob/0-10-stable/docs/howto/serialize_poro.md).
15
+ Example class is inherited `ActiveRecord::Base`, because [serializing PORO with AMS is pretty hard](https://github.com/rails-api/active_model_serializers/blob/0-10-stable/docs/howto/serialize_poro.md).
16
16
 
17
17
  ```rb
18
18
  class User < ActiveRecord::Base
@@ -175,7 +175,7 @@ class UserSerializer < ActiveModel::Serializer
175
175
  has_many :articles, serializer: ArticleSerializer # For has_many relation
176
176
  end
177
177
  user = User.create!
178
- user.craete_profile! email: email
178
+ user.create_profile! email: email
179
179
  user.articles.create! title: title, body: body
180
180
  ActiveModelSerializers::SerializableResource.new(
181
181
  user
data/docs/rails.md CHANGED
@@ -14,7 +14,7 @@ You might want to add some configurations to initializer file such as `alba.rb`
14
14
  ```ruby
15
15
  # alba.rb
16
16
  Alba.backend = :active_support
17
- Alba.enable_inference!(:active_support)
17
+ Alba.enable_inference!(with: :active_support)
18
18
  ```
19
19
 
20
20
  You can also use `:oj_rails` for backend if you prefer using Oj.
@@ -37,8 +37,10 @@ module Alba
37
37
  @object = @condition.call(object, params, target) if @condition
38
38
  return if @object.nil?
39
39
 
40
- if @resource.is_a?(Proc) && @object.is_a?(Enumerable)
41
- to_h_with_each_resource(within, params)
40
+ if @resource.is_a?(Proc)
41
+ return to_h_with_each_resource(within, params) if @object.is_a?(Enumerable)
42
+
43
+ @resource.call(@object).new(@object, within: within, params: params).to_h
42
44
  else
43
45
  to_h_with_constantize_resource(within, params)
44
46
  end
@@ -63,10 +65,10 @@ module Alba
63
65
  klass.transform_keys(key_transformation)
64
66
  klass.class_eval(&block)
65
67
  klass
66
- elsif Alba.inferring
68
+ elsif Alba.inflector
67
69
  Alba.infer_resource_class(@name, nesting: nesting)
68
70
  else
69
- raise ArgumentError, 'When Alba.inferring is false, either resource or block is required'
71
+ raise ArgumentError, 'When Alba.inflector is nil, either resource or block is required'
70
72
  end
71
73
  end
72
74
 
@@ -20,7 +20,7 @@ module Alba
20
20
  return Alba::REMOVE_KEY unless condition_passes?(resource, object)
21
21
 
22
22
  fetched_attribute = yield(@body)
23
- return fetched_attribute if fetched_attribute.nil? || !with_two_arity_proc_condition
23
+ return fetched_attribute if !with_two_arity_proc_condition
24
24
 
25
25
  return Alba::REMOVE_KEY unless resource.instance_exec(object, attribute_from_association_body_or(fetched_attribute), &@condition)
26
26
 
data/lib/alba/layout.rb CHANGED
@@ -8,8 +8,8 @@ module Alba
8
8
 
9
9
  def_delegators :@resource, :object, :params, :serializable_hash, :to_h
10
10
 
11
- # @params file [String] name of the layout file
12
- # @params inline [Proc] a proc returning JSON string or a Hash representing JSON
11
+ # @param file [String] name of the layout file
12
+ # @param inline [Proc] a proc returning JSON string or a Hash representing JSON
13
13
  def initialize(file:, inline:)
14
14
  if file
15
15
  raise ArgumentError, 'File layout must be a String representing filename' unless file.is_a?(String)
@@ -0,0 +1,8 @@
1
+ module Alba
2
+ # Rails integration
3
+ class Railtie < Rails::Railtie
4
+ initializer 'alba.initialize' do
5
+ Alba.inflector = :active_support
6
+ end
7
+ end
8
+ end
data/lib/alba/resource.rb CHANGED
@@ -11,7 +11,7 @@ module Alba
11
11
  module Resource
12
12
  # @!parse include InstanceMethods
13
13
  # @!parse extend ClassMethods
14
- DSLS = {_attributes: {}, _key: nil, _key_for_collection: nil, _meta: nil, _transform_type: :none, _transforming_root_key: false, _on_error: nil, _on_nil: nil, _layout: nil, _collection_key: nil}.freeze # rubocop:disable Layout/LineLength
14
+ DSLS = {_attributes: {}, _key: nil, _key_for_collection: nil, _meta: nil, _transform_type: :none, _transforming_root_key: false, _key_transformation_cascade: true, _on_error: nil, _on_nil: nil, _layout: nil, _collection_key: nil}.freeze # rubocop:disable Layout/LineLength
15
15
  private_constant :DSLS
16
16
 
17
17
  WITHIN_DEFAULT = Object.new.freeze
@@ -41,7 +41,6 @@ module Alba
41
41
  @object = object
42
42
  @params = params
43
43
  @within = within
44
- @method_existence = {} # Cache for `respond_to?` result
45
44
  DSLS.each_key { |name| instance_variable_set("@#{name}", self.class.__send__(name)) }
46
45
  end
47
46
 
@@ -79,7 +78,6 @@ module Alba
79
78
  #
80
79
  # @param root_key [Symbol, nil, true]
81
80
  # @param meta [Hash] metadata for this seialization
82
- # @param symbolize_root_key [Boolean] determines if root key should be symbolized
83
81
  # @return [Hash]
84
82
  def as_json(root_key: nil, meta: {})
85
83
  key = root_key.nil? ? fetch_key : root_key.to_s
@@ -149,7 +147,7 @@ module Alba
149
147
  end
150
148
 
151
149
  def _key_for_collection
152
- if Alba.inferring
150
+ if Alba.inflector
153
151
  @_key_for_collection == true ? resource_name(pluralized: true) : @_key_for_collection.to_s
154
152
  else
155
153
  @_key_for_collection == true ? raise_root_key_inference_error : @_key_for_collection.to_s
@@ -158,7 +156,7 @@ module Alba
158
156
 
159
157
  # @return [String]
160
158
  def _key
161
- if Alba.inferring
159
+ if Alba.inflector
162
160
  @_key == true ? resource_name(pluralized: false) : @_key.to_s
163
161
  else
164
162
  @_key == true ? raise_root_key_inference_error : @_key.to_s
@@ -174,7 +172,7 @@ module Alba
174
172
  end
175
173
 
176
174
  def raise_root_key_inference_error
177
- raise Alba::Error, 'You must call Alba.enable_inference! to set root_key to true for inferring root key.'
175
+ raise Alba::Error, 'You must set inflector when setting root key as true.'
178
176
  end
179
177
 
180
178
  def transforming_root_key?
@@ -182,27 +180,27 @@ module Alba
182
180
  end
183
181
 
184
182
  def converter
185
- lambda do |object|
186
- attributes_to_hash(object, {})
183
+ lambda do |obj|
184
+ attributes_to_hash(obj, {})
187
185
  end
188
186
  end
189
187
 
190
188
  def collection_converter
191
- lambda do |object, a|
189
+ lambda do |obj, a|
192
190
  a << {}
193
191
  h = a.last
194
- attributes_to_hash(object, h)
192
+ attributes_to_hash(obj, h)
195
193
  a
196
194
  end
197
195
  end
198
196
 
199
- def attributes_to_hash(object, hash)
197
+ def attributes_to_hash(obj, hash)
200
198
  attributes.each do |key, attribute|
201
- set_key_and_attribute_body_from(object, key, attribute, hash)
199
+ set_key_and_attribute_body_from(obj, key, attribute, hash)
202
200
  rescue ::Alba::Error, FrozenError, TypeError
203
201
  raise
204
202
  rescue StandardError => e
205
- handle_error(e, object, key, attribute, hash)
203
+ handle_error(e, obj, key, attribute, hash)
206
204
  end
207
205
  hash
208
206
  end
@@ -213,20 +211,28 @@ module Alba
213
211
  @_attributes
214
212
  end
215
213
 
216
- def set_key_and_attribute_body_from(object, key, attribute, hash)
214
+ # Default implementation for selecting attributes
215
+ # Override this method to filter attributes based on key and value
216
+ def select(_key, _value)
217
+ true
218
+ end
219
+
220
+ def set_key_and_attribute_body_from(obj, key, attribute, hash)
217
221
  key = transform_key(key)
218
- value = fetch_attribute(object, key, attribute)
222
+ value = fetch_attribute(obj, key, attribute)
223
+ return unless select(key, value)
224
+
219
225
  hash[key] = value unless value == Alba::REMOVE_KEY
220
226
  end
221
227
 
222
- def handle_error(error, object, key, attribute, hash)
228
+ def handle_error(error, obj, key, attribute, hash)
223
229
  on_error = @_on_error || :raise
224
230
  case on_error # rubocop:disable Style/MissingElse
225
231
  when :raise, nil then raise(error)
226
232
  when :nullify then hash[key] = nil
227
233
  when :ignore then nil
228
234
  when Proc
229
- key, value = on_error.call(error, object, key, attribute, self.class)
235
+ key, value = on_error.call(error, obj, key, attribute, self.class)
230
236
  hash[key] = value
231
237
  end
232
238
  end
@@ -237,7 +243,7 @@ module Alba
237
243
  return key if @_transform_type == :none || key.empty? # We can skip transformation
238
244
 
239
245
  inflector = Alba.inflector
240
- raise Alba::Error, 'Inflector is nil. You can set inflector with `Alba.enable_inference!(with: :active_support)` for example.' unless inflector
246
+ raise Alba::Error, 'Inflector is nil. You must set inflector before transforming keys.' unless inflector
241
247
 
242
248
  case @_transform_type # rubocop:disable Style/MissingElse
243
249
  when :camel then inflector.camelize(key)
@@ -247,23 +253,23 @@ module Alba
247
253
  end
248
254
  end
249
255
 
250
- def fetch_attribute(object, key, attribute) # rubocop:disable Metrics/CyclomaticComplexity
256
+ def fetch_attribute(obj, key, attribute) # rubocop:disable Metrics/CyclomaticComplexity
251
257
  value = case attribute
252
- when Symbol then fetch_attribute_from_object_and_resource(object, attribute)
253
- when Proc then instance_exec(object, &attribute)
254
- when Alba::Association then yield_if_within(attribute.name.to_sym) { |within| attribute.to_h(object, params: params, within: within) }
255
- when TypedAttribute, NestedAttribute then attribute.value(object)
256
- when ConditionalAttribute then attribute.with_passing_condition(resource: self, object: object) { |attr| fetch_attribute(object, key, attr) }
258
+ when Symbol then fetch_attribute_from_object_and_resource(obj, attribute)
259
+ when Proc then instance_exec(obj, &attribute)
260
+ when Alba::Association then yield_if_within(attribute.name.to_sym) { |within| attribute.to_h(obj, params: params, within: within) }
261
+ when TypedAttribute, NestedAttribute then attribute.value(obj)
262
+ when ConditionalAttribute then attribute.with_passing_condition(resource: self, object: obj) { |attr| fetch_attribute(obj, key, attr) }
257
263
  else
258
264
  raise ::Alba::Error, "Unsupported type of attribute: #{attribute.class}"
259
265
  end
260
- value.nil? && nil_handler ? instance_exec(object, key, attribute, &nil_handler) : value
266
+ value.nil? && nil_handler ? instance_exec(obj, key, attribute, &nil_handler) : value
261
267
  end
262
268
 
263
- def fetch_attribute_from_object_and_resource(object, attribute)
264
- has_method = @method_existence[attribute]
265
- has_method = @method_existence[attribute] = object.respond_to?(attribute) if has_method.nil?
266
- has_method ? object.__send__(attribute) : __send__(attribute, object)
269
+ def fetch_attribute_from_object_and_resource(obj, attribute)
270
+ obj.__send__(attribute)
271
+ rescue NoMethodError
272
+ __send__(attribute, obj)
267
273
  end
268
274
 
269
275
  def nil_handler
@@ -313,7 +319,7 @@ module Alba
313
319
  # @param attrs_with_types [Hash<[Symbol, String], [Array<Symbol, Proc>, Symbol]>]
314
320
  # attributes with name in its key and type and optional type converter in its value
315
321
  # @return [void]
316
- def attributes(*attrs, if: nil, **attrs_with_types) # rubocop:disable Naming/MethodParameterName
322
+ def attributes(*attrs, if: nil, **attrs_with_types)
317
323
  if_value = binding.local_variable_get(:if)
318
324
  assign_attributes(attrs, if_value)
319
325
  assign_attributes_with_types(attrs_with_types, if_value)
@@ -435,8 +441,8 @@ module Alba
435
441
 
436
442
  # Set layout
437
443
  #
438
- # @params file [String] name of the layout file
439
- # @params inline [Proc] a proc returning JSON string or a Hash representing JSON
444
+ # @param file [String] name of the layout file
445
+ # @param inline [Proc] a proc returning JSON string or a Hash representing JSON
440
446
  def layout(file: nil, inline: nil)
441
447
  @_layout = Layout.new(file: file, inline: inline)
442
448
  end
data/lib/alba/version.rb CHANGED
@@ -1,3 +1,3 @@
1
1
  module Alba
2
- VERSION = '2.0.1'.freeze
2
+ VERSION = '2.2.0'.freeze
3
3
  end
data/lib/alba.rb CHANGED
@@ -4,13 +4,15 @@ require_relative 'alba/errors'
4
4
  require_relative 'alba/resource'
5
5
  require_relative 'alba/deprecation'
6
6
 
7
+ require_relative 'alba/railtie' if defined?(Rails::Railtie)
8
+
7
9
  # Core module
8
10
  module Alba
9
11
  class << self
10
- attr_reader :backend, :encoder, :inferring
12
+ attr_reader :backend, :encoder
11
13
 
12
- # Accessor for inflector, a module responsible for inflecting strings
13
- attr_accessor :inflector
14
+ # Getter for inflector, a module responsible for inflecting strings
15
+ attr_reader :inflector
14
16
 
15
17
  # Set the backend, which actually serializes object into JSON
16
18
  #
@@ -54,14 +56,36 @@ module Alba
54
56
  # @param with [Symbol, Class, Module] inflector
55
57
  # When it's a Symbol, it sets inflector with given name
56
58
  # When it's a Class or a Module, it sets given object to inflector
59
+ # @deprecated Use {#inflector=} instead
57
60
  def enable_inference!(with:)
61
+ Alba::Deprecation.warn('Alba.enable_inference! is deprecated. Use `Alba.inflector=` instead.')
58
62
  @inflector = inflector_from(with)
59
63
  @inferring = true
60
64
  end
61
65
 
62
66
  # Disable inference for key and resource name
67
+ #
68
+ # @deprecated Use {#inflector=} instead
63
69
  def disable_inference!
70
+ Alba::Deprecation.warn('Alba.disable_inference! is deprecated. Use `Alba.inflector = nil` instead.')
64
71
  @inferring = false
72
+ @inflector = nil
73
+ end
74
+
75
+ # @deprecated Use {#inflector} instead
76
+ # @return [Boolean] whether inference is enabled or not
77
+ def inferring
78
+ Alba::Deprecation.warn('Alba.inferring is deprecated. Use `Alba.inflector` instead.')
79
+ @inferring
80
+ end
81
+
82
+ # Set an inflector
83
+ #
84
+ # @param inflector [Symbol, Class, Module] inflector
85
+ # When it's a Symbol, it accepts `:default`, `:active_support` or `:dry`
86
+ # When it's a Class or a Module, it should have some methods, see {Alba::DefaultInflector}
87
+ def inflector=(inflector)
88
+ @inflector = inflector_from(inflector)
65
89
  end
66
90
 
67
91
  # @param block [Block] resource body
@@ -77,7 +101,7 @@ module Alba
77
101
  # @param nesting [String, nil] namespace Alba tries to find resource class in
78
102
  # @return [Class<Alba::Resource>] resource class
79
103
  def infer_resource_class(name, nesting: nil)
80
- raise Alba::Error, 'Inference is disabled so Alba cannot infer resource name. Use `Alba.enable_inference!` before use.' unless Alba.inferring
104
+ raise Alba::Error, 'Inference is disabled so Alba cannot infer resource name. Set inflector before use.' unless Alba.inflector
81
105
 
82
106
  const_parent = nesting.nil? ? Object : Object.const_get(nesting)
83
107
  const_parent.const_get("#{inflector.classify(name)}Resource")
@@ -95,6 +119,7 @@ module Alba
95
119
 
96
120
  def inflector_from(name_or_module)
97
121
  case name_or_module
122
+ when nil then nil
98
123
  when :default, :active_support
99
124
  require_relative 'alba/default_inflector'
100
125
  Alba::DefaultInflector
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: alba
3
3
  version: !ruby/object:Gem::Version
4
- version: 2.0.1
4
+ version: 2.2.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - OKURA Masafumi
8
8
  autorequire:
9
9
  bindir: exe
10
10
  cert_chain: []
11
- date: 2022-11-02 00:00:00.000000000 Z
11
+ date: 2023-02-17 00:00:00.000000000 Z
12
12
  dependencies: []
13
13
  description: Alba is the fastest JSON serializer for Ruby. It focuses on performance,
14
14
  flexibility and usability.
@@ -40,6 +40,7 @@ files:
40
40
  - alba.gemspec
41
41
  - benchmark/README.md
42
42
  - benchmark/collection.rb
43
+ - benchmark/prep.rb
43
44
  - benchmark/single_resource.rb
44
45
  - bin/console
45
46
  - bin/setup
@@ -58,6 +59,7 @@ files:
58
59
  - lib/alba/errors.rb
59
60
  - lib/alba/layout.rb
60
61
  - lib/alba/nested_attribute.rb
62
+ - lib/alba/railtie.rb
61
63
  - lib/alba/resource.rb
62
64
  - lib/alba/typed_attribute.rb
63
65
  - lib/alba/version.rb
@@ -82,14 +84,14 @@ required_ruby_version: !ruby/object:Gem::Requirement
82
84
  requirements:
83
85
  - - ">="
84
86
  - !ruby/object:Gem::Version
85
- version: 2.6.0
87
+ version: 2.7.0
86
88
  required_rubygems_version: !ruby/object:Gem::Requirement
87
89
  requirements:
88
90
  - - ">="
89
91
  - !ruby/object:Gem::Version
90
92
  version: '0'
91
93
  requirements: []
92
- rubygems_version: 3.3.21
94
+ rubygems_version: 3.4.6
93
95
  signing_key:
94
96
  specification_version: 4
95
97
  summary: Alba is the fastest JSON serializer for Ruby.