mongoid 5.0.0 → 5.0.1
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 +4 -4
- checksums.yaml.gz.sig +0 -0
- data.tar.gz.sig +2 -0
- data/CHANGELOG.md +54 -2
- data/lib/config/locales/en.yml +1 -1
- data/lib/mongoid/attributes.rb +1 -1
- data/lib/mongoid/clients.rb +7 -4
- data/lib/mongoid/clients/options.rb +2 -2
- data/lib/mongoid/contextual/aggregable/mongo.rb +2 -1
- data/lib/mongoid/contextual/geo_near.rb +1 -1
- data/lib/mongoid/contextual/memory.rb +4 -1
- data/lib/mongoid/contextual/mongo.rb +4 -5
- data/lib/mongoid/document.rb +1 -0
- data/lib/mongoid/indexable/specification.rb +3 -5
- data/lib/mongoid/indexable/validators/options.rb +7 -1
- data/lib/mongoid/matchable/exists.rb +1 -1
- data/lib/mongoid/persistable.rb +2 -1
- data/lib/mongoid/persistable/creatable.rb +1 -1
- data/lib/mongoid/persistable/deletable.rb +1 -1
- data/lib/mongoid/persistable/updatable.rb +2 -2
- data/lib/mongoid/positional.rb +75 -0
- data/lib/mongoid/relations/counter_cache.rb +19 -0
- data/lib/mongoid/relations/eager/base.rb +4 -2
- data/lib/mongoid/relations/embedded/batchable.rb +10 -3
- data/lib/mongoid/relations/proxy.rb +1 -1
- data/lib/mongoid/relations/touchable.rb +1 -1
- data/lib/mongoid/scopable.rb +6 -5
- data/lib/mongoid/selectable.rb +36 -1
- data/lib/mongoid/threaded.rb +34 -2
- data/lib/mongoid/timestamps/created.rb +1 -2
- data/lib/mongoid/timestamps/timeless.rb +19 -2
- data/lib/mongoid/timestamps/updated.rb +1 -1
- data/lib/mongoid/traversable.rb +1 -1
- data/lib/mongoid/version.rb +1 -1
- data/lib/rails/generators/mongoid/config/templates/mongoid.yml +3 -1
- data/spec/app/models/account.rb +8 -0
- data/spec/app/models/answer.rb +2 -0
- data/spec/app/models/article.rb +2 -0
- data/spec/app/models/author.rb +2 -0
- data/spec/app/models/baby.rb +4 -0
- data/spec/app/models/book.rb +2 -0
- data/spec/app/models/consumption_period.rb +7 -0
- data/spec/app/models/exhibitor.rb +1 -0
- data/spec/app/models/kaleidoscope.rb +6 -0
- data/spec/app/models/kangaroo.rb +4 -0
- data/spec/app/models/note.rb +3 -0
- data/spec/app/models/page.rb +11 -0
- data/spec/app/models/simple.rb +5 -0
- data/spec/config/mongoid.yml +3 -1
- data/spec/mongoid/atomic/paths_spec.rb +17 -10
- data/spec/mongoid/attributes_spec.rb +2 -2
- data/spec/mongoid/clients/options_spec.rb +15 -0
- data/spec/mongoid/clients_spec.rb +6 -2
- data/spec/mongoid/config_spec.rb +3 -2
- data/spec/mongoid/contextual/aggregable/mongo_spec.rb +25 -2
- data/spec/mongoid/contextual/atomic_spec.rb +6 -6
- data/spec/mongoid/contextual/mongo_spec.rb +28 -75
- data/spec/mongoid/criteria_spec.rb +54 -0
- data/spec/mongoid/fields/standard_spec.rb +1 -1
- data/spec/mongoid/fields_spec.rb +1 -1
- data/spec/mongoid/indexable/specification_spec.rb +1 -1
- data/spec/mongoid/indexable_spec.rb +7 -7
- data/spec/mongoid/interceptable_spec.rb +55 -0
- data/spec/mongoid/persistable/creatable_spec.rb +19 -0
- data/spec/mongoid/persistable/destroyable_spec.rb +50 -0
- data/spec/mongoid/persistable/incrementable_spec.rb +56 -4
- data/spec/mongoid/persistable/pushable_spec.rb +11 -0
- data/spec/mongoid/persistable/savable_spec.rb +20 -2
- data/spec/mongoid/positional_spec.rb +221 -0
- data/spec/mongoid/query_cache_spec.rb +19 -0
- data/spec/mongoid/relations/auto_save_spec.rb +1 -1
- data/spec/mongoid/relations/bindings/referenced/many_to_many_spec.rb +1 -1
- data/spec/mongoid/relations/counter_cache_spec.rb +64 -11
- data/spec/mongoid/relations/eager/has_many_spec.rb +37 -0
- data/spec/mongoid/relations/eager_spec.rb +11 -0
- data/spec/mongoid/relations/embedded/many_spec.rb +38 -9
- data/spec/mongoid/relations/embedded/one_spec.rb +1 -1
- data/spec/mongoid/relations/proxy_spec.rb +22 -0
- data/spec/mongoid/relations/reflections_spec.rb +1 -1
- data/spec/mongoid/scopable_spec.rb +160 -19
- data/spec/mongoid/selectable_spec.rb +16 -6
- data/spec/mongoid/timestamps/timeless_spec.rb +17 -0
- data/spec/mongoid/validatable/uniqueness_spec.rb +17 -0
- metadata +40 -5
- 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
|
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
|
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: :
|
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: :
|
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
|
data/spec/mongoid/config_spec.rb
CHANGED
@@ -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" => :
|
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-
|
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(:
|
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(:
|
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
|
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
|
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
|
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
|
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
|
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
|
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
|
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
|
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
|
data/spec/mongoid/fields_spec.rb
CHANGED
@@ -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
|
196
|
-
expect(options).to eq(
|
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,
|
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
|
494
|
-
expect(options).to eq(
|
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
|
|