mongoid 5.0.0 → 5.0.1

Sign up to get free protection for your applications and to get access to all the features.
Files changed (85) hide show
  1. checksums.yaml +4 -4
  2. checksums.yaml.gz.sig +0 -0
  3. data.tar.gz.sig +2 -0
  4. data/CHANGELOG.md +54 -2
  5. data/lib/config/locales/en.yml +1 -1
  6. data/lib/mongoid/attributes.rb +1 -1
  7. data/lib/mongoid/clients.rb +7 -4
  8. data/lib/mongoid/clients/options.rb +2 -2
  9. data/lib/mongoid/contextual/aggregable/mongo.rb +2 -1
  10. data/lib/mongoid/contextual/geo_near.rb +1 -1
  11. data/lib/mongoid/contextual/memory.rb +4 -1
  12. data/lib/mongoid/contextual/mongo.rb +4 -5
  13. data/lib/mongoid/document.rb +1 -0
  14. data/lib/mongoid/indexable/specification.rb +3 -5
  15. data/lib/mongoid/indexable/validators/options.rb +7 -1
  16. data/lib/mongoid/matchable/exists.rb +1 -1
  17. data/lib/mongoid/persistable.rb +2 -1
  18. data/lib/mongoid/persistable/creatable.rb +1 -1
  19. data/lib/mongoid/persistable/deletable.rb +1 -1
  20. data/lib/mongoid/persistable/updatable.rb +2 -2
  21. data/lib/mongoid/positional.rb +75 -0
  22. data/lib/mongoid/relations/counter_cache.rb +19 -0
  23. data/lib/mongoid/relations/eager/base.rb +4 -2
  24. data/lib/mongoid/relations/embedded/batchable.rb +10 -3
  25. data/lib/mongoid/relations/proxy.rb +1 -1
  26. data/lib/mongoid/relations/touchable.rb +1 -1
  27. data/lib/mongoid/scopable.rb +6 -5
  28. data/lib/mongoid/selectable.rb +36 -1
  29. data/lib/mongoid/threaded.rb +34 -2
  30. data/lib/mongoid/timestamps/created.rb +1 -2
  31. data/lib/mongoid/timestamps/timeless.rb +19 -2
  32. data/lib/mongoid/timestamps/updated.rb +1 -1
  33. data/lib/mongoid/traversable.rb +1 -1
  34. data/lib/mongoid/version.rb +1 -1
  35. data/lib/rails/generators/mongoid/config/templates/mongoid.yml +3 -1
  36. data/spec/app/models/account.rb +8 -0
  37. data/spec/app/models/answer.rb +2 -0
  38. data/spec/app/models/article.rb +2 -0
  39. data/spec/app/models/author.rb +2 -0
  40. data/spec/app/models/baby.rb +4 -0
  41. data/spec/app/models/book.rb +2 -0
  42. data/spec/app/models/consumption_period.rb +7 -0
  43. data/spec/app/models/exhibitor.rb +1 -0
  44. data/spec/app/models/kaleidoscope.rb +6 -0
  45. data/spec/app/models/kangaroo.rb +4 -0
  46. data/spec/app/models/note.rb +3 -0
  47. data/spec/app/models/page.rb +11 -0
  48. data/spec/app/models/simple.rb +5 -0
  49. data/spec/config/mongoid.yml +3 -1
  50. data/spec/mongoid/atomic/paths_spec.rb +17 -10
  51. data/spec/mongoid/attributes_spec.rb +2 -2
  52. data/spec/mongoid/clients/options_spec.rb +15 -0
  53. data/spec/mongoid/clients_spec.rb +6 -2
  54. data/spec/mongoid/config_spec.rb +3 -2
  55. data/spec/mongoid/contextual/aggregable/mongo_spec.rb +25 -2
  56. data/spec/mongoid/contextual/atomic_spec.rb +6 -6
  57. data/spec/mongoid/contextual/mongo_spec.rb +28 -75
  58. data/spec/mongoid/criteria_spec.rb +54 -0
  59. data/spec/mongoid/fields/standard_spec.rb +1 -1
  60. data/spec/mongoid/fields_spec.rb +1 -1
  61. data/spec/mongoid/indexable/specification_spec.rb +1 -1
  62. data/spec/mongoid/indexable_spec.rb +7 -7
  63. data/spec/mongoid/interceptable_spec.rb +55 -0
  64. data/spec/mongoid/persistable/creatable_spec.rb +19 -0
  65. data/spec/mongoid/persistable/destroyable_spec.rb +50 -0
  66. data/spec/mongoid/persistable/incrementable_spec.rb +56 -4
  67. data/spec/mongoid/persistable/pushable_spec.rb +11 -0
  68. data/spec/mongoid/persistable/savable_spec.rb +20 -2
  69. data/spec/mongoid/positional_spec.rb +221 -0
  70. data/spec/mongoid/query_cache_spec.rb +19 -0
  71. data/spec/mongoid/relations/auto_save_spec.rb +1 -1
  72. data/spec/mongoid/relations/bindings/referenced/many_to_many_spec.rb +1 -1
  73. data/spec/mongoid/relations/counter_cache_spec.rb +64 -11
  74. data/spec/mongoid/relations/eager/has_many_spec.rb +37 -0
  75. data/spec/mongoid/relations/eager_spec.rb +11 -0
  76. data/spec/mongoid/relations/embedded/many_spec.rb +38 -9
  77. data/spec/mongoid/relations/embedded/one_spec.rb +1 -1
  78. data/spec/mongoid/relations/proxy_spec.rb +22 -0
  79. data/spec/mongoid/relations/reflections_spec.rb +1 -1
  80. data/spec/mongoid/scopable_spec.rb +160 -19
  81. data/spec/mongoid/selectable_spec.rb +16 -6
  82. data/spec/mongoid/timestamps/timeless_spec.rb +17 -0
  83. data/spec/mongoid/validatable/uniqueness_spec.rb +17 -0
  84. metadata +40 -5
  85. metadata.gz.sig +3 -0
@@ -1465,7 +1465,7 @@ describe Mongoid::Attributes do
1465
1465
  expect(product.cost).to eq(500)
1466
1466
  end
1467
1467
 
1468
- it "aliases the existance check" do
1468
+ it "aliases the existence check" do
1469
1469
  expect(product.cost?).to be true
1470
1470
  end
1471
1471
 
@@ -1506,7 +1506,7 @@ describe Mongoid::Attributes do
1506
1506
  expect(product.price).to eq(500)
1507
1507
  end
1508
1508
 
1509
- it "aliases the existance check" do
1509
+ it "aliases the existence check" do
1510
1510
  expect(product.price?).to be true
1511
1511
  end
1512
1512
 
@@ -8,6 +8,10 @@ describe Mongoid::Clients::Options do
8
8
 
9
9
  let(:options) { { database: 'test' } }
10
10
 
11
+ let!(:cluster) do
12
+ Band.mongo_client.cluster
13
+ end
14
+
11
15
  let!(:klass) do
12
16
  Band.with(options)
13
17
  end
@@ -33,6 +37,17 @@ describe Mongoid::Clients::Options do
33
37
  it "keeps the options" do
34
38
  expect(klass.persistence_options).to eq(options)
35
39
  end
40
+
41
+ context 'when changing the collection' do
42
+
43
+ let(:options) do
44
+ { collection: 'other' }
45
+ end
46
+
47
+ it 'uses that collection' do
48
+ expect(klass.collection.name).to eq(options[:collection])
49
+ end
50
+ end
36
51
  end
37
52
 
38
53
  context "when returning a criteria" do
@@ -413,7 +413,7 @@ describe Mongoid::Clients do
413
413
  context "when no client exists with the key" do
414
414
 
415
415
  before(:all) do
416
- Band.store_in(client: :nonexistant)
416
+ Band.store_in(client: :nonexistent)
417
417
  end
418
418
 
419
419
  let(:band) do
@@ -469,7 +469,7 @@ describe Mongoid::Clients do
469
469
  context "when no client exists with the key" do
470
470
 
471
471
  before(:all) do
472
- Band.store_in(client: :nonexistant)
472
+ Band.store_in(client: :nonexistent)
473
473
  end
474
474
 
475
475
  it "raises an error" do
@@ -749,6 +749,10 @@ describe Mongoid::Clients do
749
749
  expect(sess[:bands].find(name: "Tool")).to_not be_nil
750
750
  end
751
751
  end
752
+
753
+ it 'uses that database for the model mongo_client' do
754
+ expect(Band.mongo_client.database.name).to eq('mongoid_optional')
755
+ end
752
756
  end
753
757
  end
754
758
  end
@@ -197,7 +197,8 @@ describe Mongoid::Config do
197
197
  end
198
198
 
199
199
  it "sets the read option" do
200
- expect(options["read"]).to eq({ "mode" => :primary })
200
+ expect(options["read"]).to eq({ "mode" => :primary_preferred,
201
+ "tag_sets" => [{ "use" => "web" }]})
201
202
  end
202
203
  end
203
204
  end
@@ -218,7 +219,7 @@ describe Mongoid::Config do
218
219
  end
219
220
  end
220
221
 
221
- context "when provided a non-existant option" do
222
+ context "when provided a non-existent option" do
222
223
 
223
224
  it "raises an error" do
224
225
  expect {
@@ -145,7 +145,7 @@ describe Mongoid::Contextual::Aggregable::Mongo do
145
145
  context "when the field does not exist" do
146
146
 
147
147
  let(:aggregates) do
148
- context.aggregates(:non_existant)
148
+ context.aggregates(:non_existent)
149
149
  end
150
150
 
151
151
  it "returns an avg" do
@@ -234,7 +234,7 @@ describe Mongoid::Contextual::Aggregable::Mongo do
234
234
  end
235
235
 
236
236
  let(:aggregates) do
237
- context.aggregates(:non_existant)
237
+ context.aggregates(:non_existent)
238
238
  end
239
239
 
240
240
  it "returns nil" do
@@ -302,6 +302,29 @@ describe Mongoid::Contextual::Aggregable::Mongo do
302
302
 
303
303
  describe "#max" do
304
304
 
305
+ context 'when the field does not exist in any document' do
306
+
307
+ let!(:depeche) do
308
+ Band.create(name: "Depeche Mode", likes: 1000)
309
+ end
310
+
311
+ let(:criteria) do
312
+ Band.all
313
+ end
314
+
315
+ let(:context) do
316
+ Mongoid::Contextual::Mongo.new(criteria)
317
+ end
318
+
319
+ let(:max) do
320
+ context.max(:non_existent)
321
+ end
322
+
323
+ it 'returns nil' do
324
+ expect(max).to be(nil)
325
+ end
326
+ end
327
+
305
328
  context "when provided a single field" do
306
329
 
307
330
  let!(:depeche) do
@@ -254,7 +254,7 @@ describe Mongoid::Contextual::Atomic do
254
254
  expect(depeche_mode.reload.members).to eq([ "Dave" ])
255
255
  end
256
256
 
257
- it "does not error on non existant fields" do
257
+ it "does not error on non existent fields" do
258
258
  expect(smiths.reload.members).to be_nil
259
259
  end
260
260
  end
@@ -285,7 +285,7 @@ describe Mongoid::Contextual::Atomic do
285
285
  expect(depeche_mode.reload.members).to eq([ "Fletch" ])
286
286
  end
287
287
 
288
- it "does not error on non existant fields" do
288
+ it "does not error on non existent fields" do
289
289
  expect(smiths.reload.members).to be_nil
290
290
  end
291
291
  end
@@ -316,7 +316,7 @@ describe Mongoid::Contextual::Atomic do
316
316
  expect(depeche_mode.reload.members).to eq([ "Dave", "Alan" ])
317
317
  end
318
318
 
319
- it "pushes to non existant fields" do
319
+ it "pushes to non existent fields" do
320
320
  expect(smiths.reload.members).to eq([ "Alan" ])
321
321
  end
322
322
  end
@@ -347,7 +347,7 @@ describe Mongoid::Contextual::Atomic do
347
347
  expect(depeche_mode.reload.members).to eq([ "Dave", "Alan", "Fletch" ])
348
348
  end
349
349
 
350
- it "pushes to non existant fields" do
350
+ it "pushes to non existent fields" do
351
351
  expect(smiths.reload.members).to eq([ "Alan", "Fletch" ])
352
352
  end
353
353
  end
@@ -378,7 +378,7 @@ describe Mongoid::Contextual::Atomic do
378
378
  expect(depeche_mode.reload.artists).to eq([ "Dave" ])
379
379
  end
380
380
 
381
- it "does not rename non existant fields" do
381
+ it "does not rename non existent fields" do
382
382
  expect(smiths.reload).to_not respond_to(:artists)
383
383
  end
384
384
  end
@@ -409,7 +409,7 @@ describe Mongoid::Contextual::Atomic do
409
409
  expect(depeche_mode.reload.name).to eq("Recoil")
410
410
  end
411
411
 
412
- it "sets non existant fields" do
412
+ it "sets non existent fields" do
413
413
  expect(smiths.reload.name).to eq("Recoil")
414
414
  end
415
415
  end
@@ -757,7 +757,7 @@ describe Mongoid::Contextual::Mongo do
757
757
 
758
758
  context "when subsequently calling #last" do
759
759
 
760
- it "returns the correnct document" do
760
+ it "returns the correct document" do
761
761
  expect(context.send(method)).to eq(new_order)
762
762
  expect(context.last).to eq(depeche_mode)
763
763
  end
@@ -783,7 +783,7 @@ describe Mongoid::Contextual::Mongo do
783
783
 
784
784
  context "when subsequently calling #last" do
785
785
 
786
- it "returns the correnct document" do
786
+ it "returns the correct document" do
787
787
  expect(context.send(method)).to eq(new_order)
788
788
  expect(context.last).to eq(depeche_mode)
789
789
  end
@@ -854,79 +854,6 @@ describe Mongoid::Contextual::Mongo do
854
854
  end
855
855
  end
856
856
 
857
- pending "#last" do
858
-
859
- context "when no default scope" do
860
-
861
- let!(:depeche_mode) do
862
- Band.create(name: "Depeche Mode")
863
- end
864
-
865
- let!(:new_order) do
866
- Band.create(name: "New Order")
867
- end
868
-
869
- let(:criteria) do
870
- Band.all
871
- end
872
-
873
- let(:context) do
874
- described_class.new(criteria)
875
- end
876
-
877
- it "returns the last matching document" do
878
- expect(context.last).to eq(new_order)
879
- end
880
- end
881
-
882
- context "when default scope" do
883
-
884
- let!(:palm) do
885
- Tree.create(name: "Palm")
886
- end
887
-
888
- let!(:maple) do
889
- Tree.create(name: "Maple")
890
- end
891
-
892
- let(:criteria) do
893
- Tree.all
894
- end
895
-
896
- let(:context) do
897
- described_class.new(criteria)
898
- end
899
-
900
- it "respects default scope" do
901
- expect(context.last).to eq(palm)
902
- end
903
- end
904
-
905
- context "when subsequently calling #first" do
906
-
907
- let!(:depeche_mode) do
908
- Band.create(name: "Depeche Mode")
909
- end
910
-
911
- let!(:new_order) do
912
- Band.create(name: "New Order")
913
- end
914
-
915
- let(:criteria) do
916
- Band.asc(:name)
917
- end
918
-
919
- let(:context) do
920
- described_class.new(criteria)
921
- end
922
-
923
- it "returns the correnct document" do
924
- expect(context.last).to eq(new_order)
925
- expect(context.first).to eq(depeche_mode)
926
- end
927
- end
928
- end
929
-
930
857
  [ :length, :size ].each do |method|
931
858
 
932
859
  describe "##{method}" do
@@ -1805,4 +1732,30 @@ describe Mongoid::Contextual::Mongo do
1805
1732
  end
1806
1733
  end
1807
1734
  end
1735
+
1736
+ describe '#pipeline' do
1737
+
1738
+ context 'when the criteria has a selector' do
1739
+
1740
+ let(:criteria) do
1741
+ Band.where(name: "New Order")
1742
+ end
1743
+
1744
+ let(:context) do
1745
+ described_class.new(criteria)
1746
+ end
1747
+
1748
+ let(:matches_operators) do
1749
+ context.send(:pipeline, 'name').select { |o| o['$match'] }
1750
+ end
1751
+
1752
+ it 'creates a pipeline with the selector as one of the $match criteria' do
1753
+ expect(matches_operators).to include('$match' => criteria.selector)
1754
+ end
1755
+
1756
+ it 'creates a pipeline with the $exists operator as one of the $match criteria' do
1757
+ expect(matches_operators).to include('$match' => { 'name' => { '$exists' => true } })
1758
+ end
1759
+ end
1760
+ end
1808
1761
  end
@@ -2821,6 +2821,60 @@ describe Mongoid::Criteria do
2821
2821
  expect(criteria.first.likes).to eq(3)
2822
2822
  end
2823
2823
  end
2824
+
2825
+ context 'when the field is a subdocument' do
2826
+
2827
+ let(:criteria) do
2828
+ Band.where(name: 'FKA Twigs')
2829
+ end
2830
+
2831
+ context 'when a top-level field and a subdocument field are plucked' do
2832
+
2833
+ before do
2834
+ Band.create(name: 'FKA Twigs')
2835
+ Band.create(name: 'FKA Twigs', records: [ Record.new(name: 'LP1') ])
2836
+ end
2837
+
2838
+ let(:embedded_pluck) do
2839
+ criteria.pluck(:name, 'records.name')
2840
+ end
2841
+
2842
+ let(:expected) do
2843
+ [
2844
+ ["FKA Twigs", nil],
2845
+ ['FKA Twigs', [{ "name" => "LP1" }]]
2846
+ ]
2847
+ end
2848
+
2849
+ it 'returns the list of top-level field and subdocument values' do
2850
+ expect(embedded_pluck). to eq(expected)
2851
+ end
2852
+ end
2853
+
2854
+ context 'when only a subdocument field is plucked' do
2855
+
2856
+ before do
2857
+ Band.create(name: 'FKA Twigs')
2858
+ Band.create(name: 'FKA Twigs', records: [ Record.new(name: 'LP1') ])
2859
+ end
2860
+
2861
+ let(:embedded_pluck) do
2862
+ criteria.pluck('records.name')
2863
+ end
2864
+
2865
+ let(:expected) do
2866
+ [
2867
+ nil,
2868
+ [{ "name" => "LP1" }]
2869
+ ]
2870
+ end
2871
+
2872
+ it 'returns the list of subdocument values' do
2873
+ expect(embedded_pluck). to eq(expected)
2874
+ end
2875
+ end
2876
+
2877
+ end
2824
2878
  end
2825
2879
 
2826
2880
  context "when plucking mult-fields" do
@@ -123,7 +123,7 @@ describe Mongoid::Fields::Standard do
123
123
  end
124
124
  end
125
125
 
126
- context "when getting a non existant value" do
126
+ context "when getting a non existent value" do
127
127
 
128
128
  it "returns nil" do
129
129
  expect(hash[:key]).to be_nil
@@ -895,7 +895,7 @@ describe Mongoid::Fields do
895
895
  (person.testing = expect("Testy")).to eq("Testy")
896
896
  end
897
897
 
898
- it "adds an existance method" do
898
+ it "adds an existence method" do
899
899
  expect(Person.new.testing?).to be false
900
900
  end
901
901
 
@@ -96,7 +96,7 @@ describe Mongoid::Indexable::Specification do
96
96
  end
97
97
 
98
98
  it "normalizes the options" do
99
- expect(spec.options).to eq(background: true, dropDups: true)
99
+ expect(spec.options).to eq(background: true, drop_dups: true)
100
100
  end
101
101
  end
102
102
  end
@@ -192,8 +192,8 @@ describe Mongoid::Indexable do
192
192
  klass.index_specification(name: 1).options
193
193
  end
194
194
 
195
- it "sets the index with dropDups options" do
196
- expect(options).to eq(dropDups: true)
195
+ it "sets the index with drop_dups option" do
196
+ expect(options).to eq(drop_dups: true)
197
197
  end
198
198
  end
199
199
 
@@ -327,7 +327,7 @@ describe Mongoid::Indexable do
327
327
  end
328
328
  end
329
329
 
330
- context "when providing a geo haystack index" do
330
+ context "when providing a geo haystack index with a bucket_size" do
331
331
 
332
332
  before do
333
333
  klass.index({ location: "geoHaystack" }, { min: -200, max: 200, bucket_size: 0.5 })
@@ -337,8 +337,8 @@ describe Mongoid::Indexable do
337
337
  klass.index_specification(location: "geoHaystack").options
338
338
  end
339
339
 
340
- it "sets the geo haystack index" do
341
- expect(options).to eq({ min: -200, max: 200, bucketSize: 0.5 })
340
+ it "sets the geo haystack index with the bucket_size option" do
341
+ expect(options).to eq({ min: -200, max: 200, bucket_size: 0.5 })
342
342
  end
343
343
  end
344
344
 
@@ -490,8 +490,8 @@ describe Mongoid::Indexable do
490
490
  klass.index_specification(name: 1).options
491
491
  end
492
492
 
493
- it "sets the index with sparse options" do
494
- expect(options).to eq(expireAfterSeconds: 3600)
493
+ it "sets the index with expire_after option" do
494
+ expect(options).to eq(expire_after: 3600)
495
495
  end
496
496
  end
497
497