serialize_attributes 0.2.0 → 0.4.0

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 336ab0663fe21a1f3750663a41aec451f209bf1141f233f3043c914aefd0ebf9
4
- data.tar.gz: c80f05ff696c4292571c5ae613343687377bb10e1235790ea332dc80e6e15230
3
+ metadata.gz: c505eb52395e2c8fe3786c3ef97dd04e5a56f978072d839ba517c0069f9dce93
4
+ data.tar.gz: 5ea660579c45ebd3cca56da5c3ea7e07fe9af5fb38a05fd62d3133f118f3d8df
5
5
  SHA512:
6
- metadata.gz: c3f9f7d020b7002f2b83e816452f4166a26cb4a1f2fdfaf3271977bfb8c80d8f075456ebeeeec042a1c544786f5fa2a5f80a16f7353596eb4817cdc76e768b95
7
- data.tar.gz: 6c0133edf56b9a396cfe011f4abda01d3ac61b1c95dca5329dcaa1d8a29b2bd366ac28f691b8e1d6aa4c565398781131921a6645f8b69a8051565bfabc9b1676
6
+ metadata.gz: 311846e88d0c92cf41bf5adbd32c1515fbd1d131df0d733cfd444963bedc8594620d05cb12cfe701b40fba851195931f6f53673dcbe25593bf257e2b28c183dc
7
+ data.tar.gz: c5e2e60ba000e0afe423cee6c37e20fae5b590a39bcadab76d65712db712359e1d4ae3c0532e44565d673cb1c8f55cd4d535b9fdc057f50d11d3e3744f0803e9
data/README.md CHANGED
@@ -7,6 +7,7 @@ class MyModel
7
7
  serialize_attributes :settings do
8
8
  attribute :user_name, :string
9
9
  attribute :subscribed, :boolean, default: false
10
+ attribute :subscriptions, :string, array: true
10
11
  end
11
12
  end
12
13
  ```
@@ -83,6 +84,13 @@ MyModel.serialized_attribute_names(:settings)
83
84
  #=> [:user_name, :subscribed]
84
85
  ```
85
86
 
87
+ You can also get a list of the attributes filtered by a type specifier:
88
+
89
+ ```ruby
90
+ MyModel.serialized_attribute_names(:settings, :boolean)
91
+ #=> [:subscribed]
92
+ ```
93
+
86
94
  ### Complex types
87
95
 
88
96
  Underneath, we use the `ActiveModel::Type` mechanism for type coercion, which means
@@ -4,7 +4,8 @@ module SerializeAttributes
4
4
  # SerializeAttributes::Store is the individual store, keyed by name. You can get a
5
5
  # reference to the store by calling `Model.serialized_attributes_store(column_name)`.
6
6
  class Store
7
- def initialize(model_class, column_name, &block) # :nodoc:
7
+ def initialize(model_class, column_name, &block)
8
+ # :nodoc:
8
9
  @model_class = model_class
9
10
  @column_name = column_name
10
11
  @attributes = {}
@@ -15,8 +16,31 @@ module SerializeAttributes
15
16
  [self, @attributes, @defaults].each(&:freeze)
16
17
  end
17
18
 
18
- # Get a list of the attributes managed by this store
19
- def attribute_names = @attributes.keys
19
+ # Get a list of the attributes managed by this store. Pass an optional `type` argument
20
+ # to filter attributes by their type.
21
+ #
22
+ # Model.serialize_attributes_store(:settings).attribute_names
23
+ # => [:user_name, :subscribed, :subscriptions]
24
+ #
25
+ # Model.serialize_attributes_store(:settings).attribute_names(type: :string)
26
+ # => [:user_name, :subscriptions]
27
+ #
28
+ # Model.serialize_attributes_store(:settings).attribute_names(type: :string, array: true)
29
+ # => [:subscriptions]
30
+ #
31
+ # Model.serialize_attributes_store(:settings).attribute_names(type: :string, array: false)
32
+ # => [:user_name]
33
+ #
34
+ #
35
+ def attribute_names(type: nil, array: nil)
36
+ attributes = @attributes
37
+ attributes = @attributes.select { |_, v| v.is_a?(ArrayWrapper) == array } unless array.nil?
38
+ if type
39
+ attributes_for_type(attributes, type)
40
+ else
41
+ attributes
42
+ end.keys
43
+ end
20
44
 
21
45
  # Cast a stored attribute against a given name
22
46
  #
@@ -48,9 +72,17 @@ module SerializeAttributes
48
72
 
49
73
  private
50
74
 
75
+ def attributes_for_type(attributes, type)
76
+ type = ActiveModel::Type.lookup(type)&.class if type.is_a?(Symbol)
77
+ attributes.select do |_, v|
78
+ v = v.__getobj__ if v.is_a?(ArrayWrapper)
79
+ v.is_a?(type)
80
+ end
81
+ end
82
+
51
83
  def attribute(name, type, **options)
52
84
  name = name.to_sym
53
- arr = options.delete(:array) { false }
85
+ arr = options.delete(:array) { false }
54
86
  type = ActiveModel::Type.lookup(type, **options.except(:default)) if type.is_a?(Symbol)
55
87
  type = ArrayWrapper.new(type) if arr
56
88
 
@@ -126,14 +158,18 @@ module SerializeAttributes
126
158
 
127
159
  # This method wraps the original store column and catches the `deserialize` call -
128
160
  # this gives us a chance to convert the data in the database back into our types.
161
+ #
162
+ # We're using the block form of `.attribute` to avoid loading the database schema just
163
+ # to figure out our wrapping type.
129
164
  def wrap_store_column
130
165
  return unless @model_class.respond_to?(:attribute_types)
131
166
 
132
- original_store_column_type = @model_class.attribute_types.fetch(@column_name.to_s)
133
- @model_class.attribute(@column_name, StoreColumnWrapper.new(
134
- original_store_column_type,
135
- self
136
- ))
167
+ store = self
168
+
169
+ @model_class.attribute(@column_name) do
170
+ original_type = @model_class.attribute_types.fetch(@column_name.to_s)
171
+ StoreColumnWrapper.new(original_type, store)
172
+ end
137
173
  end
138
174
  end
139
175
  end
@@ -1,5 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  module SerializeAttributes
4
- VERSION = "0.2.0"
4
+ VERSION = "0.4.0"
5
5
  end
@@ -34,9 +34,10 @@ module SerializeAttributes
34
34
 
35
35
  # Get a list of the attributes registered in a given store
36
36
  #
37
- # Person.serialized_attribute_names(:settings)
38
- def serialized_attribute_names(column_name)
39
- serialized_attributes_store(column_name).attribute_names
37
+ # Person.serialized_attribute_names(:settings, :string)
38
+ # => [:user_name]
39
+ def serialized_attribute_names(column_name, type = nil)
40
+ serialized_attributes_store(column_name).attribute_names(type: type)
40
41
  end
41
42
  end
42
43
 
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: serialize_attributes
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.2.0
4
+ version: 0.4.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Zaikio
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2022-01-12 00:00:00.000000000 Z
11
+ date: 2022-03-07 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: activemodel