active_record-json_associations 0.6.10 → 0.10.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.
- checksums.yaml +5 -5
- data/.gitignore +1 -0
- data/.travis.yml +15 -3
- data/Appraisals +21 -0
- data/README.md +26 -0
- data/active_record-json_associations.gemspec +3 -1
- data/bin/setup +8 -0
- data/gemfiles/rails_5.0.gemfile +8 -0
- data/gemfiles/rails_5.1.gemfile +7 -0
- data/gemfiles/rails_5.2.gemfile +7 -0
- data/gemfiles/rails_6.0.gemfile +7 -0
- data/gemfiles/rails_6.1.gemfile +7 -0
- data/lib/active_record/json_associations.rb +60 -8
- data/lib/active_record/json_associations/version.rb +1 -1
- data/spec/json_associations_spec.rb +212 -3
- data/spec/spec_helper.rb +1 -0
- metadata +44 -9
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
|
-
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
2
|
+
SHA256:
|
3
|
+
metadata.gz: 3dcecc3d5ba41f7deed96e8178f04221c39678799e3706b0c95938f91f197daf
|
4
|
+
data.tar.gz: c9fcdad4e8cbe19a16fc7bf3d27c8e176e5cedb06a415e95c36aff1b734ffb85
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: a13fc51a526b61d909d6559e22969a9e4f7c75e880efc2ffc50b0c01e1b2aa7daf4858c33beb0dfbac7a57aa77329fd030af02db02efcb7058b8b78f93386328
|
7
|
+
data.tar.gz: e6d33f695da6f13a6ed3253ab90a0246e77a788f7593b3d1338ec8e11d6e449b4f294a8c690f5f4f2f506fb10478c3494e198fba7275d50b8d3f72f38e0d1485
|
data/.gitignore
CHANGED
data/.travis.yml
CHANGED
@@ -1,6 +1,18 @@
|
|
1
1
|
language: ruby
|
2
2
|
rvm:
|
3
|
-
- 2.
|
4
|
-
- 2.
|
5
|
-
- 2.
|
3
|
+
- 2.4
|
4
|
+
- 2.5
|
5
|
+
- 2.6
|
6
|
+
- 2.7
|
7
|
+
gemfile:
|
8
|
+
- gemfiles/rails_5.0.gemfile
|
9
|
+
- gemfiles/rails_5.1.gemfile
|
10
|
+
- gemfiles/rails_5.2.gemfile
|
11
|
+
- gemfiles/rails_6.0.gemfile
|
12
|
+
jobs:
|
13
|
+
exclude:
|
14
|
+
- rvm: 2.4
|
15
|
+
gemfile: gemfiles/rails_6.0.gemfile
|
16
|
+
before_install:
|
17
|
+
- gem install bundler -v"~>1.17"
|
6
18
|
|
data/Appraisals
ADDED
@@ -0,0 +1,21 @@
|
|
1
|
+
appraise "rails-5.0" do
|
2
|
+
gem "rails", "~>5.0.0"
|
3
|
+
gem "sqlite3", "~>1.3.13" # 1.4 seems to break rails 5.0?
|
4
|
+
end
|
5
|
+
|
6
|
+
appraise "rails-5.1" do
|
7
|
+
gem "rails", "~>5.1.0"
|
8
|
+
end
|
9
|
+
|
10
|
+
appraise "rails-5.2" do
|
11
|
+
gem "rails", "~>5.2.0"
|
12
|
+
end
|
13
|
+
|
14
|
+
appraise "rails-6.0" do
|
15
|
+
gem "rails", "~>6.0.0"
|
16
|
+
end
|
17
|
+
|
18
|
+
appraise "rails-6.1" do
|
19
|
+
gem "rails", "~>6.1.0"
|
20
|
+
end
|
21
|
+
|
data/README.md
CHANGED
@@ -37,6 +37,20 @@ parent.child_ids #=> [1,2]
|
|
37
37
|
parent.children? #=> true
|
38
38
|
```
|
39
39
|
|
40
|
+
And a scope method for finding records assocatied with an id:
|
41
|
+
|
42
|
+
```ruby
|
43
|
+
Parent.child_ids_including(2) # => [<Parent child_ids: [1,2,3]>]
|
44
|
+
```
|
45
|
+
|
46
|
+
Or any of specified array of ids:
|
47
|
+
|
48
|
+
```ruby
|
49
|
+
Parent.child_ids_including([2,4,5]) # => [<Parent child_ids: [1,2,3]>]
|
50
|
+
```
|
51
|
+
|
52
|
+
`touch: true` can be specified on belongs_to_many to touch the associated records' timestamps when the record is modified.
|
53
|
+
|
40
54
|
It also adds an `json_foreign_key` option to `has_many` for specifying that the foreign keys are in a json array.
|
41
55
|
|
42
56
|
```ruby
|
@@ -49,6 +63,18 @@ parent = Parent.create children: [child]
|
|
49
63
|
child.parents == [parent] #=> true
|
50
64
|
```
|
51
65
|
|
66
|
+
I can't figure out how to support building records off the association, so instead there are the `has_one`/`belongs_to` builder methods:
|
67
|
+
|
68
|
+
```ruby
|
69
|
+
child.build_parent
|
70
|
+
child.create_parent
|
71
|
+
child.create_parent!
|
72
|
+
|
73
|
+
# also supports optional attributes:
|
74
|
+
|
75
|
+
child.build_parent(name: "Momma")
|
76
|
+
```
|
77
|
+
|
52
78
|
## Requirements
|
53
79
|
|
54
80
|
* ActiveRecord 5.0+
|
@@ -20,10 +20,12 @@ Gem::Specification.new do |spec|
|
|
20
20
|
|
21
21
|
spec.add_dependency "activerecord"
|
22
22
|
|
23
|
-
spec.add_development_dependency "bundler"
|
23
|
+
spec.add_development_dependency "bundler"
|
24
|
+
spec.add_development_dependency "appraisal"
|
24
25
|
spec.add_development_dependency "rake"
|
25
26
|
spec.add_development_dependency "rspec"
|
26
27
|
spec.add_development_dependency "sqlite3"
|
27
28
|
spec.add_development_dependency "byebug"
|
29
|
+
spec.add_development_dependency "timecop"
|
28
30
|
end
|
29
31
|
|
data/bin/setup
ADDED
@@ -3,7 +3,15 @@ require "json"
|
|
3
3
|
|
4
4
|
module ActiveRecord
|
5
5
|
module JsonAssociations
|
6
|
-
|
6
|
+
FIELD_INCLUDE_SCOPE_BUILDER_PROC = proc do |context, field, id|
|
7
|
+
context.where("#{field}='[#{id}]'").or(
|
8
|
+
context.where("#{field} LIKE '[#{id},%'")).or(
|
9
|
+
context.where("#{field} LIKE '%,#{id},%'")).or(
|
10
|
+
context.where("#{field} LIKE '%,#{id}]'"))
|
11
|
+
end
|
12
|
+
private_constant :FIELD_INCLUDE_SCOPE_BUILDER_PROC
|
13
|
+
|
14
|
+
def belongs_to_many(many, class_name: nil, touch: nil)
|
7
15
|
one = many.to_s.singularize
|
8
16
|
one_ids = :"#{one}_ids"
|
9
17
|
one_ids_equals = :"#{one_ids}="
|
@@ -14,6 +22,39 @@ module ActiveRecord
|
|
14
22
|
|
15
23
|
serialize one_ids, JSON
|
16
24
|
|
25
|
+
if touch
|
26
|
+
after_commit do
|
27
|
+
method = respond_to?(:saved_changes) ? :saved_changes : :previous_changes
|
28
|
+
old_ids, new_ids = send(method)[one_ids.to_s]
|
29
|
+
ids = Array(send(one_ids)) | Array(old_ids) | Array(new_ids)
|
30
|
+
scope = class_name.constantize.where(self.class.primary_key => ids)
|
31
|
+
|
32
|
+
if scope.respond_to?(:touch) # AR 6.0+
|
33
|
+
scope.touch_all
|
34
|
+
elsif self.class.respond_to?(:touch_attributes_with_time) # AR 5.1+
|
35
|
+
scope.update_all self.class.touch_attributes_with_time
|
36
|
+
else # AR 5.0
|
37
|
+
attributes = timestamp_attributes_for_update_in_model.inject({}) do |attributes, key|
|
38
|
+
attributes.merge(key => current_time_from_proper_timezone)
|
39
|
+
end
|
40
|
+
scope.update_all attributes
|
41
|
+
end
|
42
|
+
end
|
43
|
+
end
|
44
|
+
|
45
|
+
extend Module.new {
|
46
|
+
define_method :"#{one_ids}_including" do |id|
|
47
|
+
raise "can't query for a record that does not have an id!" if id.blank?
|
48
|
+
if id.is_a?(Hash)
|
49
|
+
Array(id[:any]).inject(none) do |context, id|
|
50
|
+
context.or(FIELD_INCLUDE_SCOPE_BUILDER_PROC.call(self, one_ids, id))
|
51
|
+
end
|
52
|
+
else
|
53
|
+
FIELD_INCLUDE_SCOPE_BUILDER_PROC.call(self, one_ids, id)
|
54
|
+
end
|
55
|
+
end
|
56
|
+
}
|
57
|
+
|
17
58
|
include Module.new {
|
18
59
|
define_method one_ids do
|
19
60
|
super().tap do |value|
|
@@ -49,7 +90,7 @@ module ActiveRecord
|
|
49
90
|
}
|
50
91
|
end
|
51
92
|
|
52
|
-
def has_many many, scope = nil, options
|
93
|
+
def has_many many, scope = nil, **options, &extension
|
53
94
|
unless (scope.is_a?(Hash) && scope[:json_foreign_key]) || (options.is_a?(Hash) && options[:json_foreign_key])
|
54
95
|
return super
|
55
96
|
end
|
@@ -64,8 +105,12 @@ module ActiveRecord
|
|
64
105
|
one_ids_equals = :"#{one_ids}="
|
65
106
|
many_equals = :"#{many}="
|
66
107
|
many_eh = :"#{many}?"
|
108
|
+
build_one = :"build_#{one}"
|
109
|
+
create_one = :"create_#{one}"
|
110
|
+
create_one_bang = :"create_#{one}!"
|
67
111
|
|
68
112
|
class_name = options[:class_name] || one.classify
|
113
|
+
klass = class_name.constantize
|
69
114
|
|
70
115
|
foreign_key = options[:json_foreign_key]
|
71
116
|
foreign_key = :"#{model_name.singular}_ids" if foreign_key == true
|
@@ -76,17 +121,12 @@ module ActiveRecord
|
|
76
121
|
end
|
77
122
|
|
78
123
|
define_method one_ids_equals do |ids|
|
79
|
-
klass = class_name.constantize
|
80
124
|
normalized_ids = Array(ids).select(&:present?).map(&:to_i)
|
81
125
|
send many_equals, klass.find(normalized_ids)
|
82
126
|
end
|
83
127
|
|
84
128
|
define_method many do
|
85
|
-
klass
|
86
|
-
klass.where("#{foreign_key} LIKE '[#{id}]'").or(
|
87
|
-
klass.where("#{foreign_key} LIKE '[#{id},%'")).or(
|
88
|
-
klass.where("#{foreign_key} LIKE '%,#{id},%'")).or(
|
89
|
-
klass.where("#{foreign_key} LIKE '%,#{id}]'"))
|
129
|
+
FIELD_INCLUDE_SCOPE_BUILDER_PROC.call(klass, foreign_key, id)
|
90
130
|
end
|
91
131
|
|
92
132
|
define_method many_equals do |collection|
|
@@ -100,6 +140,18 @@ module ActiveRecord
|
|
100
140
|
define_method many_eh do
|
101
141
|
send(many).any?
|
102
142
|
end
|
143
|
+
|
144
|
+
define_method build_one do |attributes={}|
|
145
|
+
klass.new attributes.merge!(foreign_key => [id])
|
146
|
+
end
|
147
|
+
|
148
|
+
define_method create_one do |attributes={}|
|
149
|
+
klass.create attributes.merge!(foreign_key => [id])
|
150
|
+
end
|
151
|
+
|
152
|
+
define_method create_one_bang do |attributes={}|
|
153
|
+
klass.create! attributes.merge!(foreign_key => [id])
|
154
|
+
end
|
103
155
|
}
|
104
156
|
end
|
105
157
|
end
|
@@ -7,18 +7,24 @@ describe ActiveRecord::JsonAssociations do
|
|
7
7
|
silence_stream(STDOUT) do
|
8
8
|
ActiveRecord::Schema.define do
|
9
9
|
create_table :parents do |t|
|
10
|
+
t.string :name
|
10
11
|
t.text :child_ids
|
11
12
|
t.text :fuzzy_ids
|
13
|
+
t.timestamps
|
12
14
|
end
|
13
15
|
|
14
|
-
create_table :children
|
16
|
+
create_table :children do |t|
|
17
|
+
t.timestamps
|
18
|
+
end
|
15
19
|
|
16
|
-
create_table :pets
|
20
|
+
create_table :pets do |t|
|
21
|
+
t.timestamps
|
22
|
+
end
|
17
23
|
end
|
18
24
|
end
|
19
25
|
|
20
26
|
class Parent < ActiveRecord::Base
|
21
|
-
belongs_to_many :children
|
27
|
+
belongs_to_many :children, touch: true
|
22
28
|
belongs_to_many :fuzzies, class_name: "Pet"
|
23
29
|
end
|
24
30
|
|
@@ -38,6 +44,148 @@ describe ActiveRecord::JsonAssociations do
|
|
38
44
|
|
39
45
|
describe ".belongs_to_many :children" do
|
40
46
|
subject { Parent.new }
|
47
|
+
let!(:winner) { Parent.create! }
|
48
|
+
|
49
|
+
describe ".child_ids_including" do
|
50
|
+
context "finds records with the specified id" do
|
51
|
+
let(:child) { Child.create! }
|
52
|
+
|
53
|
+
it "as the whole json array" do
|
54
|
+
parent = Parent.create(children: [child])
|
55
|
+
expect(Parent.child_ids_including(child.id)).to eq [parent]
|
56
|
+
end
|
57
|
+
|
58
|
+
it "at the beginning of the json array" do
|
59
|
+
parent = Parent.create(children: [child, Child.create!])
|
60
|
+
expect(Parent.child_ids_including(child.id)).to eq [parent]
|
61
|
+
end
|
62
|
+
|
63
|
+
it "in the middle of the json array" do
|
64
|
+
parent = Parent.create(children: [Child.create!, child, Child.create!])
|
65
|
+
expect(Parent.child_ids_including(child.id)).to eq [parent]
|
66
|
+
end
|
67
|
+
|
68
|
+
it "at the end of the json array" do
|
69
|
+
parent = Parent.create(children: [Child.create!, child])
|
70
|
+
expect(Parent.child_ids_including(child.id)).to eq [parent]
|
71
|
+
end
|
72
|
+
end
|
73
|
+
|
74
|
+
context "finds records including any of the specified array of ids" do
|
75
|
+
let(:peter) { Child.create! }
|
76
|
+
let(:paul) { Child.create! }
|
77
|
+
|
78
|
+
it "both as the whole json array" do
|
79
|
+
parent = Parent.create(children: [peter, paul])
|
80
|
+
expect(Parent.child_ids_including(any: [peter.id, paul.id])).to eq [parent]
|
81
|
+
end
|
82
|
+
|
83
|
+
it "one as the whole json array" do
|
84
|
+
parent = Parent.create(children: [peter])
|
85
|
+
expect(Parent.child_ids_including(any: [peter.id, paul.id])).to eq [parent]
|
86
|
+
end
|
87
|
+
|
88
|
+
it "the other as the whole json array" do
|
89
|
+
parent = Parent.create(children: [paul])
|
90
|
+
expect(Parent.child_ids_including(any: [peter.id, paul.id])).to eq [parent]
|
91
|
+
end
|
92
|
+
|
93
|
+
it "both at the beginning of the json array" do
|
94
|
+
parent = Parent.create(children: [peter, paul, Child.create!])
|
95
|
+
expect(Parent.child_ids_including(any: [peter.id, paul.id])).to eq [parent]
|
96
|
+
end
|
97
|
+
|
98
|
+
it "one at the beginning of the json array" do
|
99
|
+
parent = Parent.create(children: [peter, Child.create!])
|
100
|
+
expect(Parent.child_ids_including(any: [peter.id, paul.id])).to eq [parent]
|
101
|
+
end
|
102
|
+
|
103
|
+
it "the other at the beginning of the json array" do
|
104
|
+
parent = Parent.create(children: [paul, Child.create!])
|
105
|
+
expect(Parent.child_ids_including(any: [peter.id, paul.id])).to eq [parent]
|
106
|
+
end
|
107
|
+
|
108
|
+
it "both in the middle of the json array" do
|
109
|
+
parent = Parent.create(children: [Child.create!, peter, paul, Child.create!])
|
110
|
+
expect(Parent.child_ids_including(any: [peter.id, paul.id])).to eq [parent]
|
111
|
+
end
|
112
|
+
|
113
|
+
it "one in the middle of the json array" do
|
114
|
+
parent = Parent.create(children: [Child.create!, peter, Child.create!])
|
115
|
+
expect(Parent.child_ids_including(any: [peter.id, paul.id])).to eq [parent]
|
116
|
+
end
|
117
|
+
|
118
|
+
it "the other in the middle of the json array" do
|
119
|
+
parent = Parent.create(children: [Child.create!, paul, Child.create!])
|
120
|
+
expect(Parent.child_ids_including(any: [peter.id, paul.id])).to eq [parent]
|
121
|
+
end
|
122
|
+
|
123
|
+
it "both at the end of the json array" do
|
124
|
+
parent = Parent.create(children: [Child.create!, peter, paul])
|
125
|
+
expect(Parent.child_ids_including(any: [peter.id, paul.id])).to eq [parent]
|
126
|
+
end
|
127
|
+
|
128
|
+
it "one at the end of the json array" do
|
129
|
+
parent = Parent.create(children: [Child.create!, peter])
|
130
|
+
expect(Parent.child_ids_including(any: [peter.id, paul.id])).to eq [parent]
|
131
|
+
end
|
132
|
+
|
133
|
+
it "the other at the end of the json array" do
|
134
|
+
parent = Parent.create(children: [Child.create!, paul])
|
135
|
+
expect(Parent.child_ids_including(any: [peter.id, paul.id])).to eq [parent]
|
136
|
+
end
|
137
|
+
end
|
138
|
+
end
|
139
|
+
|
140
|
+
describe "touch: true" do
|
141
|
+
around do |example|
|
142
|
+
old_zone = Time.zone
|
143
|
+
Time.zone = "UTC"
|
144
|
+
example.run
|
145
|
+
Time.zone = old_zone
|
146
|
+
end
|
147
|
+
|
148
|
+
let(:old_time) { 1.year.ago.round }
|
149
|
+
let(:new_time) { 1.second.ago.round }
|
150
|
+
|
151
|
+
around do |example|
|
152
|
+
Timecop.freeze(new_time) do
|
153
|
+
example.run
|
154
|
+
end
|
155
|
+
end
|
156
|
+
|
157
|
+
it "touches records associated upon creation" do
|
158
|
+
children = [Child.create!(updated_at: old_time), Child.create!(updated_at: old_time)]
|
159
|
+
fuzzies = [Pet.create!(updated_at: old_time), Pet.create!(updated_at: old_time)]
|
160
|
+
parent = Parent.create!(children: children, fuzzies: fuzzies)
|
161
|
+
expect(children.each(&:reload).map(&:updated_at)).to eq [new_time, new_time] # touch: true
|
162
|
+
expect(fuzzies.each(&:reload).map(&:updated_at)).to eq [old_time, old_time] # touch: nil
|
163
|
+
end
|
164
|
+
|
165
|
+
it "touches exising association records" do
|
166
|
+
children = [Child.create!, Child.create!]
|
167
|
+
parent = Parent.create!(children: children)
|
168
|
+
children.each { |child| child.update!(updated_at: old_time) }
|
169
|
+
parent.save!
|
170
|
+
expect(children.each(&:reload).map(&:updated_at)).to eq [new_time, new_time]
|
171
|
+
end
|
172
|
+
|
173
|
+
it "touches removed associated records" do
|
174
|
+
peter, paul, mary = Child.create!, Child.create!, Child.create!
|
175
|
+
parent = Parent.create!(children: [peter, paul, mary])
|
176
|
+
[peter, paul, mary].each { |child| child.update_column :updated_at, old_time }
|
177
|
+
parent.update!(children: [peter, paul])
|
178
|
+
expect([peter, paul, mary].each(&:reload).map(&:updated_at)).to eq [new_time, new_time, new_time]
|
179
|
+
end
|
180
|
+
|
181
|
+
it "touches added associated records" do
|
182
|
+
peter, paul, mary = Child.create!, Child.create!, Child.create!
|
183
|
+
parent = Parent.create!(children: [peter, paul])
|
184
|
+
[peter, paul, mary].each { |child| child.update_column :updated_at, old_time }
|
185
|
+
parent.update!(children: [peter, paul, mary])
|
186
|
+
expect([peter, paul, mary].each(&:reload).map(&:updated_at)).to eq [new_time, new_time, new_time]
|
187
|
+
end
|
188
|
+
end
|
41
189
|
|
42
190
|
describe "#child_ids" do
|
43
191
|
it "is empty by default" do
|
@@ -199,6 +347,67 @@ describe ActiveRecord::JsonAssociations do
|
|
199
347
|
expect(subject.parents?).to be_truthy
|
200
348
|
end
|
201
349
|
end
|
350
|
+
|
351
|
+
describe "#build_parent" do
|
352
|
+
it "doesnt save the record" do
|
353
|
+
parent = subject.build_parent
|
354
|
+
expect(parent).to be_new_record
|
355
|
+
end
|
356
|
+
|
357
|
+
it "sets the foreign key column" do
|
358
|
+
parent = subject.build_parent
|
359
|
+
expect(parent.children).to eq([subject])
|
360
|
+
end
|
361
|
+
|
362
|
+
it "passes attributes through" do
|
363
|
+
parent = subject.build_parent(name: "Parent")
|
364
|
+
expect(parent.name).to eq("Parent")
|
365
|
+
end
|
366
|
+
end
|
367
|
+
|
368
|
+
describe "#create_parent" do
|
369
|
+
it "saves the record" do
|
370
|
+
parent = subject.create_parent
|
371
|
+
expect(parent).to be_persisted
|
372
|
+
end
|
373
|
+
|
374
|
+
it "sets the foreign key column" do
|
375
|
+
parent = subject.create_parent
|
376
|
+
expect(parent.children).to eq([subject])
|
377
|
+
end
|
378
|
+
|
379
|
+
it "passes attributes through" do
|
380
|
+
parent = subject.create_parent(name: "Parent")
|
381
|
+
expect(parent.name).to eq("Parent")
|
382
|
+
end
|
383
|
+
|
384
|
+
it "calls create on the model" do
|
385
|
+
expect(Parent).to receive(:create)
|
386
|
+
subject.create_parent
|
387
|
+
end
|
388
|
+
end
|
389
|
+
|
390
|
+
describe "#create_parent!" do
|
391
|
+
it "saves the record" do
|
392
|
+
parent = subject.create_parent!
|
393
|
+
expect(parent).to be_persisted
|
394
|
+
end
|
395
|
+
|
396
|
+
it "sets the foreign key column" do
|
397
|
+
parent = subject.create_parent!
|
398
|
+
expect(parent.children).to eq([subject])
|
399
|
+
end
|
400
|
+
|
401
|
+
it "passes attributes through" do
|
402
|
+
parent = subject.create_parent!(name: "Parent")
|
403
|
+
expect(parent.name).to eq("Parent")
|
404
|
+
end
|
405
|
+
|
406
|
+
it "calls create! on the model" do
|
407
|
+
expect(Parent).to receive(:create!)
|
408
|
+
subject.create_parent!
|
409
|
+
end
|
410
|
+
end
|
202
411
|
end
|
203
412
|
|
204
413
|
describe ".has_many :parents, json_foreign_key: :fuzzy_ids" do
|
data/spec/spec_helper.rb
CHANGED
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: active_record-json_associations
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.
|
4
|
+
version: 0.10.0
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Micah Geisel
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date:
|
11
|
+
date: 2021-01-25 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: activerecord
|
@@ -28,16 +28,30 @@ dependencies:
|
|
28
28
|
name: bundler
|
29
29
|
requirement: !ruby/object:Gem::Requirement
|
30
30
|
requirements:
|
31
|
-
- - "
|
31
|
+
- - ">="
|
32
|
+
- !ruby/object:Gem::Version
|
33
|
+
version: '0'
|
34
|
+
type: :development
|
35
|
+
prerelease: false
|
36
|
+
version_requirements: !ruby/object:Gem::Requirement
|
37
|
+
requirements:
|
38
|
+
- - ">="
|
32
39
|
- !ruby/object:Gem::Version
|
33
|
-
version: '
|
40
|
+
version: '0'
|
41
|
+
- !ruby/object:Gem::Dependency
|
42
|
+
name: appraisal
|
43
|
+
requirement: !ruby/object:Gem::Requirement
|
44
|
+
requirements:
|
45
|
+
- - ">="
|
46
|
+
- !ruby/object:Gem::Version
|
47
|
+
version: '0'
|
34
48
|
type: :development
|
35
49
|
prerelease: false
|
36
50
|
version_requirements: !ruby/object:Gem::Requirement
|
37
51
|
requirements:
|
38
|
-
- - "
|
52
|
+
- - ">="
|
39
53
|
- !ruby/object:Gem::Version
|
40
|
-
version: '
|
54
|
+
version: '0'
|
41
55
|
- !ruby/object:Gem::Dependency
|
42
56
|
name: rake
|
43
57
|
requirement: !ruby/object:Gem::Requirement
|
@@ -94,21 +108,43 @@ dependencies:
|
|
94
108
|
- - ">="
|
95
109
|
- !ruby/object:Gem::Version
|
96
110
|
version: '0'
|
111
|
+
- !ruby/object:Gem::Dependency
|
112
|
+
name: timecop
|
113
|
+
requirement: !ruby/object:Gem::Requirement
|
114
|
+
requirements:
|
115
|
+
- - ">="
|
116
|
+
- !ruby/object:Gem::Version
|
117
|
+
version: '0'
|
118
|
+
type: :development
|
119
|
+
prerelease: false
|
120
|
+
version_requirements: !ruby/object:Gem::Requirement
|
121
|
+
requirements:
|
122
|
+
- - ">="
|
123
|
+
- !ruby/object:Gem::Version
|
124
|
+
version: '0'
|
97
125
|
description: Instead of a many-to-many join table, serialize the ids into a JSON array.
|
98
126
|
email:
|
99
127
|
- micah@botandrose.com
|
100
|
-
executables:
|
128
|
+
executables:
|
129
|
+
- setup
|
101
130
|
extensions: []
|
102
131
|
extra_rdoc_files: []
|
103
132
|
files:
|
104
133
|
- ".gitignore"
|
105
134
|
- ".rspec"
|
106
135
|
- ".travis.yml"
|
136
|
+
- Appraisals
|
107
137
|
- Gemfile
|
108
138
|
- LICENSE.txt
|
109
139
|
- README.md
|
110
140
|
- Rakefile
|
111
141
|
- active_record-json_associations.gemspec
|
142
|
+
- bin/setup
|
143
|
+
- gemfiles/rails_5.0.gemfile
|
144
|
+
- gemfiles/rails_5.1.gemfile
|
145
|
+
- gemfiles/rails_5.2.gemfile
|
146
|
+
- gemfiles/rails_6.0.gemfile
|
147
|
+
- gemfiles/rails_6.1.gemfile
|
112
148
|
- lib/active_record/json_associations.rb
|
113
149
|
- lib/active_record/json_associations/version.rb
|
114
150
|
- spec/json_associations_spec.rb
|
@@ -132,8 +168,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
|
|
132
168
|
- !ruby/object:Gem::Version
|
133
169
|
version: '0'
|
134
170
|
requirements: []
|
135
|
-
|
136
|
-
rubygems_version: 2.4.8
|
171
|
+
rubygems_version: 3.0.3
|
137
172
|
signing_key:
|
138
173
|
specification_version: 4
|
139
174
|
summary: Instead of a many-to-many join table, serialize the ids into a JSON array.
|