mongoid_max_denormalize 0.0.2 → 0.0.3
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/README.md +36 -6
- data/lib/mongoid/max/denormalize/base.rb +26 -0
- data/lib/mongoid/max/denormalize/config_error.rb +2 -2
- data/lib/mongoid/max/denormalize/many_to_one.rb +47 -27
- data/lib/mongoid/max/denormalize/one_to_many.rb +11 -9
- data/lib/mongoid/max/denormalize/version.rb +1 -1
- data/lib/mongoid/max/denormalize.rb +3 -9
- data/spec/cases/existing_models_spec.rb +104 -0
- data/spec/cases/{song_and_notes_spec.rb → song_and_ratings_spec.rb} +6 -3
- data/spec/spec_helper.rb +2 -0
- metadata +5 -5
- data/spec/cases/existing_spec.rb +0 -61
data/README.md
CHANGED
@@ -6,8 +6,13 @@ It was designed for a minimum number of queries to the database.
|
|
6
6
|
|
7
7
|
For now, support only Mongoid 3.
|
8
8
|
|
9
|
-
*
|
10
|
-
*
|
9
|
+
* Denormalize fields
|
10
|
+
* Denormalize methods (only in One to Many situations for now)
|
11
|
+
* Denormalize `count` in Many to One situations
|
12
|
+
* Propagate only when needed:
|
13
|
+
* for fields: when there are actual changes
|
14
|
+
* for methods: always (we can't know in an inexpensive way what is the old value to figure out if there is a change)
|
15
|
+
* Take advantage of atomic operations on multiple documents of MongoDB
|
11
16
|
|
12
17
|
*This is a pre-version not suitable for production.*
|
13
18
|
|
@@ -34,6 +39,13 @@ Add `include Mongoid::Max::Denormalize` in your model and also:
|
|
34
39
|
denormalize relation, field_1, field_2 ... field_n, options
|
35
40
|
|
36
41
|
|
42
|
+
### Warming up
|
43
|
+
|
44
|
+
If there are existing records prior to the denormalization setup, you have to warm up. See below for each relation type.
|
45
|
+
|
46
|
+
Note: you can't warm up from both sides of the relation. Only the most efficient is available.
|
47
|
+
|
48
|
+
|
37
49
|
### One to Many
|
38
50
|
|
39
51
|
**Supported fields:** normal Mongoid fields, and methods.
|
@@ -58,7 +70,7 @@ Example :
|
|
58
70
|
include Mongoid::Document
|
59
71
|
include Mongoid::Max::Denormalize
|
60
72
|
|
61
|
-
|
73
|
+
belongs_to :post
|
62
74
|
denormalize :post, :title, :slug
|
63
75
|
end
|
64
76
|
|
@@ -72,6 +84,10 @@ Example :
|
|
72
84
|
@comment.post_title #=> "All Must Share The Burden"
|
73
85
|
@comment.post_slug #=> "all-must-share-the-burden"
|
74
86
|
|
87
|
+
To warm up the denormalization for an existing collection:
|
88
|
+
|
89
|
+
Post.denormalize_to_comments!
|
90
|
+
|
75
91
|
**Tips :** In your views, do not use `@comment.post` but `@comment.post_id` or `@comment.post_id?`
|
76
92
|
to avoid a query that checks/retrieve for the post. We want to avoid it, don't we ?
|
77
93
|
|
@@ -116,7 +132,7 @@ Example :
|
|
116
132
|
class Comment
|
117
133
|
include Mongoid::Document
|
118
134
|
|
119
|
-
|
135
|
+
belongs_to :post
|
120
136
|
|
121
137
|
field :rating
|
122
138
|
field :stuff
|
@@ -130,10 +146,14 @@ Example :
|
|
130
146
|
@post.comments_rating #=> [5, 3]
|
131
147
|
@post.comments_stuff #=> ["A", "B"]
|
132
148
|
|
149
|
+
To warm up the denormalization for an existing collection:
|
150
|
+
|
151
|
+
Post.denormalize_from_comments!
|
152
|
+
|
133
153
|
You can see that each denormalized field in stored in a separate array. This is wanted.
|
134
|
-
An option `:group` will come to allow :
|
154
|
+
An option `:group` will come to allow the way below (and maybe permit methods denormalization) :
|
135
155
|
|
136
|
-
@post.comments_fields #=> [{:rating => 5, :stuff => "A"},{:rating => 5, :stuff => "B"}]
|
156
|
+
@post.comments_fields #=> [{:rating => 5, :stuff => "A"}, {:rating => 5, :stuff => "B"}]
|
137
157
|
|
138
158
|
|
139
159
|
### Many to One
|
@@ -142,6 +162,16 @@ To come...
|
|
142
162
|
|
143
163
|
|
144
164
|
|
165
|
+
## Planned
|
166
|
+
|
167
|
+
* Support for Many to Many
|
168
|
+
* Support for `:group` option in Many to One
|
169
|
+
* Support for methods denormalization in Many to One (depends on `:group` option)
|
170
|
+
* Support for `:sum` and `:mean` options in Many to One
|
171
|
+
* Support for `:touch` option to "touch" an `updated_at` field (for cache purpose)
|
172
|
+
|
173
|
+
|
174
|
+
|
145
175
|
## Contributing
|
146
176
|
|
147
177
|
Contributions and bug reports are welcome.
|
@@ -13,8 +13,34 @@ module Mongoid
|
|
13
13
|
@inverse_meta = inverse_meta
|
14
14
|
@fields = fields
|
15
15
|
@options = options
|
16
|
+
|
17
|
+
verify
|
18
|
+
end
|
19
|
+
|
20
|
+
def verify
|
21
|
+
# There are fields
|
22
|
+
raise ConfigError.new("Nothing to denormalize", klass, relation) if fields.empty? && options.empty?
|
23
|
+
|
24
|
+
# All fields/methods are well defined
|
25
|
+
fields.each do |field|
|
26
|
+
unless meta.klass.instance_methods.include? field
|
27
|
+
raise ConfigError.new("Unknown field or method :#{field}", klass, relation)
|
28
|
+
end
|
29
|
+
end
|
30
|
+
|
31
|
+
# All options are allowed
|
32
|
+
unless unallowed_options.empty?
|
33
|
+
raise ConfigError.new("Unknown or not supported options :#{unallowed_options.first}", klass, relation)
|
34
|
+
end
|
16
35
|
end
|
17
36
|
|
37
|
+
def allowed_options
|
38
|
+
[]
|
39
|
+
end
|
40
|
+
|
41
|
+
def unallowed_options
|
42
|
+
options.keys - allowed_options
|
43
|
+
end
|
18
44
|
|
19
45
|
def relation
|
20
46
|
@meta.name
|
@@ -4,8 +4,8 @@ module Mongoid
|
|
4
4
|
module Denormalize
|
5
5
|
class ConfigError < ::StandardError
|
6
6
|
|
7
|
-
def initialize(summary, klass)
|
8
|
-
super("[
|
7
|
+
def initialize(summary, klass, relation=nil)
|
8
|
+
super("[%s.denormalize%s] %s" % [klass, relation && " :#{relation}", summary])
|
9
9
|
end
|
10
10
|
|
11
11
|
end
|
@@ -5,10 +5,17 @@ module Mongoid
|
|
5
5
|
|
6
6
|
class ManyToOne < Base
|
7
7
|
|
8
|
-
def
|
8
|
+
def verify
|
9
|
+
super
|
9
10
|
|
10
|
-
|
11
|
-
|
11
|
+
unless fields_methods.empty?
|
12
|
+
raise ConfigError.new("Methods denormalization not supported for Many to One", klass, relation)
|
13
|
+
end
|
14
|
+
end
|
15
|
+
|
16
|
+
def attach
|
17
|
+
fields_only.each do |field|
|
18
|
+
klass.field "#{relation}_#{field}", type: Array, default: []
|
12
19
|
end
|
13
20
|
|
14
21
|
if has_count?
|
@@ -16,26 +23,36 @@ module Mongoid
|
|
16
23
|
end
|
17
24
|
|
18
25
|
callback_code = <<EOM
|
19
|
-
|
26
|
+
before_create :denormalize_from_#{relation}
|
20
27
|
|
21
|
-
def denormalize_from_#{relation}
|
22
|
-
|
28
|
+
def denormalize_from_#{relation}(force=false)
|
29
|
+
#{relation}_retrieved = nil
|
23
30
|
|
24
|
-
fields = [#{Base.array_code_for(
|
25
|
-
|
26
|
-
|
27
|
-
|
28
|
-
|
29
|
-
|
30
|
-
|
31
|
-
self.send(:"#{relation}_\#{field}=", #{relation}.send(field))
|
31
|
+
fields = [#{Base.array_code_for(fields_only)}]
|
32
|
+
unless fields.empty?
|
33
|
+
#{relation}_retrieved = #{relation}.unscoped.to_a
|
34
|
+
if #{relation}_retrieved.count > 0
|
35
|
+
fields.each do |field|
|
36
|
+
self.send(:"#{relation}_\#{field}=", #{relation}_retrieved.map(&field).compact)
|
37
|
+
end
|
32
38
|
end
|
33
39
|
end
|
34
40
|
|
41
|
+
if #{has_count?}
|
42
|
+
self.#{relation}_count = #{relation}_retrieved.nil? ? #{relation}.unscoped.count : #{relation}_retrieved.count
|
43
|
+
end
|
44
|
+
|
35
45
|
true
|
36
46
|
end
|
47
|
+
|
48
|
+
def self.denormalize_from_#{relation}!
|
49
|
+
each do |obj|
|
50
|
+
obj.denormalize_from_#{relation}(true)
|
51
|
+
obj.save!
|
52
|
+
end
|
53
|
+
end
|
37
54
|
EOM
|
38
|
-
|
55
|
+
klass.class_eval callback_code
|
39
56
|
|
40
57
|
callback_code = <<EOM
|
41
58
|
around_save :denormalize_to_#{inverse_relation}
|
@@ -74,6 +91,8 @@ EOM
|
|
74
91
|
end
|
75
92
|
end
|
76
93
|
end
|
94
|
+
elsif #{inverse_meta.key}.nil?
|
95
|
+
changed_fields = []
|
77
96
|
else
|
78
97
|
changed_fields = fields & changed.map(&:to_sym)
|
79
98
|
changed_fields.each do |field|
|
@@ -82,11 +101,10 @@ EOM
|
|
82
101
|
end
|
83
102
|
end
|
84
103
|
|
85
|
-
yield
|
104
|
+
yield if block_given?
|
86
105
|
return if changed_fields.empty?
|
87
106
|
|
88
|
-
to_update = { "$set" => {}, "$inc" => {} }
|
89
|
-
to_push = {}
|
107
|
+
to_update = { "$set" => {}, "$inc" => {}, "$push" => {} }
|
90
108
|
to_get = {}
|
91
109
|
|
92
110
|
to_rem_fields = to_rem.reject {|k,v| v.nil?}.keys
|
@@ -94,7 +112,7 @@ EOM
|
|
94
112
|
|
95
113
|
# Those to add only
|
96
114
|
(to_add_only_fields = to_add_fields - to_rem_fields).each do |field|
|
97
|
-
|
115
|
+
to_update["$push"][field] = to_add[field]
|
98
116
|
end
|
99
117
|
|
100
118
|
to_set_fields = (to_add_fields + to_rem_fields - to_add_only_fields).uniq
|
@@ -116,14 +134,11 @@ EOM
|
|
116
134
|
to_update["$set"][field] = array
|
117
135
|
end
|
118
136
|
|
119
|
-
|
120
137
|
to_update["$inc"][:#{relation}_count] = 1 if #{has_count?} && (was_new || was_added)
|
121
138
|
to_update["$inc"][:#{relation}_count] = -1 if #{has_count?} && (was_removed)
|
122
139
|
|
140
|
+
to_update.reject! {|k,v| v.empty?}
|
123
141
|
#{klass}.collection.find(:_id => remote_id).update_all(to_update) unless to_update.empty?
|
124
|
-
|
125
|
-
|
126
|
-
#{klass}.collection.find(:_id => remote_id).update_all({"$push" => to_push}) unless to_push.empty?
|
127
142
|
end
|
128
143
|
|
129
144
|
def denormalize_to_#{inverse_relation}_old
|
@@ -136,7 +151,7 @@ EOM
|
|
136
151
|
to_rem[:"#{relation}_\#{field}"] = send(:"\#{field}_was")
|
137
152
|
end
|
138
153
|
|
139
|
-
to_update = { "$set" => {}, "$inc" => {} }
|
154
|
+
to_update = { "$set" => {}, "$inc" => {}, "$push" => {} }
|
140
155
|
to_get = {}
|
141
156
|
|
142
157
|
to_rem_fields = to_rem.reject {|k,v| v.nil?}.keys
|
@@ -159,6 +174,7 @@ EOM
|
|
159
174
|
|
160
175
|
to_update["$inc"][:#{relation}_count] = -1 if #{has_count?}
|
161
176
|
|
177
|
+
to_update.reject! {|k,v| v.empty?}
|
162
178
|
#{klass}.collection.find(:_id => remote_id).update_all(to_update) unless to_update.empty?
|
163
179
|
end
|
164
180
|
|
@@ -176,10 +192,9 @@ EOM
|
|
176
192
|
to_rem[:"#{relation}_\#{field}"] = send(field)
|
177
193
|
end
|
178
194
|
|
179
|
-
yield
|
195
|
+
yield if block_given?
|
180
196
|
|
181
|
-
to_update = { "$set" => {}, "$inc" => {} }
|
182
|
-
to_push = {}
|
197
|
+
to_update = { "$set" => {}, "$inc" => {}, "$push" => {} }
|
183
198
|
to_get = {}
|
184
199
|
|
185
200
|
to_rem_fields = to_rem.reject {|k,v| v.nil?}.keys
|
@@ -199,12 +214,17 @@ EOM
|
|
199
214
|
|
200
215
|
to_update["$inc"][:#{relation}_count] = -1 if #{has_count?}
|
201
216
|
|
217
|
+
to_update.reject! {|k,v| v.empty?}
|
202
218
|
#{klass}.collection.find(:_id => remote_id).update_all(to_update) unless to_update.empty?
|
203
219
|
end
|
204
220
|
EOM
|
205
221
|
meta.klass.class_eval callback_code
|
206
222
|
end
|
207
223
|
|
224
|
+
def allowed_options
|
225
|
+
super + [:count]
|
226
|
+
end
|
227
|
+
|
208
228
|
def has_count?
|
209
229
|
!options[:count].nil?
|
210
230
|
end
|
@@ -6,7 +6,6 @@ module Mongoid
|
|
6
6
|
class OneToMany < Base
|
7
7
|
|
8
8
|
def attach
|
9
|
-
|
10
9
|
fields.each do |field|
|
11
10
|
field_meta = meta.klass.fields[field.to_s]
|
12
11
|
klass.field "#{relation}_#{field}", type: field_meta.try(:type)
|
@@ -37,15 +36,15 @@ EOM
|
|
37
36
|
callback_code = <<EOM
|
38
37
|
around_save :denormalize_to_#{inverse_relation}
|
39
38
|
|
40
|
-
def denormalize_to_#{inverse_relation}
|
41
|
-
return unless changed?
|
39
|
+
def denormalize_to_#{inverse_relation}(force = false)
|
40
|
+
return unless changed? || force
|
42
41
|
|
43
42
|
fields = [#{Base.array_code_for(fields)}]
|
44
43
|
fields_only = [#{Base.array_code_for(fields_only)}]
|
45
44
|
methods = [#{Base.array_code_for(fields_methods)}]
|
46
|
-
changed_fields = fields_only & changed.map(&:to_sym)
|
45
|
+
changed_fields = force ? fields_only.dup : (fields_only & changed.map(&:to_sym))
|
47
46
|
|
48
|
-
yield
|
47
|
+
yield if block_given?
|
49
48
|
|
50
49
|
return if changed_fields.count == 0
|
51
50
|
|
@@ -57,12 +56,18 @@ EOM
|
|
57
56
|
#{inverse_relation}.update to_set
|
58
57
|
end
|
59
58
|
|
59
|
+
def self.denormalize_to_#{inverse_relation}!
|
60
|
+
each do |obj|
|
61
|
+
obj.denormalize_to_#{inverse_relation}(true)
|
62
|
+
end
|
63
|
+
end
|
64
|
+
|
60
65
|
around_destroy :denormalize_to_#{inverse_relation}_destroy
|
61
66
|
|
62
67
|
def denormalize_to_#{inverse_relation}_destroy
|
63
68
|
fields = [#{Base.array_code_for(fields)}]
|
64
69
|
|
65
|
-
yield
|
70
|
+
yield if block_given?
|
66
71
|
|
67
72
|
to_set = {}
|
68
73
|
fields.each do |field|
|
@@ -73,9 +78,6 @@ EOM
|
|
73
78
|
end
|
74
79
|
EOM
|
75
80
|
meta.klass.class_eval callback_code
|
76
|
-
|
77
|
-
|
78
|
-
|
79
81
|
end
|
80
82
|
|
81
83
|
end
|
@@ -20,26 +20,20 @@ module Mongoid
|
|
20
20
|
# puts "#options : #{options.inspect}"
|
21
21
|
|
22
22
|
meta = self.relations[relation.to_s]
|
23
|
-
raise ConfigError.new("Unknown relation
|
23
|
+
raise ConfigError.new("Unknown relation", self, relation) if meta.nil?
|
24
24
|
# puts "# meta : #{meta.inspect}"
|
25
25
|
|
26
26
|
inverse_meta = meta.klass.relations[meta.inverse.to_s]
|
27
|
-
raise ConfigError.new("Unknown inverse relation
|
27
|
+
raise ConfigError.new("Unknown inverse relation", self, relation) if inverse_meta.nil?
|
28
28
|
# puts "#inverse_meta : #{inverse_meta.inspect}"
|
29
29
|
|
30
|
-
methods = []
|
31
|
-
fields.each do |field|
|
32
|
-
unless meta.klass.instance_methods.include? field
|
33
|
-
raise ConfigError.new("Unknown field or method :#{field} in :#{relation}", self)
|
34
|
-
end
|
35
|
-
end
|
36
30
|
|
37
31
|
if meta.relation == Mongoid::Relations::Referenced::In && inverse_meta.relation == Mongoid::Relations::Referenced::Many
|
38
32
|
OneToMany.new(self, meta, inverse_meta, fields, options).attach
|
39
33
|
elsif meta.relation == Mongoid::Relations::Referenced::Many && inverse_meta.relation == Mongoid::Relations::Referenced::In
|
40
34
|
ManyToOne.new(self, meta, inverse_meta, fields, options).attach
|
41
35
|
else
|
42
|
-
raise ConfigError.new("Relation not supported
|
36
|
+
raise ConfigError.new("Relation not supported", self, relation)
|
43
37
|
end
|
44
38
|
|
45
39
|
end
|
@@ -0,0 +1,104 @@
|
|
1
|
+
# encoding: utf-8
|
2
|
+
require 'spec_helper'
|
3
|
+
|
4
|
+
#
|
5
|
+
# The case
|
6
|
+
#
|
7
|
+
class Author
|
8
|
+
include Mongoid::Document
|
9
|
+
|
10
|
+
field :name, type: String
|
11
|
+
|
12
|
+
has_many :books
|
13
|
+
end
|
14
|
+
|
15
|
+
class Book
|
16
|
+
include Mongoid::Document
|
17
|
+
include Mongoid::Max::Denormalize
|
18
|
+
|
19
|
+
field :name, type: String
|
20
|
+
|
21
|
+
def slug
|
22
|
+
name.try(:parameterize)
|
23
|
+
end
|
24
|
+
|
25
|
+
belongs_to :author
|
26
|
+
|
27
|
+
has_many :reviews
|
28
|
+
end
|
29
|
+
|
30
|
+
class Review
|
31
|
+
include Mongoid::Document
|
32
|
+
include Mongoid::Max::Denormalize
|
33
|
+
|
34
|
+
belongs_to :book
|
35
|
+
|
36
|
+
field :rating, type: Integer
|
37
|
+
end
|
38
|
+
|
39
|
+
def reload!
|
40
|
+
[@author, @book, @review_1, @review_2].each(&:reload)
|
41
|
+
end
|
42
|
+
|
43
|
+
#
|
44
|
+
# The specs
|
45
|
+
#
|
46
|
+
describe "Case: Existing models" do
|
47
|
+
before(:each) do
|
48
|
+
@author = Author.create!(name: "Michael Crichton")
|
49
|
+
@book = Book.create!(name: "Jurassic Park", author: @author)
|
50
|
+
@review_1 = Review.create!(book: @book, rating: 4)
|
51
|
+
@review_2 = Review.create!(book: @book, rating: 5)
|
52
|
+
|
53
|
+
reload!
|
54
|
+
end
|
55
|
+
|
56
|
+
context "when defining the denormalization for Authors in Books" do
|
57
|
+
before { Book.denormalize :author, :name }
|
58
|
+
|
59
|
+
it "Authors denormalized fields should fill" do
|
60
|
+
@book.author_name.should be_nil
|
61
|
+
|
62
|
+
Author.denormalize_to_books!
|
63
|
+
reload!
|
64
|
+
|
65
|
+
@book.author_name.should eq("Michael Crichton")
|
66
|
+
end
|
67
|
+
end
|
68
|
+
|
69
|
+
context "when defining the denormalization for Books in Reviews" do
|
70
|
+
before { Review.denormalize :book, :name, :slug }
|
71
|
+
|
72
|
+
it "Books denormalized fields should fill" do
|
73
|
+
[@review_1, @review_2].each do |review|
|
74
|
+
review.book_name.should be_nil
|
75
|
+
review.book_slug.should be_nil
|
76
|
+
end
|
77
|
+
|
78
|
+
Book.denormalize_to_reviews!
|
79
|
+
reload!
|
80
|
+
|
81
|
+
[@review_1, @review_2].each do |review|
|
82
|
+
review.book_name.should eq("Jurassic Park")
|
83
|
+
review.book_slug.should eq("jurassic-park")
|
84
|
+
end
|
85
|
+
end
|
86
|
+
end
|
87
|
+
|
88
|
+
context "when defining the denormalization for Reviews in Books" do
|
89
|
+
before { Book.denormalize :reviews, :rating, :count => true }
|
90
|
+
|
91
|
+
it "Reviews denormalized fields should fill" do
|
92
|
+
@book.reviews_count.should be_nil
|
93
|
+
@book.reviews_rating.should be_nil
|
94
|
+
|
95
|
+
Book.denormalize_from_reviews!
|
96
|
+
reload!
|
97
|
+
|
98
|
+
@book.reviews_count.should eq 2
|
99
|
+
@book.reviews_rating.should eq [4, 5]
|
100
|
+
end
|
101
|
+
end
|
102
|
+
|
103
|
+
end
|
104
|
+
|
@@ -9,6 +9,7 @@ class Rating
|
|
9
9
|
|
10
10
|
field :note, type: Integer
|
11
11
|
field :comment, type: String
|
12
|
+
field :upset_level, type: Integer
|
12
13
|
|
13
14
|
belongs_to :song
|
14
15
|
end
|
@@ -19,7 +20,8 @@ class Song
|
|
19
20
|
|
20
21
|
has_many :ratings
|
21
22
|
|
22
|
-
denormalize :ratings, :note, :comment, count: true, mean: [:note]
|
23
|
+
#denormalize :ratings, :note, :comment, count: true, mean: [:note]
|
24
|
+
denormalize :ratings, :note, :comment, :upset_level, count: true
|
23
25
|
end
|
24
26
|
|
25
27
|
|
@@ -55,12 +57,12 @@ describe "Case: a song and his ratings" do
|
|
55
57
|
its(:ratings_count) { should eq 1 }
|
56
58
|
its(:ratings_note) { should eq [5] }
|
57
59
|
its(:ratings_comment) { should eq ["Good!"] }
|
58
|
-
|
59
|
-
# its(:ratings_mean) { should eq 5 }
|
60
|
+
its(:ratings_upset_level) { should eq [] }
|
60
61
|
|
61
62
|
context "when modifing the first rating (=4)" do
|
62
63
|
before do
|
63
64
|
@rating.note = 4
|
65
|
+
@rating.upset_level = 0
|
64
66
|
@rating.save!
|
65
67
|
@song.reload
|
66
68
|
end
|
@@ -69,6 +71,7 @@ describe "Case: a song and his ratings" do
|
|
69
71
|
its(:ratings_count) { should eq 1 }
|
70
72
|
its(:ratings_note) { should eq [4] }
|
71
73
|
its(:ratings_comment) { should eq ["Good!"] }
|
74
|
+
its(:ratings_upset_level) { should eq [0] }
|
72
75
|
end
|
73
76
|
|
74
77
|
context "when adding an other rating (=5)" do
|
data/spec/spec_helper.rb
CHANGED
metadata
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: mongoid_max_denormalize
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.0.
|
4
|
+
version: 0.0.3
|
5
5
|
prerelease:
|
6
6
|
platform: ruby
|
7
7
|
authors:
|
@@ -94,10 +94,10 @@ files:
|
|
94
94
|
- lib/mongoid/max/denormalize/base.rb
|
95
95
|
- lib/mongoid/max/denormalize.rb
|
96
96
|
- spec/lib/mongoid_max_denormalize_spec.rb
|
97
|
-
- spec/cases/
|
97
|
+
- spec/cases/song_and_ratings_spec.rb
|
98
|
+
- spec/cases/existing_models_spec.rb
|
98
99
|
- spec/cases/contact_and_addresses_spec.rb
|
99
100
|
- spec/cases/post_and_comments_spec.rb
|
100
|
-
- spec/cases/song_and_notes_spec.rb
|
101
101
|
- spec/spec_helper.rb
|
102
102
|
homepage: http://github.com/maximeg/mongoid_max_denormalize
|
103
103
|
licenses: []
|
@@ -125,8 +125,8 @@ specification_version: 3
|
|
125
125
|
summary: MaxMapper, polyvalent ORM for Rails
|
126
126
|
test_files:
|
127
127
|
- spec/lib/mongoid_max_denormalize_spec.rb
|
128
|
-
- spec/cases/
|
128
|
+
- spec/cases/song_and_ratings_spec.rb
|
129
|
+
- spec/cases/existing_models_spec.rb
|
129
130
|
- spec/cases/contact_and_addresses_spec.rb
|
130
131
|
- spec/cases/post_and_comments_spec.rb
|
131
|
-
- spec/cases/song_and_notes_spec.rb
|
132
132
|
- spec/spec_helper.rb
|
data/spec/cases/existing_spec.rb
DELETED
@@ -1,61 +0,0 @@
|
|
1
|
-
# encoding: utf-8
|
2
|
-
require 'spec_helper'
|
3
|
-
|
4
|
-
#
|
5
|
-
# The case
|
6
|
-
#
|
7
|
-
class Author
|
8
|
-
include Mongoid::Document
|
9
|
-
|
10
|
-
field :name, type: String
|
11
|
-
|
12
|
-
has_many :books
|
13
|
-
end
|
14
|
-
|
15
|
-
class Book
|
16
|
-
include Mongoid::Document
|
17
|
-
include Mongoid::Max::Denormalize
|
18
|
-
|
19
|
-
field :name, type: String
|
20
|
-
|
21
|
-
belongs_to :author
|
22
|
-
|
23
|
-
has_many :reviews
|
24
|
-
end
|
25
|
-
|
26
|
-
class Review
|
27
|
-
include Mongoid::Document
|
28
|
-
include Mongoid::Max::Denormalize
|
29
|
-
|
30
|
-
belongs_to :book
|
31
|
-
|
32
|
-
field :rating, type: Integer
|
33
|
-
end
|
34
|
-
|
35
|
-
#
|
36
|
-
# The specs
|
37
|
-
#
|
38
|
-
describe "Case: Existing" do
|
39
|
-
|
40
|
-
before do
|
41
|
-
@author = Author.create!(name: "Michael Crichton")
|
42
|
-
@book = Book.create!(name: "Jurassic Park", author: @author)
|
43
|
-
@review_1 = Review.create!(book: @book, rating: 4)
|
44
|
-
@review_2 = Review.create!(book: @book, rating: 5)
|
45
|
-
end
|
46
|
-
|
47
|
-
context "when defining the denormalization" do
|
48
|
-
before do
|
49
|
-
Book.denormalize :author, :name
|
50
|
-
Book.denormalize :reviews, :rating, :count => true
|
51
|
-
Review.denormalize :book, :name
|
52
|
-
end
|
53
|
-
|
54
|
-
it "denormalization should be empty" do
|
55
|
-
|
56
|
-
end
|
57
|
-
|
58
|
-
end
|
59
|
-
|
60
|
-
end
|
61
|
-
|