mongoid 7.3.4 → 7.3.5
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- checksums.yaml.gz.sig +0 -0
- data/lib/mongoid/association/embedded/batchable.rb +20 -3
- data/lib/mongoid/association/referenced/has_many/proxy.rb +2 -2
- data/lib/mongoid/atomic/paths/embedded/many.rb +19 -0
- data/lib/mongoid/criteria/queryable/storable.rb +1 -1
- data/lib/mongoid/persistable/upsertable.rb +1 -1
- data/lib/mongoid/version.rb +1 -1
- data/lib/rails/generators/mongoid/config/templates/mongoid.yml +7 -2
- data/spec/lite_spec_helper.rb +8 -1
- data/spec/mongoid/association/embedded/embeds_many/proxy_spec.rb +21 -0
- data/spec/mongoid/association/embedded/embeds_many_models.rb +137 -0
- data/spec/mongoid/association/referenced/has_and_belongs_to_many/proxy_spec.rb +8 -0
- data/spec/mongoid/association/referenced/has_many/proxy_spec.rb +24 -8
- data/spec/mongoid/criteria_spec.rb +32 -0
- data/spec/mongoid/query_cache_spec.rb +2 -2
- data/spec/mongoid/scopable_spec.rb +11 -0
- data/spec/shared/lib/mrss/cluster_config.rb +6 -1
- data/spec/shared/lib/mrss/session_registry.rb +69 -0
- data/spec/shared/lib/mrss/session_registry_legacy.rb +60 -0
- data/spec/shared/share/Dockerfile.erb +3 -3
- data/spec/shared/shlib/server.sh +1 -1
- data/spec/support/models/audible_sound.rb +3 -0
- data.tar.gz.sig +0 -0
- metadata +581 -577
- metadata.gz.sig +2 -3
- data/spec/support/session_registry.rb +0 -50
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA256:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: efce0ba93d948e87b85aa1a6e1a0768ecb2bd17a052d5e34afb426c357391492
|
4
|
+
data.tar.gz: 39784e3b229e457971b79962c26e22f3f1e721c68d72268bdafafa821c245c80
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: f690e5ca59dfdf1e658ac922c5e8c0e0de1bef099f005205cab26b4e27922ce82b64dae38e803673b32e73f9327746562548c3f9667a4d3fd275483729e6ff3d
|
7
|
+
data.tar.gz: b87aef76b5145507b5e48f8516f4b27b99f401d7afb2fa56441d1d47540eac6f3f7bf198fadfd995e9fc08b0563727b6a5c4f7ce5014456e0dd4a6d345cdf3bb
|
checksums.yaml.gz.sig
CHANGED
Binary file
|
@@ -82,7 +82,8 @@ module Mongoid
|
|
82
82
|
def batch_replace(docs)
|
83
83
|
if docs.blank?
|
84
84
|
if _assigning? && !empty?
|
85
|
-
_base.delayed_atomic_sets.
|
85
|
+
_base.delayed_atomic_sets.delete(path)
|
86
|
+
clear_atomic_path_cache
|
86
87
|
_base.add_atomic_unset(first)
|
87
88
|
target_duplicate = _target.dup
|
88
89
|
pre_process_batch_remove(target_duplicate, :delete)
|
@@ -94,7 +95,8 @@ module Mongoid
|
|
94
95
|
_base.delayed_atomic_sets.clear unless _assigning?
|
95
96
|
docs = normalize_docs(docs).compact
|
96
97
|
_target.clear and _unscoped.clear
|
97
|
-
_base.delayed_atomic_unsets.
|
98
|
+
_base.delayed_atomic_unsets.delete(path)
|
99
|
+
clear_atomic_path_cache
|
98
100
|
inserts = execute_batch_set(docs)
|
99
101
|
add_atomic_sets(inserts)
|
100
102
|
end
|
@@ -252,7 +254,22 @@ module Mongoid
|
|
252
254
|
#
|
253
255
|
# @since 3.0.0
|
254
256
|
def path
|
255
|
-
@path ||= _unscoped.
|
257
|
+
@path ||= if _unscoped.empty?
|
258
|
+
Mongoid::Atomic::Paths::Embedded::Many.position_without_document(_base, _association)
|
259
|
+
else
|
260
|
+
_unscoped.first.atomic_path
|
261
|
+
end
|
262
|
+
end
|
263
|
+
|
264
|
+
# Clear the cache for path and atomic_paths. This method is used when
|
265
|
+
# the path method is used, and the association has not been set on the
|
266
|
+
# document yet, which can cause path and atomic_paths to be calculated
|
267
|
+
# incorrectly later.
|
268
|
+
#
|
269
|
+
# @api private
|
270
|
+
def clear_atomic_path_cache
|
271
|
+
self.path = nil
|
272
|
+
_base.instance_variable_set("@atomic_paths", nil)
|
256
273
|
end
|
257
274
|
|
258
275
|
# Set the atomic path.
|
@@ -506,8 +506,8 @@ module Mongoid
|
|
506
506
|
selector = conditions || {}
|
507
507
|
removed = klass.send(method, selector.merge!(criteria.selector))
|
508
508
|
_target.delete_if do |doc|
|
509
|
-
|
510
|
-
unbind_one(doc)
|
509
|
+
doc._matches?(selector).tap do |b|
|
510
|
+
unbind_one(doc) if b
|
511
511
|
end
|
512
512
|
end
|
513
513
|
removed
|
@@ -39,6 +39,25 @@ module Mongoid
|
|
39
39
|
locator = document.new_record? ? "" : ".#{document._index}"
|
40
40
|
"#{pos}#{"." unless pos.blank?}#{document._association.store_as}#{locator}"
|
41
41
|
end
|
42
|
+
|
43
|
+
class << self
|
44
|
+
|
45
|
+
# Get the position of where the document would go for the given
|
46
|
+
# association. The use case for this function is when trying to
|
47
|
+
# persist an empty list for an embedded association. All of the
|
48
|
+
# existing functions for getting the position to store a document
|
49
|
+
# require passing in a document to store, which we don't have when
|
50
|
+
# trying to store the empty list.
|
51
|
+
#
|
52
|
+
# @param [ Document ] parent The parent document to store in.
|
53
|
+
# @param [ Association ] association The association.
|
54
|
+
#
|
55
|
+
# @return [ String ] The position string.
|
56
|
+
def position_without_document(parent, association)
|
57
|
+
pos = parent.atomic_position
|
58
|
+
"#{pos}#{"." unless pos.blank?}#{association.store_as}"
|
59
|
+
end
|
60
|
+
end
|
42
61
|
end
|
43
62
|
end
|
44
63
|
end
|
data/lib/mongoid/version.rb
CHANGED
@@ -80,8 +80,13 @@ development:
|
|
80
80
|
# (default: 10)
|
81
81
|
# connect_timeout: 10
|
82
82
|
|
83
|
-
#
|
84
|
-
#
|
83
|
+
# How long to wait for a response for each operation sent to the
|
84
|
+
# server. This timeout should be set to a value larger than the
|
85
|
+
# processing time for the longest operation that will be executed
|
86
|
+
# by the application. Note that this is a client-side timeout;
|
87
|
+
# the server may continue executing an operation after the client
|
88
|
+
# aborts it with the SocketTimeout exception.
|
89
|
+
# (default: nil, meaning no timeout)
|
85
90
|
# socket_timeout: 5
|
86
91
|
|
87
92
|
# The name of the replica set to connect to. Servers provided as seeds that do
|
data/spec/lite_spec_helper.rb
CHANGED
@@ -19,7 +19,14 @@ autoload :Timecop, 'timecop'
|
|
19
19
|
|
20
20
|
require 'support/spec_config'
|
21
21
|
require 'mrss/lite_constraints'
|
22
|
-
|
22
|
+
|
23
|
+
if Gem::Version.new(Mongo::VERSION) < Gem::Version.new('2.18.0.alpha')
|
24
|
+
require "mrss/session_registry_legacy"
|
25
|
+
else
|
26
|
+
require "mrss/session_registry"
|
27
|
+
end
|
28
|
+
|
29
|
+
Mrss.patch_mongo_for_session_registry
|
23
30
|
|
24
31
|
unless SpecConfig.instance.ci?
|
25
32
|
begin
|
@@ -2,6 +2,7 @@
|
|
2
2
|
# encoding: utf-8
|
3
3
|
|
4
4
|
require "spec_helper"
|
5
|
+
require_relative '../embeds_many_models.rb'
|
5
6
|
|
6
7
|
describe Mongoid::Association::Embedded::EmbedsMany::Proxy do
|
7
8
|
|
@@ -4400,4 +4401,24 @@ describe Mongoid::Association::Embedded::EmbedsMany::Proxy do
|
|
4400
4401
|
end
|
4401
4402
|
end
|
4402
4403
|
end
|
4404
|
+
|
4405
|
+
context "when using assign_attributes with an already populated array" do
|
4406
|
+
let(:post) { EmmPost.create! }
|
4407
|
+
|
4408
|
+
before do
|
4409
|
+
post.assign_attributes(company_tags: [{id: BSON::ObjectId.new, title: 'a'}],
|
4410
|
+
user_tags: [{id: BSON::ObjectId.new, title: 'b'}])
|
4411
|
+
post.save!
|
4412
|
+
post.reload
|
4413
|
+
post.assign_attributes(company_tags: [{id: BSON::ObjectId.new, title: 'c'}],
|
4414
|
+
user_tags: [])
|
4415
|
+
post.save!
|
4416
|
+
post.reload
|
4417
|
+
end
|
4418
|
+
|
4419
|
+
it "has the correct embedded documents" do
|
4420
|
+
expect(post.company_tags.length).to eq(1)
|
4421
|
+
expect(post.company_tags.first.title).to eq("c")
|
4422
|
+
end
|
4423
|
+
end
|
4403
4424
|
end
|
@@ -52,3 +52,140 @@ class EmmProduct
|
|
52
52
|
|
53
53
|
field :name, type: String
|
54
54
|
end
|
55
|
+
|
56
|
+
class EmmInner
|
57
|
+
include Mongoid::Document
|
58
|
+
|
59
|
+
embeds_many :friends, :class_name => self.name, :cyclic => true
|
60
|
+
embedded_in :parent, :class_name => self.name, :cyclic => true
|
61
|
+
|
62
|
+
field :level, :type => Integer
|
63
|
+
end
|
64
|
+
|
65
|
+
class EmmOuter
|
66
|
+
include Mongoid::Document
|
67
|
+
embeds_many :inners, class_name: 'EmmInner'
|
68
|
+
|
69
|
+
field :level, :type => Integer
|
70
|
+
end
|
71
|
+
|
72
|
+
class EmmCustomerAddress
|
73
|
+
include Mongoid::Document
|
74
|
+
|
75
|
+
embedded_in :addressable, polymorphic: true, inverse_of: :work_address
|
76
|
+
end
|
77
|
+
|
78
|
+
class EmmFriend
|
79
|
+
include Mongoid::Document
|
80
|
+
|
81
|
+
embedded_in :befriendable, polymorphic: true
|
82
|
+
end
|
83
|
+
|
84
|
+
class EmmCustomer
|
85
|
+
include Mongoid::Document
|
86
|
+
|
87
|
+
embeds_one :home_address, class_name: 'EmmCustomerAddress', as: :addressable
|
88
|
+
embeds_one :work_address, class_name: 'EmmCustomerAddress', as: :addressable
|
89
|
+
|
90
|
+
embeds_many :close_friends, class_name: 'EmmFriend', as: :befriendable
|
91
|
+
embeds_many :acquaintances, class_name: 'EmmFriend', as: :befriendable
|
92
|
+
end
|
93
|
+
|
94
|
+
class EmmUser
|
95
|
+
include Mongoid::Document
|
96
|
+
include Mongoid::Timestamps
|
97
|
+
|
98
|
+
embeds_many :orders, class_name: 'EmmOrder'
|
99
|
+
end
|
100
|
+
|
101
|
+
class EmmOrder
|
102
|
+
include Mongoid::Document
|
103
|
+
|
104
|
+
field :amount, type: Integer
|
105
|
+
|
106
|
+
embedded_in :user, class_name: 'EmmUser'
|
107
|
+
end
|
108
|
+
|
109
|
+
module EmmSpec
|
110
|
+
# There is also a top-level Car class defined.
|
111
|
+
class Car
|
112
|
+
include Mongoid::Document
|
113
|
+
|
114
|
+
embeds_many :doors
|
115
|
+
end
|
116
|
+
|
117
|
+
class Door
|
118
|
+
include Mongoid::Document
|
119
|
+
|
120
|
+
embedded_in :car
|
121
|
+
end
|
122
|
+
|
123
|
+
class Tank
|
124
|
+
include Mongoid::Document
|
125
|
+
|
126
|
+
embeds_many :guns
|
127
|
+
embeds_many :emm_turrets
|
128
|
+
# This association references a model that is not in our module,
|
129
|
+
# and it does not define class_name hence Mongoid will not be able to
|
130
|
+
# figure out the inverse for this association.
|
131
|
+
embeds_many :emm_hatches
|
132
|
+
|
133
|
+
# class_name is intentionally unqualified, references a class in the
|
134
|
+
# same module. Rails permits class_name to be unqualified like this.
|
135
|
+
embeds_many :launchers, class_name: 'Launcher'
|
136
|
+
end
|
137
|
+
|
138
|
+
class Gun
|
139
|
+
include Mongoid::Document
|
140
|
+
|
141
|
+
embedded_in :tank
|
142
|
+
end
|
143
|
+
|
144
|
+
class Launcher
|
145
|
+
include Mongoid::Document
|
146
|
+
|
147
|
+
# class_name is intentionally unqualified.
|
148
|
+
embedded_in :tank, class_name: 'Tank'
|
149
|
+
end
|
150
|
+
end
|
151
|
+
|
152
|
+
# This is intentionally on top level.
|
153
|
+
class EmmTurret
|
154
|
+
include Mongoid::Document
|
155
|
+
|
156
|
+
embedded_in :tank, class_name: 'EmmSpec::Tank'
|
157
|
+
end
|
158
|
+
|
159
|
+
# This is intentionally on top level.
|
160
|
+
class EmmHatch
|
161
|
+
include Mongoid::Document
|
162
|
+
|
163
|
+
# No :class_name option on this association intentionally.
|
164
|
+
embedded_in :tank
|
165
|
+
end
|
166
|
+
|
167
|
+
class EmmPost
|
168
|
+
include Mongoid::Document
|
169
|
+
|
170
|
+
embeds_many :company_tags, class_name: "EmmCompanyTag"
|
171
|
+
embeds_many :user_tags, class_name: "EmmUserTag"
|
172
|
+
end
|
173
|
+
|
174
|
+
|
175
|
+
class EmmCompanyTag
|
176
|
+
include Mongoid::Document
|
177
|
+
|
178
|
+
field :title, type: String
|
179
|
+
|
180
|
+
embedded_in :post, class_name: "EmmPost"
|
181
|
+
end
|
182
|
+
|
183
|
+
|
184
|
+
class EmmUserTag
|
185
|
+
include Mongoid::Document
|
186
|
+
|
187
|
+
field :title, type: String
|
188
|
+
|
189
|
+
embedded_in :post, class_name: "EmmPost"
|
190
|
+
end
|
191
|
+
|
@@ -2395,6 +2395,10 @@ describe Mongoid::Association::Referenced::HasAndBelongsToMany::Proxy do
|
|
2395
2395
|
it "removes the ids from the foreign key" do
|
2396
2396
|
expect(person.preference_ids).to eq([ preference_two.id ])
|
2397
2397
|
end
|
2398
|
+
|
2399
|
+
it "sets the association locally" do
|
2400
|
+
expect(person.preferences).to eq([preference_two])
|
2401
|
+
end
|
2398
2402
|
end
|
2399
2403
|
|
2400
2404
|
context "when conditions are not provided" do
|
@@ -2421,6 +2425,10 @@ describe Mongoid::Association::Referenced::HasAndBelongsToMany::Proxy do
|
|
2421
2425
|
it "returns the number of documents deleted" do
|
2422
2426
|
expect(deleted).to eq(2)
|
2423
2427
|
end
|
2428
|
+
|
2429
|
+
it "sets the association locally" do
|
2430
|
+
expect(person.preferences).to eq([])
|
2431
|
+
end
|
2424
2432
|
end
|
2425
2433
|
end
|
2426
2434
|
end
|
@@ -2214,10 +2214,8 @@ describe Mongoid::Association::Referenced::HasMany::Proxy do
|
|
2214
2214
|
Person.create(username: 'durran')
|
2215
2215
|
end
|
2216
2216
|
|
2217
|
-
|
2218
|
-
|
2219
|
-
person.posts.create(title: "Test")
|
2220
|
-
end
|
2217
|
+
let!(:post1) { person.posts.create!(title: "Testing") }
|
2218
|
+
let!(:post2) { person.posts.create!(title: "Test") }
|
2221
2219
|
|
2222
2220
|
it "removes the correct posts" do
|
2223
2221
|
person.posts.send(method, { title: "Testing" })
|
@@ -2233,6 +2231,11 @@ describe Mongoid::Association::Referenced::HasMany::Proxy do
|
|
2233
2231
|
it "returns the number of documents deleted" do
|
2234
2232
|
expect(person.posts.send(method, { title: "Testing" })).to eq(1)
|
2235
2233
|
end
|
2234
|
+
|
2235
|
+
it "sets the association locally" do
|
2236
|
+
person.posts.send(method, { title: "Testing" })
|
2237
|
+
expect(person.posts).to eq([post2])
|
2238
|
+
end
|
2236
2239
|
end
|
2237
2240
|
|
2238
2241
|
context "when conditions are not provided" do
|
@@ -2259,6 +2262,11 @@ describe Mongoid::Association::Referenced::HasMany::Proxy do
|
|
2259
2262
|
it "returns the number of documents deleted" do
|
2260
2263
|
expect(person.posts.send(method)).to eq(2)
|
2261
2264
|
end
|
2265
|
+
|
2266
|
+
it "sets the association locally" do
|
2267
|
+
person.posts.send(method)
|
2268
|
+
expect(person.posts).to eq([])
|
2269
|
+
end
|
2262
2270
|
end
|
2263
2271
|
end
|
2264
2272
|
|
@@ -2270,10 +2278,8 @@ describe Mongoid::Association::Referenced::HasMany::Proxy do
|
|
2270
2278
|
Movie.create(title: "Bladerunner")
|
2271
2279
|
end
|
2272
2280
|
|
2273
|
-
|
2274
|
-
|
2275
|
-
movie.ratings.create(value: 2)
|
2276
|
-
end
|
2281
|
+
let!(:rating1) { movie.ratings.create!(value: 1) }
|
2282
|
+
let!(:rating2) { movie.ratings.create!(value: 2) }
|
2277
2283
|
|
2278
2284
|
it "removes the correct ratings" do
|
2279
2285
|
movie.ratings.send(method, { value: 1 })
|
@@ -2288,6 +2294,11 @@ describe Mongoid::Association::Referenced::HasMany::Proxy do
|
|
2288
2294
|
it "returns the number of documents deleted" do
|
2289
2295
|
expect(movie.ratings.send(method, { value: 1 })).to eq(1)
|
2290
2296
|
end
|
2297
|
+
|
2298
|
+
it "sets the association locally" do
|
2299
|
+
movie.ratings.send(method, { value: 1 })
|
2300
|
+
expect(movie.ratings).to eq([rating2])
|
2301
|
+
end
|
2291
2302
|
end
|
2292
2303
|
|
2293
2304
|
context "when conditions are not provided" do
|
@@ -2314,6 +2325,11 @@ describe Mongoid::Association::Referenced::HasMany::Proxy do
|
|
2314
2325
|
it "returns the number of documents deleted" do
|
2315
2326
|
expect(movie.ratings.send(method)).to eq(2)
|
2316
2327
|
end
|
2328
|
+
|
2329
|
+
it "sets the association locally" do
|
2330
|
+
movie.ratings.send(method)
|
2331
|
+
expect(movie.ratings).to eq([])
|
2332
|
+
end
|
2317
2333
|
end
|
2318
2334
|
end
|
2319
2335
|
end
|
@@ -3490,6 +3490,38 @@ describe Mongoid::Criteria do
|
|
3490
3490
|
'foo' => 1, '$and' => [{'foo' => 2}], 'bar' => 3)
|
3491
3491
|
end
|
3492
3492
|
end
|
3493
|
+
|
3494
|
+
context "when duplicating where conditions" do
|
3495
|
+
let(:criteria) { Sound.where(active: true).where(active: true) }
|
3496
|
+
|
3497
|
+
it 'does not duplicate criteria' do
|
3498
|
+
expect(criteria.selector).to eq('active' => true)
|
3499
|
+
end
|
3500
|
+
end
|
3501
|
+
|
3502
|
+
context "when duplicating where conditions with different values" do
|
3503
|
+
let(:criteria) { Sound.where(active: true).where(active: false).where(active: true).where(active: false) }
|
3504
|
+
|
3505
|
+
it 'does not duplicate criteria' do
|
3506
|
+
expect(criteria.selector).to eq(
|
3507
|
+
'active' => true, '$and' => [{'active' => false}])
|
3508
|
+
end
|
3509
|
+
end
|
3510
|
+
|
3511
|
+
# Used to test MONGOID-5251 where the find command was adding unnecessary
|
3512
|
+
# and clauses. Since the find command creates the criteria and executes it,
|
3513
|
+
# it is difficult to analyze the criteria used. For this reason, I have
|
3514
|
+
# extracted the crux of the issue, adding an _id to the the criteria twice,
|
3515
|
+
# and used that for the test case.
|
3516
|
+
context "when searching by _id twice" do
|
3517
|
+
let(:_id) { BSON::ObjectId.new }
|
3518
|
+
let(:criteria) { Band.where(_id: _id) }
|
3519
|
+
let(:dup_criteria) { criteria.where(_id: _id)}
|
3520
|
+
|
3521
|
+
it "does not duplicate the criteria" do
|
3522
|
+
expect(dup_criteria.selector).to eq({ "_id" => _id })
|
3523
|
+
end
|
3524
|
+
end
|
3493
3525
|
end
|
3494
3526
|
|
3495
3527
|
describe "#for_js" do
|
@@ -17,11 +17,11 @@ describe Mongoid::QueryCache do
|
|
17
17
|
# occur only within the scope of these tests.
|
18
18
|
#
|
19
19
|
# Other session leaks will be detected and addressed as part of RUBY-2391.
|
20
|
-
SessionRegistry.instance.clear_registry
|
20
|
+
Mrss::SessionRegistry.instance.clear_registry
|
21
21
|
end
|
22
22
|
|
23
23
|
after do
|
24
|
-
SessionRegistry.instance.verify_sessions_ended!
|
24
|
+
Mrss::SessionRegistry.instance.verify_sessions_ended!
|
25
25
|
end
|
26
26
|
|
27
27
|
let(:reset_legacy_qc_warning) do
|
@@ -111,6 +111,17 @@ describe Mongoid::Scopable do
|
|
111
111
|
expect(Band).to be_default_scoping
|
112
112
|
end
|
113
113
|
end
|
114
|
+
|
115
|
+
context "when parent class has default scope" do
|
116
|
+
|
117
|
+
let (:selector) do
|
118
|
+
AudibleSound.all.selector
|
119
|
+
end
|
120
|
+
|
121
|
+
it "the subclass doesn't duplicate the default scope in the selector" do
|
122
|
+
expect(selector).to eq({'active' => true})
|
123
|
+
end
|
124
|
+
end
|
114
125
|
end
|
115
126
|
|
116
127
|
describe ".default_scopable?" do
|
@@ -209,7 +209,12 @@ module Mrss
|
|
209
209
|
@server_version = build_info['version']
|
210
210
|
@enterprise = build_info['modules'] && build_info['modules'].include?('enterprise')
|
211
211
|
|
212
|
-
@server_parameters =
|
212
|
+
@server_parameters = begin
|
213
|
+
client.use(:admin).command(getParameter: '*').first
|
214
|
+
rescue => e
|
215
|
+
STDERR.puts("WARNING: Failed to obtain server parameters: #{e.class}: #{e.message}")
|
216
|
+
{}
|
217
|
+
end
|
213
218
|
|
214
219
|
if !sharded_ish? && short_server_version >= '3.4'
|
215
220
|
rv = @server_parameters['featureCompatibilityVersion']
|
@@ -0,0 +1,69 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
# encoding: utf-8
|
3
|
+
|
4
|
+
require 'singleton'
|
5
|
+
|
6
|
+
module Mrss
|
7
|
+
|
8
|
+
def self.patch_mongo_for_session_registry
|
9
|
+
|
10
|
+
Mongo::Client.class_eval do
|
11
|
+
alias :get_session_without_tracking :get_session
|
12
|
+
|
13
|
+
def get_session(options = {})
|
14
|
+
get_session_without_tracking(options).tap do |session|
|
15
|
+
SessionRegistry.instance.register(session) if session&.materialized?
|
16
|
+
end
|
17
|
+
end
|
18
|
+
end
|
19
|
+
|
20
|
+
Mongo::Session.class_eval do
|
21
|
+
alias :end_session_without_tracking :end_session
|
22
|
+
|
23
|
+
def end_session
|
24
|
+
SessionRegistry.instance.unregister(self)
|
25
|
+
end_session_without_tracking
|
26
|
+
end
|
27
|
+
|
28
|
+
alias :materialize_if_needed_without_tracking :materialize_if_needed
|
29
|
+
|
30
|
+
def materialize_if_needed
|
31
|
+
materialize_if_needed_without_tracking.tap do
|
32
|
+
SessionRegistry.instance.register(self)
|
33
|
+
end
|
34
|
+
end
|
35
|
+
end
|
36
|
+
end
|
37
|
+
end
|
38
|
+
|
39
|
+
module Mrss
|
40
|
+
class SessionRegistry
|
41
|
+
include Singleton
|
42
|
+
|
43
|
+
def initialize
|
44
|
+
@registry = {}
|
45
|
+
end
|
46
|
+
|
47
|
+
def register(session)
|
48
|
+
@registry[session.session_id] = session if session
|
49
|
+
end
|
50
|
+
|
51
|
+
def unregister(session)
|
52
|
+
return if session.ended? || !session.materialized?
|
53
|
+
@registry.delete(session.session_id)
|
54
|
+
end
|
55
|
+
|
56
|
+
def verify_sessions_ended!
|
57
|
+
@registry.delete_if { |_, session| session.ended? }
|
58
|
+
|
59
|
+
unless @registry.empty?
|
60
|
+
sessions = @registry.map { |_, session| session }
|
61
|
+
raise "Session registry contains live sessions: #{sessions.join(', ')}"
|
62
|
+
end
|
63
|
+
end
|
64
|
+
|
65
|
+
def clear_registry
|
66
|
+
@registry = {}
|
67
|
+
end
|
68
|
+
end
|
69
|
+
end
|
@@ -0,0 +1,60 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
# encoding: utf-8
|
3
|
+
|
4
|
+
require 'singleton'
|
5
|
+
|
6
|
+
module Mrss
|
7
|
+
|
8
|
+
def self.patch_mongo_for_session_registry
|
9
|
+
|
10
|
+
Mongo::Client.class_eval do
|
11
|
+
alias :get_session_without_tracking :get_session
|
12
|
+
|
13
|
+
def get_session(options = {})
|
14
|
+
get_session_without_tracking(options).tap do |session|
|
15
|
+
SessionRegistry.instance.register(session)
|
16
|
+
end
|
17
|
+
end
|
18
|
+
end
|
19
|
+
|
20
|
+
Mongo::Session.class_eval do
|
21
|
+
alias :end_session_without_tracking :end_session
|
22
|
+
|
23
|
+
def end_session
|
24
|
+
SessionRegistry.instance.unregister(self)
|
25
|
+
end_session_without_tracking
|
26
|
+
end
|
27
|
+
end
|
28
|
+
end
|
29
|
+
end
|
30
|
+
|
31
|
+
module Mrss
|
32
|
+
class SessionRegistry
|
33
|
+
include Singleton
|
34
|
+
|
35
|
+
def initialize
|
36
|
+
@registry = {}
|
37
|
+
end
|
38
|
+
|
39
|
+
def register(session)
|
40
|
+
@registry[session.session_id] = session if session
|
41
|
+
end
|
42
|
+
|
43
|
+
def unregister(session)
|
44
|
+
@registry.delete(session.session_id) unless session.ended?
|
45
|
+
end
|
46
|
+
|
47
|
+
def verify_sessions_ended!
|
48
|
+
@registry.delete_if { |_, session| session.ended? }
|
49
|
+
|
50
|
+
unless @registry.empty?
|
51
|
+
sessions = @registry.map { |_, session| session }
|
52
|
+
raise "Session registry contains live sessions: #{sessions.join(', ')}"
|
53
|
+
end
|
54
|
+
end
|
55
|
+
|
56
|
+
def clear_registry
|
57
|
+
@registry = {}
|
58
|
+
end
|
59
|
+
end
|
60
|
+
end
|
@@ -233,13 +233,13 @@ CFG
|
|
233
233
|
# Current virtualenv fails with
|
234
234
|
# https://github.com/pypa/virtualenv/issues/1630
|
235
235
|
<% if distro =~ /ubuntu2004/ %>
|
236
|
-
RUN python3 -m pip install 'virtualenv<20' 'mtools-legacy[mlaunch]'
|
236
|
+
RUN python3 -m pip install 'virtualenv<20' 'mtools-legacy[mlaunch]==1.5.5'
|
237
237
|
<% else %>
|
238
|
-
RUN python2 -m pip install 'virtualenv<20' 'mtools-legacy[mlaunch]'
|
238
|
+
RUN python2 -m pip install 'virtualenv<20' 'mtools-legacy[mlaunch]==1.5.5'
|
239
239
|
<% end %>
|
240
240
|
|
241
241
|
RUN pip --version && \
|
242
|
-
pip install mtools-legacy[mlaunch]
|
242
|
+
pip install 'mtools-legacy[mlaunch]==1.5.5'
|
243
243
|
|
244
244
|
<% if @env.fetch('MONGODB_VERSION') >= '4.4' %>
|
245
245
|
# ubuntu1604 installs MarkupSafe 0.0.0 here instead of 2.0.0+
|
data/spec/shared/shlib/server.sh
CHANGED
data.tar.gz.sig
CHANGED
Binary file
|