mongoid 0.11.6 → 0.11.7

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/HISTORY CHANGED
@@ -1,3 +1,16 @@
1
+ === 0.11.7
2
+ - Added #sum to criteria which takes a single field
3
+ to aggregate on. Example: Person.sum(:age) would
4
+ return a float that was the sum of all people's
5
+ ages in the db.
6
+
7
+ - Fixed issue with queries from parent classes always
8
+ casting the returned documents to the parent.
9
+
10
+ - Fixed singleton require issue.
11
+
12
+ - Group queries now run as db commands
13
+
1
14
  === 0.11.6
2
15
  - Allow namespaced documents to default with:
3
16
  "namespace_modelname"
data/VERSION CHANGED
@@ -1 +1 @@
1
- 0.11.6
1
+ 0.11.7
@@ -28,6 +28,7 @@ gem "leshill-will_paginate", ">= 2.3.11"
28
28
 
29
29
  require "delegate"
30
30
  require "observer"
31
+ require "singleton"
31
32
  require "time"
32
33
  require "validatable"
33
34
  require "active_support/callbacks"
@@ -48,6 +49,7 @@ require "mongoid/extensions"
48
49
  require "mongoid/errors"
49
50
  require "mongoid/field"
50
51
  require "mongoid/finders"
52
+ require "mongoid/memoization"
51
53
  require "mongoid/timestamps"
52
54
  require "mongoid/versioning"
53
55
  require "mongoid/document"
@@ -11,6 +11,10 @@ module Mongoid # :nodoc:
11
11
  module Associations #:nodoc:
12
12
  def self.included(base)
13
13
  base.class_eval do
14
+ # Associations need to inherit down the chain.
15
+ class_inheritable_accessor :associations
16
+ self.associations = {}.with_indifferent_access
17
+
14
18
  include InstanceMethods
15
19
  extend ClassMethods
16
20
  end
@@ -35,9 +39,6 @@ module Mongoid # :nodoc:
35
39
  end
36
40
 
37
41
  module ClassMethods
38
- def associations
39
- @associations ||= {}.with_indifferent_access
40
- end
41
42
  # Adds the association back to the parent document. This macro is
42
43
  # necessary to set the references from the child back to the parent
43
44
  # document. If a child does not define this association calling
@@ -198,22 +199,16 @@ module Mongoid # :nodoc:
198
199
 
199
200
  protected
200
201
  # Adds the association to the associations hash with the type as the key,
201
- # then adds the accessors for the association.
202
+ # then adds the accessors for the association. The defined setters and
203
+ # getters for the associations will perform the necessary memoization.
202
204
  def add_association(type, options)
203
205
  name = options.name
204
206
  associations[name] = type
205
207
  define_method(name) do
206
- return instance_variable_get("@#{name}") if instance_variable_defined?("@#{name}")
207
- proxy = type.instantiate(self, options)
208
- instance_variable_set("@#{name}", proxy)
208
+ memoized(name) { type.instantiate(self, options) }
209
209
  end
210
210
  define_method("#{name}=") do |object|
211
- proxy = type.update(object, self, options)
212
- if instance_variable_defined?("@#{name}")
213
- remove_instance_variable("@#{name}")
214
- else
215
- instance_variable_set("@#{name}", proxy)
216
- end
211
+ reset(name) { type.update(object, self, options) }
217
212
  end
218
213
  end
219
214
  end
@@ -48,9 +48,8 @@ module Mongoid #:nodoc:
48
48
  # Example:
49
49
  #
50
50
  # <tt>criteria.select(:field1).where(:field1 => "Title").aggregate(Person)</tt>
51
- def aggregate(klass = nil)
52
- @klass = klass if klass
53
- @klass.collection.group(@options[:fields], @selector, { :count => 0 }, AGGREGATE_REDUCE)
51
+ def aggregate
52
+ @klass.collection.group(@options[:fields], @selector, { :count => 0 }, AGGREGATE_REDUCE, true)
54
53
  end
55
54
 
56
55
  # Adds a criterion to the +Criteria+ that specifies values that must all
@@ -165,9 +164,13 @@ module Mongoid #:nodoc:
165
164
  @options[:fields],
166
165
  @selector,
167
166
  { :group => [] },
168
- GROUP_REDUCE
167
+ GROUP_REDUCE,
168
+ true
169
169
  ).collect do |docs|
170
- docs["group"] = docs["group"].collect { |attrs| @klass.instantiate(attrs) }; docs
170
+ docs["group"] = docs["group"].collect do |attrs|
171
+ attrs["_type"].constantize.instantiate(attrs)
172
+ end
173
+ docs
171
174
  end
172
175
  end
173
176
 
@@ -230,7 +233,7 @@ module Mongoid #:nodoc:
230
233
  sorting = [[:_id, :asc]] unless sorting
231
234
  opts[:sort] = sorting.collect { |option| [ option[0], option[1].invert ] }
232
235
  attributes = @klass.collection.find_one(@selector, opts)
233
- attributes ? @klass.instantiate(attributes) : nil
236
+ attributes ? attributes["_type"].constantize.instantiate(attributes) : nil
234
237
  end
235
238
 
236
239
  # Adds a criterion to the +Criteria+ that specifies the maximum number of
@@ -338,7 +341,7 @@ module Mongoid #:nodoc:
338
341
  # <tt>Criteria.select(:name).where(:name = "Chrissy").one</tt>
339
342
  def one
340
343
  attributes = @klass.collection.find_one(@selector, @options.dup)
341
- attributes ? @klass.instantiate(attributes) : nil
344
+ attributes ? attributes["_type"].constantize.instantiate(attributes) : nil
342
345
  end
343
346
 
344
347
  alias :first :one
@@ -418,6 +421,26 @@ module Mongoid #:nodoc:
418
421
  @options[:skip] = value; self
419
422
  end
420
423
 
424
+ SUM_REDUCE = "function(obj, prev) { prev.sum += obj.[field]; }"
425
+ # Sum the criteria. This will take the internally built selector and options
426
+ # and pass them on to the Ruby driver's +group()+ method on the collection. The
427
+ # collection itself will be retrieved from the class provided, and once the
428
+ # query has returned it will provided a grouping of keys with sums.
429
+ #
430
+ # Example:
431
+ #
432
+ # <tt>criteria.select(:field1).where(:field1 => "Title").sum</tt>
433
+ def sum(field)
434
+ collection = @klass.collection.group(
435
+ @options[:fields],
436
+ @selector,
437
+ { :sum => 0 },
438
+ SUM_REDUCE.gsub("[field]", field.to_s),
439
+ true
440
+ )
441
+ collection.first["sum"]
442
+ end
443
+
421
444
  # Translate the supplied arguments into a +Criteria+ object.
422
445
  #
423
446
  # If the passed in args is a single +String+, then it will
@@ -490,7 +513,7 @@ module Mongoid #:nodoc:
490
513
  attributes = @klass.collection.find(@selector, @options.dup)
491
514
  if attributes
492
515
  @count = attributes.count
493
- attributes.collect { |doc| @klass.instantiate(doc) }
516
+ attributes.collect { |doc| doc["_type"].constantize.instantiate(doc) }
494
517
  else
495
518
  []
496
519
  end
@@ -4,7 +4,7 @@ module Mongoid #:nodoc:
4
4
  def self.included(base)
5
5
  base.class_eval do
6
6
  include ActiveSupport::Callbacks
7
- include Associations, Attributes, Commands, Observable, Validatable
7
+ include Associations, Attributes, Commands, Memoization, Observable, Validatable
8
8
  include InstanceMethods
9
9
 
10
10
  extend ClassMethods
@@ -128,6 +128,22 @@ module Mongoid #:nodoc:
128
128
  Criteria.new(self).only(*args)
129
129
  end
130
130
 
131
+ # Convenience method for returning the sum of a specified field for all
132
+ # documents in the database.
133
+ #
134
+ # Options:
135
+ #
136
+ # field: The field to use when calculating the sum.
137
+ #
138
+ # Example:
139
+ #
140
+ # <tt>Person.sum(:age)</tt>
141
+ #
142
+ # Returns: <tt>Float</tt> of the sum.
143
+ def sum(field)
144
+ Criteria.new(self).sum(field)
145
+ end
146
+
131
147
  # Entry point for creating a new criteria from a Document. This will
132
148
  # instantiate a new +Criteria+ object with the supplied select criterion
133
149
  # already added to it.
@@ -0,0 +1,27 @@
1
+ module Mongoid #:nodoc
2
+ module Memoization
3
+
4
+ # Handles cases when accessing an association that should be memoized in
5
+ # the Mongoid specific manner.
6
+ def memoized(name, &block)
7
+ var = "@#{name}"
8
+ if instance_variable_defined?(var)
9
+ return instance_variable_get(var)
10
+ end
11
+ value = yield
12
+ instance_variable_set(var, value)
13
+ end
14
+
15
+ # Mongoid specific behavior is to remove the memoized object when setting
16
+ # the association, or if it wasn't previously memoized it will get set.
17
+ def reset(name, &block)
18
+ var = "@#{name}"
19
+ value = yield
20
+ if instance_variable_defined?(var)
21
+ remove_instance_variable(var)
22
+ else
23
+ instance_variable_set(var, value)
24
+ end
25
+ end
26
+ end
27
+ end
@@ -5,11 +5,11 @@
5
5
 
6
6
  Gem::Specification.new do |s|
7
7
  s.name = %q{mongoid}
8
- s.version = "0.11.6"
8
+ s.version = "0.11.7"
9
9
 
10
10
  s.required_rubygems_version = Gem::Requirement.new(">= 0") if s.respond_to? :required_rubygems_version=
11
11
  s.authors = ["Durran Jordan"]
12
- s.date = %q{2010-01-05}
12
+ s.date = %q{2010-01-06}
13
13
  s.email = %q{durran@gmail.com}
14
14
  s.extra_rdoc_files = [
15
15
  "README.textile"
@@ -68,6 +68,7 @@ Gem::Specification.new do |s|
68
68
  "lib/mongoid/extensions/time/conversions.rb",
69
69
  "lib/mongoid/field.rb",
70
70
  "lib/mongoid/finders.rb",
71
+ "lib/mongoid/memoization.rb",
71
72
  "lib/mongoid/timestamps.rb",
72
73
  "lib/mongoid/versioning.rb",
73
74
  "mongoid.gemspec",
@@ -121,6 +122,7 @@ Gem::Specification.new do |s|
121
122
  "spec/unit/mongoid/extensions/time/conversions_spec.rb",
122
123
  "spec/unit/mongoid/field_spec.rb",
123
124
  "spec/unit/mongoid/finders_spec.rb",
125
+ "spec/unit/mongoid/memoization_spec.rb",
124
126
  "spec/unit/mongoid/timestamps_spec.rb",
125
127
  "spec/unit/mongoid/versioning_spec.rb",
126
128
  "spec/unit/mongoid_spec.rb"
@@ -179,6 +181,7 @@ Gem::Specification.new do |s|
179
181
  "spec/unit/mongoid/extensions/time/conversions_spec.rb",
180
182
  "spec/unit/mongoid/field_spec.rb",
181
183
  "spec/unit/mongoid/finders_spec.rb",
184
+ "spec/unit/mongoid/memoization_spec.rb",
182
185
  "spec/unit/mongoid/timestamps_spec.rb",
183
186
  "spec/unit/mongoid/versioning_spec.rb",
184
187
  "spec/unit/mongoid_spec.rb"
@@ -1,5 +1,6 @@
1
1
  require "rubygems"
2
2
  require "ruby-prof"
3
+ require "benchmark"
3
4
  require "mongoid"
4
5
 
5
6
  connection = Mongo::Connection.new
@@ -10,7 +11,6 @@ Mongoid.database.collection("people").drop
10
11
  class Person
11
12
  include Mongoid::Document
12
13
  include Mongoid::Timestamps
13
- include Mongoid::Versioning
14
14
  field :birth_date, :type => Date
15
15
  has_one :name
16
16
  has_one :address
@@ -19,7 +19,6 @@ end
19
19
 
20
20
  class Name
21
21
  include Mongoid::Document
22
- include Mongoid::Timestamps
23
22
  field :given
24
23
  field :family
25
24
  field :middle
@@ -28,7 +27,6 @@ end
28
27
 
29
28
  class Address
30
29
  include Mongoid::Document
31
- include Mongoid::Timestamps
32
30
  field :street
33
31
  field :city
34
32
  field :state
@@ -39,36 +37,39 @@ end
39
37
 
40
38
  class Phone
41
39
  include Mongoid::Document
42
- include Mongoid::Timestamps
43
40
  field :country_code, :type => Integer
44
41
  field :number
45
42
  field :phone_type
46
43
  belongs_to :person, :inverse_of => :phones
47
44
  end
48
45
 
49
- RubyProf.start
46
+ # RubyProf.start
50
47
 
51
48
  puts "Starting benchmark..."
52
49
 
53
- 1000.times do |n|
54
- person = Person.new(:birth_date => Date.new(1970, 1, 1))
55
- name = Name.new(:given => "James", :family => "Kirk", :middle => "Tiberius")
56
- address = Address.new(
57
- :street => "1 Starfleet Command Way",
58
- :city => "San Francisco",
59
- :state => "CA",
60
- :post_code => "94133",
61
- :type => "Work"
62
- )
63
- phone = Phone.new(:country_code => 1, :number => "415-555-1212", :type => "Mobile")
64
- person.name = name
65
- person.address = address
66
- person.phones << phone
67
- person.save
50
+ Benchmark.bm do |bm|
51
+ bm.report("Mongoid") do
52
+ 10000.times do |n|
53
+ person = Person.new(:birth_date => Date.new(1970, 1, 1))
54
+ name = Name.new(:given => "James", :family => "Kirk", :middle => "Tiberius")
55
+ address = Address.new(
56
+ :street => "1 Starfleet Command Way",
57
+ :city => "San Francisco",
58
+ :state => "CA",
59
+ :post_code => "94133",
60
+ :type => "Work"
61
+ )
62
+ phone = Phone.new(:country_code => 1, :number => "415-555-1212", :type => "Mobile")
63
+ person.name = name
64
+ person.address = address
65
+ person.phones << phone
66
+ person.save
67
+ end
68
+ end
68
69
  end
69
70
 
70
- result = RubyProf.stop
71
- printer = RubyProf::FlatPrinter.new(result)
72
- printer.print(STDOUT, 0)
71
+ # result = RubyProf.stop
72
+ # printer = RubyProf::FlatPrinter.new(result)
73
+ # printer.print(STDOUT, 0)
73
74
 
74
75
  # Mongoid.database.collection("people").drop
@@ -2,16 +2,34 @@ require "spec_helper"
2
2
 
3
3
  describe Mongoid::Criteria do
4
4
 
5
- before do
6
- @person = Person.create(:title => "Sir", :age => 33, :aliases => ["D", "Durran"])
7
- end
5
+ describe "#sum" do
6
+
7
+ before do
8
+ 10.times do |n|
9
+ Person.create(:title => "Sir", :age => 5, :aliases => ["D", "Durran"])
10
+ end
11
+ end
12
+
13
+ after do
14
+ Person.delete_all
15
+ end
16
+
17
+ it "provides sums for all the fields provided" do
18
+ Person.where(:age.gt => 3).sum(:age).should == 50.0
19
+ end
8
20
 
9
- after do
10
- Person.delete_all
11
21
  end
12
22
 
13
23
  describe "#where" do
14
24
 
25
+ before do
26
+ @person = Person.create(:title => "Sir", :age => 33, :aliases => ["D", "Durran"])
27
+ end
28
+
29
+ after do
30
+ Person.delete_all
31
+ end
32
+
15
33
  context "with complex criterion" do
16
34
 
17
35
  context "#all" do
@@ -87,6 +87,24 @@ describe Mongoid::Document do
87
87
 
88
88
  end
89
89
 
90
+ context "when document has subclasses" do
91
+
92
+ before do
93
+ @firefox = Firefox.create(:name => "firefox")
94
+ end
95
+
96
+ after do
97
+ Firefox.delete_all
98
+ end
99
+
100
+ it "returns subclasses for querying parents" do
101
+ firefox = Canvas.where(:name => "firefox").first
102
+ firefox.should be_a_kind_of(Firefox)
103
+ firefox.should == @firefox
104
+ end
105
+
106
+ end
107
+
90
108
  context "deleting subclasses" do
91
109
 
92
110
  before do
@@ -104,6 +104,7 @@ describe Mongoid::Attributes do
104
104
  context "when allowing dynamic fields" do
105
105
 
106
106
  before do
107
+ Mongoid.allow_dynamic_fields = true
107
108
  @person = Person.new(@attributes)
108
109
  end
109
110
 
@@ -4,6 +4,7 @@ describe Mongoid::Criteria do
4
4
 
5
5
  before do
6
6
  @criteria = Mongoid::Criteria.new(Person)
7
+ @canvas_criteria = Mongoid::Criteria.new(Canvas)
7
8
  end
8
9
 
9
10
  describe "#[]" do
@@ -32,22 +33,6 @@ describe Mongoid::Criteria do
32
33
 
33
34
  describe "#aggregate" do
34
35
 
35
- context "when klass provided" do
36
-
37
- before do
38
- @reduce = "function(obj, prev) { prev.count++; }"
39
- @criteria = Mongoid::Criteria.new(Person)
40
- @collection = mock
41
- Person.expects(:collection).returns(@collection)
42
- end
43
-
44
- it "calls group on the collection with the aggregate js" do
45
- @collection.expects(:group).with([:field1], {:_type => { "$in" => ["Doctor", "Person"] }}, {:count => 0}, @reduce)
46
- @criteria.only(:field1).aggregate
47
- end
48
-
49
- end
50
-
51
36
  context "when klass not provided" do
52
37
 
53
38
  before do
@@ -57,8 +42,8 @@ describe Mongoid::Criteria do
57
42
  end
58
43
 
59
44
  it "calls group on the collection with the aggregate js" do
60
- @collection.expects(:group).with([:field1], {:_type => { "$in" => ["Doctor", "Person"] }}, {:count => 0}, @reduce)
61
- @criteria.only(:field1).aggregate(Person)
45
+ @collection.expects(:group).with([:field1], {:_type => { "$in" => ["Doctor", "Person"] }}, {:count => 0}, @reduce, true)
46
+ @criteria.only(:field1).aggregate
62
47
  end
63
48
 
64
49
  end
@@ -246,7 +231,9 @@ describe Mongoid::Criteria do
246
231
  before do
247
232
  @collection = mock
248
233
  Person.expects(:collection).returns(@collection)
249
- @collection.expects(:find_one).with(@criteria.selector, @criteria.options).returns({ :title => "Sir" })
234
+ @collection.expects(:find_one).with(@criteria.selector, @criteria.options).returns(
235
+ { "title" => "Sir", "_type" => "Person" }
236
+ )
250
237
  end
251
238
 
252
239
  it "calls find on the collection with the selector and options" do
@@ -271,6 +258,23 @@ describe Mongoid::Criteria do
271
258
 
272
259
  end
273
260
 
261
+ context "when document is a subclass of the class queried from" do
262
+
263
+ before do
264
+ @collection = mock
265
+ Canvas.expects(:collection).returns(@collection)
266
+ @collection.expects(:find_one).with(@canvas_criteria.selector, @canvas_criteria.options).returns(
267
+ { "name" => "Firefox", "_type" => "Firefox" }
268
+ )
269
+ end
270
+
271
+ it "instantiates the subclass" do
272
+ criteria = Mongoid::Criteria.new(Canvas)
273
+ criteria.first.should be_a_kind_of(Firefox)
274
+ end
275
+
276
+ end
277
+
274
278
  end
275
279
 
276
280
  describe "#excludes" do
@@ -335,7 +339,7 @@ describe Mongoid::Criteria do
335
339
  describe "#group" do
336
340
 
337
341
  before do
338
- @grouping = [{ "title" => "Sir", "group" => [{ "title" => "Sir", "age" => 30 }] }]
342
+ @grouping = [{ "title" => "Sir", "group" => [{ "title" => "Sir", "age" => 30, "_type" => "Person" }] }]
339
343
  end
340
344
 
341
345
  context "when klass provided" do
@@ -348,7 +352,7 @@ describe Mongoid::Criteria do
348
352
  end
349
353
 
350
354
  it "calls group on the collection with the aggregate js" do
351
- @collection.expects(:group).with([:field1], {:_type => { "$in" => ["Doctor", "Person"] }}, {:group => []}, @reduce).returns(@grouping)
355
+ @collection.expects(:group).with([:field1], {:_type => { "$in" => ["Doctor", "Person"] }}, {:group => []}, @reduce, true).returns(@grouping)
352
356
  @criteria.only(:field1).group
353
357
  end
354
358
 
@@ -363,7 +367,7 @@ describe Mongoid::Criteria do
363
367
  end
364
368
 
365
369
  it "calls group on the collection with the aggregate js" do
366
- @collection.expects(:group).with([:field1], {:_type => { "$in" => ["Doctor", "Person"] }}, {:group => []}, @reduce).returns(@grouping)
370
+ @collection.expects(:group).with([:field1], {:_type => { "$in" => ["Doctor", "Person"] }}, {:group => []}, @reduce, true).returns(@grouping)
367
371
  @criteria.only(:field1).group
368
372
  end
369
373
 
@@ -415,7 +419,9 @@ describe Mongoid::Criteria do
415
419
  before do
416
420
  @collection = mock
417
421
  Person.expects(:collection).returns(@collection)
418
- @collection.expects(:find_one).with(@criteria.selector, { :sort => [[:title, :desc]] }).returns({ :title => "Sir" })
422
+ @collection.expects(:find_one).with(@criteria.selector, { :sort => [[:title, :desc]] }).returns(
423
+ { "title" => "Sir", "_type" => "Person" }
424
+ )
419
425
  end
420
426
 
421
427
  it "calls find on the collection with the selector and sort options reversed" do
@@ -446,7 +452,9 @@ describe Mongoid::Criteria do
446
452
  before do
447
453
  @collection = mock
448
454
  Person.expects(:collection).returns(@collection)
449
- @collection.expects(:find_one).with(@criteria.selector, { :sort => [[:_id, :desc]] }).returns({ :title => "Sir" })
455
+ @collection.expects(:find_one).with(@criteria.selector, { :sort => [[:_id, :desc]] }).returns(
456
+ { "title" => "Sir", "_type" => "Person" }
457
+ )
450
458
  end
451
459
 
452
460
  it "defaults to sort by id" do
@@ -661,7 +669,9 @@ describe Mongoid::Criteria do
661
669
  before do
662
670
  @collection = mock
663
671
  Person.expects(:collection).returns(@collection)
664
- @collection.expects(:find_one).with(@criteria.selector, @criteria.options).returns({ :title => "Sir" })
672
+ @collection.expects(:find_one).with(@criteria.selector, @criteria.options).returns(
673
+ { "title"=> "Sir", "_type" => "Person" }
674
+ )
665
675
  end
666
676
 
667
677
  it "calls find on the collection with the selector and options" do
@@ -830,6 +840,25 @@ describe Mongoid::Criteria do
830
840
 
831
841
  end
832
842
 
843
+ describe "#sum" do
844
+
845
+ context "when klass not provided" do
846
+
847
+ before do
848
+ @reduce = "function(obj, prev) { prev.sum += obj.age; }"
849
+ @collection = mock
850
+ Person.expects(:collection).returns(@collection)
851
+ end
852
+
853
+ it "calls group on the collection with the aggregate js" do
854
+ @collection.expects(:group).with(nil, {:_type => { "$in" => ["Doctor", "Person"] }}, {:sum => 0}, @reduce, true).returns([{"sum" => 50.0}])
855
+ @criteria.sum(:age)
856
+ end
857
+
858
+ end
859
+
860
+ end
861
+
833
862
  describe ".translate" do
834
863
 
835
864
  context "with a single argument" do
@@ -295,6 +295,21 @@ describe Mongoid::Finders do
295
295
 
296
296
  end
297
297
 
298
+ describe ".sum" do
299
+
300
+ before do
301
+ @criteria = mock
302
+ end
303
+
304
+ it "returns the sum of a new criteria" do
305
+ Mongoid::Criteria.expects(:new).returns(@criteria)
306
+ @criteria.expects(:sum).with(:age).returns(50.0)
307
+ sum = Person.sum(:age)
308
+ sum.should == 50.0
309
+ end
310
+
311
+ end
312
+
298
313
  describe ".where" do
299
314
 
300
315
  it "returns a new criteria with select conditions added" do
@@ -0,0 +1,75 @@
1
+ require "spec_helper"
2
+
3
+ describe Mongoid::Memoization do
4
+
5
+ let(:memo) { "Memo" }
6
+
7
+ before do
8
+ @person = Person.new
9
+ end
10
+
11
+ describe "#memoized" do
12
+
13
+ context "when variable has been defined" do
14
+
15
+ before do
16
+ @person.instance_variable_set("@memo", memo)
17
+ end
18
+
19
+ it "returns the memoized value" do
20
+ @person.memoized(:memo) { nil }.should == memo
21
+ end
22
+
23
+ end
24
+
25
+ context "when variable has not been defined" do
26
+
27
+ it "returns the new value" do
28
+ @person.memoized(:memo) { memo }.should == memo
29
+ end
30
+
31
+ it "memoizes the new value" do
32
+ @person.memoized(:memo) { memo }
33
+ @person.instance_variable_get("@memo").should == memo
34
+ end
35
+
36
+ end
37
+
38
+ end
39
+
40
+ describe "#reset" do
41
+
42
+ context "when variable has been defined" do
43
+
44
+ before do
45
+ @person.instance_variable_set("@memo", memo)
46
+ end
47
+
48
+ it "removes the memoized value" do
49
+ @person.reset(:memo) { nil }
50
+ @person.instance_variable_defined?("@memo").should be_false
51
+ end
52
+
53
+ it "returns the new value" do
54
+ @person.reset(:memo) { memo }.should == memo
55
+ end
56
+
57
+ end
58
+
59
+ context "when variable has not been defined" do
60
+
61
+ it "memoizes the new value" do
62
+ @person.reset(:memo) { memo }
63
+ @person.instance_variable_get("@memo").should == memo
64
+ end
65
+
66
+ it "returns the value" do
67
+ @person.reset(:memo) { memo }.should == memo
68
+ end
69
+
70
+ end
71
+
72
+
73
+ end
74
+
75
+ end
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: mongoid
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.11.6
4
+ version: 0.11.7
5
5
  platform: ruby
6
6
  authors:
7
7
  - Durran Jordan
@@ -9,7 +9,7 @@ autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
11
 
12
- date: 2010-01-05 00:00:00 -05:00
12
+ date: 2010-01-06 00:00:00 -05:00
13
13
  default_executable:
14
14
  dependencies:
15
15
  - !ruby/object:Gem::Dependency
@@ -134,6 +134,7 @@ files:
134
134
  - lib/mongoid/extensions/time/conversions.rb
135
135
  - lib/mongoid/field.rb
136
136
  - lib/mongoid/finders.rb
137
+ - lib/mongoid/memoization.rb
137
138
  - lib/mongoid/timestamps.rb
138
139
  - lib/mongoid/versioning.rb
139
140
  - mongoid.gemspec
@@ -187,6 +188,7 @@ files:
187
188
  - spec/unit/mongoid/extensions/time/conversions_spec.rb
188
189
  - spec/unit/mongoid/field_spec.rb
189
190
  - spec/unit/mongoid/finders_spec.rb
191
+ - spec/unit/mongoid/memoization_spec.rb
190
192
  - spec/unit/mongoid/timestamps_spec.rb
191
193
  - spec/unit/mongoid/versioning_spec.rb
192
194
  - spec/unit/mongoid_spec.rb
@@ -267,6 +269,7 @@ test_files:
267
269
  - spec/unit/mongoid/extensions/time/conversions_spec.rb
268
270
  - spec/unit/mongoid/field_spec.rb
269
271
  - spec/unit/mongoid/finders_spec.rb
272
+ - spec/unit/mongoid/memoization_spec.rb
270
273
  - spec/unit/mongoid/timestamps_spec.rb
271
274
  - spec/unit/mongoid/versioning_spec.rb
272
275
  - spec/unit/mongoid_spec.rb