store_model 2.1.1 → 2.2.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: a3b12509ebafeb20d7a2bcb2ae1094dcd756f1b86f31dd8066b0abd61d8f998a
4
- data.tar.gz: d3a06944b46ebf4094de55736e892f15ae27514e0604047260e74a033bbc7cda
3
+ metadata.gz: 02f882325fbae00f97a61603cdab0578ccfd1723a54b8b6e4cfd61aeaabe8a6f
4
+ data.tar.gz: bfd3a7c92a01debecb1fea0d36f73306486612ec7cba22095f9673907ae6b9e4
5
5
  SHA512:
6
- metadata.gz: 7d8ec95caf59aea39e3cedc20a471db9289f4c1eda9d083a1b2fd321f732e7d056b67ac58a7f4f437cb04e932c1f14f18e56dfb9b04c884e5d64025cc7d7989b
7
- data.tar.gz: e526dbc89d1c4186b1fe94581acb2b1d80e207bcf08d69809dffc393d43e3d8d2cd08c905d3d3d4f842c9bf7db9ad1581611368fabe8206eb0445c16a2c615eb
6
+ metadata.gz: d8a703611d38eedfa8d66e5db71084df8a89676e8f6401207451160278ec4df9c7274acab73027d6eba9c6bcb884c77ebd06c420fc08dd592ea423b7e45f9821
7
+ data.tar.gz: c2a876abb12ccd218c40f0e0d9d89613ea03f0d318f7dcffb83c85ea6f6cee3bebc52caf8ae2cf21bc0bc37969d271d04d61a6199d08865ab54ce40277f36a91
data/README.md CHANGED
@@ -1,4 +1,4 @@
1
- # StoreModel [![Gem Version](https://badge.fury.io/rb/store_model.svg)](https://rubygems.org/gems/store_model) [![Coverage Status](https://coveralls.io/repos/github/DmitryTsepelev/store_model/badge.svg?branch=master)](https://coveralls.io/github/DmitryTsepelev/store_model?branch=master) ![](https://ruby-gem-downloads-badge.herokuapp.com/store_model?type=total)
1
+ # StoreModel [![Gem Version](https://badge.fury.io/rb/store_model.svg)](https://rubygems.org/gems/store_model) ![](https://ruby-gem-downloads-badge.herokuapp.com/store_model?type=total)
2
2
 
3
3
  **StoreModel** gem allows you to wrap JSON-backed DB columns with ActiveModel-like classes.
4
4
 
@@ -118,7 +118,7 @@ module StoreModel
118
118
  #
119
119
  # @return [String]
120
120
  def inspect
121
- attribute_string = attributes.map { |name, value| "#{name}: #{value.nil? ? 'nil' : value}" }
121
+ attribute_string = attributes.map { |name, value| "#{name}: #{value.inspect}" }
122
122
  .join(", ")
123
123
  "#<#{self.class.name} #{attribute_string}>"
124
124
  end
@@ -35,25 +35,45 @@ module StoreModel
35
35
  #
36
36
  # See https://api.rubyonrails.org/classes/ActiveRecord/NestedAttributes/ClassMethods.html#method-i-accepts_nested_attributes_for
37
37
  def accepts_nested_attributes_for(*attributes)
38
- global_options = attributes.extract_options!
38
+ options = attributes.extract_options!
39
39
 
40
- attributes.each do |attribute, options|
41
- case attribute_types[attribute.to_s]
40
+ attributes.each do |attribute|
41
+ case nested_attribute_type(attribute)
42
42
  when Types::OneBase, Types::ManyBase
43
- define_store_model_attr_accessors(attribute, options || global_options)
43
+ options.reverse_merge!(allow_destroy: false, update_only: false)
44
+ define_store_model_attr_accessors(attribute, options)
44
45
  else
45
- super(attribute, options || global_options)
46
+ super(*attribute, options)
46
47
  end
47
48
  end
48
49
  end
49
50
 
50
51
  private
51
52
 
53
+ # If attribute defined in ActiveRecord model but you dont yet have database created
54
+ # you cannot access attribute types.
55
+ # To handle this case, we can use ActiveRecord::Attributes 'attributes_to_define_after_schema_loads'
56
+ # which stores information about custom defined attributes.
57
+ # See ActiveRecord::Attributes#atribute
58
+ # If #accepts_nested_attributes_for is used inside active model instance
59
+ # schema is not required to determine attribute type so we can still use attribute_types
60
+ # If schema loaded the attribute_types already populated and we can safely use it
61
+ # See ActiveRecord::ModelSchema#load_schema!
62
+ def nested_attribute_type(attribute)
63
+ if self < ActiveRecord::Base && !schema_loaded?
64
+ attributes_to_define_after_schema_loads[attribute.to_s]&.first
65
+ else
66
+ attribute_types[attribute.to_s]
67
+ end
68
+ end
69
+
52
70
  def define_store_model_attr_accessors(attribute, options)
53
- case attribute_types[attribute.to_s]
71
+ case nested_attribute_type(attribute)
54
72
  when Types::OneBase
55
73
  define_association_setter_for_single(attribute, options)
56
- alias_method "#{attribute}_attributes=", "#{attribute}="
74
+ define_method "#{attribute}_attributes=" do |*args, **kwargs|
75
+ send("#{attribute}=", *args, **kwargs)
76
+ end
57
77
  when Types::ManyBase
58
78
  define_association_setter_for_many(attribute, options)
59
79
  end
@@ -64,7 +84,7 @@ module StoreModel
64
84
  def define_attr_accessor_for_destroy(association, options)
65
85
  return unless options&.dig(:allow_destroy)
66
86
 
67
- attribute_types[association.to_s].model_klass.class_eval do
87
+ nested_attribute_type(association).model_klass.class_eval do
68
88
  attr_accessor :_destroy
69
89
  end
70
90
  end
@@ -88,7 +108,10 @@ module StoreModel
88
108
  end
89
109
  end
90
110
 
91
- def assign_nested_attributes_for_collection_association(association, attributes, options)
111
+ # Base
112
+ def assign_nested_attributes_for_collection_association(association, attributes, options = nil)
113
+ return super(association, attributes) unless options
114
+
92
115
  attributes = attributes.values if attributes.is_a?(Hash)
93
116
 
94
117
  if options&.dig(:allow_destroy)
@@ -63,7 +63,7 @@ module StoreModel
63
63
  def deserialize(value)
64
64
  case value
65
65
  when String
66
- payload = ActiveSupport::JSON.decode(value) rescue nil
66
+ payload = ActiveSupport::JSON.decode(value) rescue {}
67
67
  model_instance(deserialize_by_types(payload))
68
68
  when Hash
69
69
  model_instance(deserialize_by_types(value))
@@ -1,5 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  module StoreModel # :nodoc:
4
- VERSION = "2.1.1"
4
+ VERSION = "2.2.0"
5
5
  end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: store_model
3
3
  version: !ruby/object:Gem::Version
4
- version: 2.1.1
4
+ version: 2.2.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - DmitryTsepelev
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2023-08-29 00:00:00.000000000 Z
11
+ date: 2024-01-06 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: activerecord
@@ -66,20 +66,6 @@ dependencies:
66
66
  - - '='
67
67
  - !ruby/object:Gem::Version
68
68
  version: 0.64.0
69
- - !ruby/object:Gem::Dependency
70
- name: coveralls
71
- requirement: !ruby/object:Gem::Requirement
72
- requirements:
73
- - - ">="
74
- - !ruby/object:Gem::Version
75
- version: '0'
76
- type: :development
77
- prerelease: false
78
- version_requirements: !ruby/object:Gem::Requirement
79
- requirements:
80
- - - ">="
81
- - !ruby/object:Gem::Version
82
- version: '0'
83
69
  description: Gem for working with JSON-backed attributes as ActiveRecord models
84
70
  email:
85
71
  - dmitry.a.tsepelev@gmail.com