mongo 2.4.3 → 2.5.0.beta

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.
Files changed (235) hide show
  1. checksums.yaml +4 -4
  2. checksums.yaml.gz.sig +3 -2
  3. data.tar.gz.sig +0 -0
  4. data/lib/mongo.rb +3 -2
  5. data/lib/mongo/auth/cr.rb +6 -4
  6. data/lib/mongo/auth/cr/conversation.rb +33 -17
  7. data/lib/mongo/auth/ldap.rb +4 -2
  8. data/lib/mongo/auth/ldap/conversation.rb +19 -9
  9. data/lib/mongo/auth/scram.rb +7 -4
  10. data/lib/mongo/auth/scram/conversation.rb +62 -24
  11. data/lib/mongo/auth/user.rb +10 -0
  12. data/lib/mongo/auth/user/view.rb +44 -22
  13. data/lib/mongo/auth/x509.rb +4 -2
  14. data/lib/mongo/auth/x509/conversation.rb +19 -9
  15. data/lib/mongo/bulk_write.rb +33 -27
  16. data/lib/mongo/bulk_write/combineable.rb +5 -0
  17. data/lib/mongo/bulk_write/transformable.rb +2 -0
  18. data/lib/mongo/bulk_write/validatable.rb +4 -0
  19. data/lib/mongo/client.rb +123 -12
  20. data/lib/mongo/cluster.rb +52 -11
  21. data/lib/mongo/cluster/app_metadata.rb +8 -2
  22. data/lib/mongo/cluster/cursor_reaper.rb +0 -1
  23. data/lib/mongo/cluster/topology.rb +1 -1
  24. data/lib/mongo/collection.rb +114 -27
  25. data/lib/mongo/collection/view.rb +8 -2
  26. data/lib/mongo/collection/view/aggregation.rb +11 -7
  27. data/lib/mongo/collection/view/builder/aggregation.rb +5 -1
  28. data/lib/mongo/collection/view/builder/find_command.rb +5 -3
  29. data/lib/mongo/collection/view/builder/map_reduce.rb +11 -3
  30. data/lib/mongo/collection/view/builder/op_query.rb +1 -1
  31. data/lib/mongo/collection/view/change_stream.rb +160 -0
  32. data/lib/mongo/collection/view/change_stream/retryable.rb +57 -0
  33. data/lib/mongo/collection/view/iterable.rb +11 -10
  34. data/lib/mongo/collection/view/map_reduce.rb +22 -18
  35. data/lib/mongo/collection/view/readable.rb +51 -37
  36. data/lib/mongo/collection/view/writable.rb +72 -40
  37. data/lib/mongo/cursor.rb +25 -4
  38. data/lib/mongo/cursor/builder/get_more_command.rb +4 -2
  39. data/lib/mongo/database.rb +22 -11
  40. data/lib/mongo/database/view.rb +16 -12
  41. data/lib/mongo/error.rb +5 -0
  42. data/lib/mongo/error/invalid_session.rb +36 -0
  43. data/lib/mongo/error/missing_resume_token.rb +39 -0
  44. data/lib/mongo/error/operation_failure.rb +17 -0
  45. data/lib/mongo/error/parser.rb +3 -2
  46. data/lib/mongo/error/unknown_payload_type.rb +41 -0
  47. data/lib/mongo/error/unsupported_array_filters.rb +51 -0
  48. data/lib/mongo/error/unsupported_message_type.rb +23 -0
  49. data/lib/mongo/grid/fs_bucket.rb +5 -4
  50. data/lib/mongo/grid/stream/read.rb +3 -2
  51. data/lib/mongo/grid/stream/write.rb +2 -2
  52. data/lib/mongo/index/view.rb +35 -25
  53. data/lib/mongo/monitoring/event/secure.rb +14 -0
  54. data/lib/mongo/operation.rb +16 -0
  55. data/lib/mongo/operation/commands.rb +1 -0
  56. data/lib/mongo/operation/commands/aggregate.rb +9 -5
  57. data/lib/mongo/operation/commands/aggregate/result.rb +1 -1
  58. data/lib/mongo/operation/commands/collections_info.rb +6 -6
  59. data/lib/mongo/operation/commands/command.rb +2 -1
  60. data/lib/mongo/operation/commands/create.rb +6 -2
  61. data/lib/mongo/operation/commands/drop.rb +6 -2
  62. data/lib/mongo/operation/commands/drop_database.rb +6 -2
  63. data/lib/mongo/operation/commands/explain.rb +27 -0
  64. data/lib/mongo/operation/commands/explain/result.rb +52 -0
  65. data/lib/mongo/operation/commands/indexes.rb +1 -1
  66. data/lib/mongo/operation/commands/list_collections.rb +1 -1
  67. data/lib/mongo/operation/commands/list_collections/result.rb +1 -1
  68. data/lib/mongo/operation/commands/list_indexes.rb +1 -1
  69. data/lib/mongo/operation/commands/list_indexes/result.rb +1 -1
  70. data/lib/mongo/operation/commands/map_reduce.rb +8 -4
  71. data/lib/mongo/operation/commands/map_reduce/result.rb +13 -1
  72. data/lib/mongo/operation/commands/user_query.rb +1 -1
  73. data/lib/mongo/operation/commands/users_info.rb +6 -2
  74. data/lib/mongo/operation/executable.rb +4 -1
  75. data/lib/mongo/operation/read_preference.rb +10 -5
  76. data/lib/mongo/operation/result.rb +26 -2
  77. data/lib/mongo/operation/specifiable.rb +13 -1
  78. data/lib/mongo/operation/uses_command_op_msg.rb +47 -0
  79. data/lib/mongo/operation/write/bulk/bulkable.rb +4 -1
  80. data/lib/mongo/operation/write/bulk/insert/result.rb +4 -4
  81. data/lib/mongo/operation/write/command/create_index.rb +6 -1
  82. data/lib/mongo/operation/write/command/delete.rb +28 -4
  83. data/lib/mongo/operation/write/command/drop_index.rb +6 -1
  84. data/lib/mongo/operation/write/command/insert.rb +22 -18
  85. data/lib/mongo/operation/write/command/update.rb +24 -9
  86. data/lib/mongo/operation/write/command/writable.rb +14 -1
  87. data/lib/mongo/operation/write/insert.rb +4 -1
  88. data/lib/mongo/operation/write/insert/result.rb +2 -2
  89. data/lib/mongo/operation/write/update.rb +7 -1
  90. data/lib/mongo/operation/write/write_command_enabled.rb +20 -3
  91. data/lib/mongo/protocol.rb +3 -0
  92. data/lib/mongo/protocol/bit_vector.rb +2 -2
  93. data/lib/mongo/protocol/compressed.rb +135 -0
  94. data/lib/mongo/protocol/delete.rb +8 -6
  95. data/lib/mongo/protocol/get_more.rb +8 -6
  96. data/lib/mongo/protocol/insert.rb +8 -6
  97. data/lib/mongo/protocol/kill_cursors.rb +8 -6
  98. data/lib/mongo/protocol/message.rb +31 -3
  99. data/lib/mongo/protocol/msg.rb +172 -0
  100. data/lib/mongo/protocol/query.rb +26 -6
  101. data/lib/mongo/protocol/registry.rb +76 -0
  102. data/lib/mongo/protocol/reply.rb +10 -5
  103. data/lib/mongo/protocol/serializers.rb +224 -0
  104. data/lib/mongo/protocol/update.rb +8 -6
  105. data/lib/mongo/retryable.rb +4 -2
  106. data/lib/mongo/server.rb +6 -3
  107. data/lib/mongo/server/connectable.rb +1 -1
  108. data/lib/mongo/server/connection.rb +30 -8
  109. data/lib/mongo/server/description.rb +25 -1
  110. data/lib/mongo/server/description/features.rb +4 -1
  111. data/lib/mongo/server/monitor.rb +5 -0
  112. data/lib/mongo/server/monitor/connection.rb +50 -2
  113. data/lib/mongo/server_selector/nearest.rb +10 -4
  114. data/lib/mongo/server_selector/primary.rb +20 -0
  115. data/lib/mongo/server_selector/primary_preferred.rb +10 -4
  116. data/lib/mongo/server_selector/secondary.rb +10 -4
  117. data/lib/mongo/server_selector/secondary_preferred.rb +24 -4
  118. data/lib/mongo/session.rb +180 -0
  119. data/lib/mongo/session/server_session.rb +73 -0
  120. data/lib/mongo/session/session_pool.rb +161 -0
  121. data/lib/mongo/uri.rb +11 -0
  122. data/lib/mongo/version.rb +1 -1
  123. data/mongo.gemspec +2 -1
  124. data/spec/mongo/auth/cr_spec.rb +12 -0
  125. data/spec/mongo/auth/ldap_spec.rb +2 -0
  126. data/spec/mongo/auth/scram/conversation_spec.rb +6 -6
  127. data/spec/mongo/auth/scram_spec.rb +25 -1
  128. data/spec/mongo/auth/user/view_spec.rb +268 -76
  129. data/spec/mongo/auth/x509_spec.rb +2 -0
  130. data/spec/mongo/bulk_write_spec.rb +435 -5
  131. data/spec/mongo/client_spec.rb +356 -39
  132. data/spec/mongo/cluster/app_metadata_spec.rb +2 -2
  133. data/spec/mongo/cluster_spec.rb +176 -0
  134. data/spec/mongo/collection/view/aggregation_spec.rb +33 -12
  135. data/spec/mongo/collection/view/builder/find_command_spec.rb +46 -6
  136. data/spec/mongo/collection/view/change_stream_spec.rb +814 -0
  137. data/spec/mongo/collection/view/map_reduce_spec.rb +94 -17
  138. data/spec/mongo/collection/view/readable_spec.rb +3 -12
  139. data/spec/mongo/collection_spec.rb +1048 -42
  140. data/spec/mongo/cursor/builder/get_more_command_spec.rb +19 -0
  141. data/spec/mongo/cursor_spec.rb +2 -2
  142. data/spec/mongo/database_spec.rb +50 -1
  143. data/spec/mongo/grid/fs_bucket_spec.rb +225 -137
  144. data/spec/mongo/grid/stream/read_spec.rb +2 -2
  145. data/spec/mongo/index/view_spec.rb +146 -8
  146. data/spec/mongo/monitoring/event/secure_spec.rb +42 -0
  147. data/spec/mongo/operation/read/query_spec.rb +2 -1
  148. data/spec/mongo/operation/specifiable_spec.rb +2 -2
  149. data/spec/mongo/operation/write/command/delete_spec.rb +96 -13
  150. data/spec/mongo/operation/write/command/insert_spec.rb +111 -12
  151. data/spec/mongo/operation/write/command/update_spec.rb +93 -10
  152. data/spec/mongo/operation/write/delete_spec.rb +1 -1
  153. data/spec/mongo/operation/write/insert_spec.rb +1 -1
  154. data/spec/mongo/operation/write/update_spec.rb +1 -1
  155. data/spec/mongo/protocol/compressed_spec.rb +66 -0
  156. data/spec/mongo/protocol/delete_spec.rb +14 -0
  157. data/spec/mongo/protocol/get_more_spec.rb +14 -0
  158. data/spec/mongo/protocol/insert_spec.rb +14 -0
  159. data/spec/mongo/protocol/kill_cursors_spec.rb +14 -0
  160. data/spec/mongo/protocol/msg_spec.rb +499 -0
  161. data/spec/mongo/protocol/query_spec.rb +45 -0
  162. data/spec/mongo/protocol/registry_spec.rb +31 -0
  163. data/spec/mongo/protocol/reply_spec.rb +14 -0
  164. data/spec/mongo/protocol/update_spec.rb +14 -0
  165. data/spec/mongo/retryable_spec.rb +6 -2
  166. data/spec/mongo/sdam_spec.rb +4 -0
  167. data/spec/mongo/server/connection_spec.rb +4 -2
  168. data/spec/mongo/server/description_spec.rb +28 -1
  169. data/spec/mongo/session/server_session_spec.rb +16 -0
  170. data/spec/mongo/session/session_pool_spec.rb +194 -0
  171. data/spec/mongo/uri_spec.rb +31 -2
  172. data/spec/spec_helper.rb +104 -0
  173. data/spec/support/authorization.rb +6 -1
  174. data/spec/support/crud.rb +3 -1
  175. data/spec/support/crud/write.rb +6 -1
  176. data/spec/support/crud_tests/write/findOneAndUpdate-arrayFilters.yml +69 -0
  177. data/spec/support/crud_tests/write/updateMany-arrayFilters.yml +63 -0
  178. data/spec/support/crud_tests/write/updateOne-arrayFilters.yml +109 -0
  179. data/spec/support/sdam/rs/discover_arbiters.yml +1 -1
  180. data/spec/support/sdam/rs/discover_passives.yml +2 -2
  181. data/spec/support/sdam/rs/discover_primary.yml +1 -1
  182. data/spec/support/sdam/rs/discover_secondary.yml +1 -1
  183. data/spec/support/sdam/rs/discovery.yml +4 -4
  184. data/spec/support/sdam/rs/equal_electionids.yml +1 -0
  185. data/spec/support/sdam/rs/ghost_discovered.yml +1 -1
  186. data/spec/support/sdam/rs/hosts_differ_from_seeds.yml +1 -1
  187. data/spec/support/sdam/rs/ls_timeout.yml +88 -0
  188. data/spec/support/sdam/rs/member_reconfig.yml +2 -2
  189. data/spec/support/sdam/rs/member_standalone.yml +2 -2
  190. data/spec/support/sdam/rs/new_primary.yml +2 -2
  191. data/spec/support/sdam/rs/new_primary_new_electionid.yml +3 -0
  192. data/spec/support/sdam/rs/new_primary_new_setversion.yml +3 -0
  193. data/spec/support/sdam/rs/new_primary_wrong_set_name.yml +2 -2
  194. data/spec/support/sdam/rs/non_rs_member.yml +1 -1
  195. data/spec/support/sdam/rs/normalize_case.yml +1 -1
  196. data/spec/support/sdam/rs/null_election_id.yml +4 -0
  197. data/spec/support/sdam/rs/primary_becomes_standalone.yml +2 -2
  198. data/spec/support/sdam/rs/primary_changes_set_name.yml +2 -2
  199. data/spec/support/sdam/rs/primary_disconnect.yml +2 -2
  200. data/spec/support/sdam/rs/primary_disconnect_electionid.yml +5 -0
  201. data/spec/support/sdam/rs/primary_disconnect_setversion.yml +5 -0
  202. data/spec/support/sdam/rs/primary_hint_from_secondary_with_mismatched_me.yml +58 -0
  203. data/spec/support/sdam/rs/primary_reports_new_member.yml +4 -4
  204. data/spec/support/sdam/rs/primary_to_no_primary_mismatched_me.yml +2 -2
  205. data/spec/support/sdam/rs/primary_wrong_set_name.yml +1 -1
  206. data/spec/support/sdam/rs/response_from_removed.yml +2 -2
  207. data/spec/support/sdam/rs/rsother_discovered.yml +1 -1
  208. data/spec/support/sdam/rs/sec_not_auth.yml +1 -1
  209. data/spec/support/sdam/rs/secondary_wrong_set_name.yml +1 -1
  210. data/spec/support/sdam/rs/secondary_wrong_set_name_with_primary.yml +2 -2
  211. data/spec/support/sdam/rs/setversion_without_electionid.yml +2 -0
  212. data/spec/support/sdam/rs/stepdown_change_set_name.yml +2 -2
  213. data/spec/support/sdam/rs/unexpected_mongos.yml +1 -1
  214. data/spec/support/sdam/rs/use_setversion_without_electionid.yml +3 -0
  215. data/spec/support/sdam/rs/wrong_set_name.yml +1 -1
  216. data/spec/support/sdam/sharded/ls_timeout_mongos.yml +97 -0
  217. data/spec/support/sdam/sharded/mongos_disconnect.yml +3 -3
  218. data/spec/support/sdam/sharded/multiple_mongoses.yml +1 -1
  219. data/spec/support/sdam/sharded/non_mongos_removed.yml +1 -1
  220. data/spec/support/sdam/sharded/normalize_uri_case.yml +1 -1
  221. data/spec/support/sdam/single/direct_connection_external_ip.yml +1 -1
  222. data/spec/support/sdam/single/direct_connection_mongos.yml +1 -1
  223. data/spec/support/sdam/single/direct_connection_rsarbiter.yml +1 -1
  224. data/spec/support/sdam/single/direct_connection_rsprimary.yml +1 -1
  225. data/spec/support/sdam/single/direct_connection_rssecondary.yml +1 -1
  226. data/spec/support/sdam/single/direct_connection_slave.yml +1 -1
  227. data/spec/support/sdam/single/direct_connection_standalone.yml +1 -1
  228. data/spec/support/sdam/single/ls_timeout_standalone.yml +35 -0
  229. data/spec/support/sdam/single/not_ok_response.yml +1 -1
  230. data/spec/support/sdam/single/standalone_removed.yml +1 -1
  231. data/spec/support/sdam/single/unavailable_seed.yml +1 -1
  232. data/spec/support/server_discovery_and_monitoring.rb +4 -0
  233. data/spec/support/shared/session.rb +236 -0
  234. metadata +53 -15
  235. metadata.gz.sig +0 -0
data/lib/mongo/cluster.rb CHANGED
@@ -48,6 +48,11 @@ module Mongo
48
48
  # @since 2.4.0
49
49
  IDLE_WRITE_PERIOD_SECONDS = 10
50
50
 
51
+ # The cluster time key in responses from mongos servers.
52
+ #
53
+ # @since 2.5.0
54
+ CLUSTER_TIME = 'clusterTime'.freeze
55
+
51
56
  # @return [ Hash ] The options hash.
52
57
  attr_reader :options
53
58
 
@@ -63,6 +68,11 @@ module Mongo
63
68
  # @since 2.4.0
64
69
  attr_reader :app_metadata
65
70
 
71
+ # @return [ BSON::Document ] The latest cluster time seen.
72
+ #
73
+ # @since 2.5.0
74
+ attr_reader :cluster_time
75
+
66
76
  def_delegators :topology, :replica_set?, :replica_set_name, :sharded?,
67
77
  :single?, :unknown?, :member_discovered
68
78
  def_delegators :@cursor_reaper, :register_cursor, :schedule_kill_cursor, :unregister_cursor
@@ -155,9 +165,11 @@ module Mongo
155
165
  @monitoring = monitoring
156
166
  @event_listeners = Event::Listeners.new
157
167
  @options = options.freeze
158
- @app_metadata ||= AppMetadata.new(self)
168
+ @app_metadata = AppMetadata.new(self)
159
169
  @update_lock = Mutex.new
160
170
  @pool_lock = Mutex.new
171
+ @cluster_time = nil
172
+ @cluster_time_lock = Mutex.new
161
173
  @topology = Topology.initial(seeds, monitoring, options)
162
174
 
163
175
  publish_sdam_event(
@@ -442,6 +454,43 @@ module Mongo
442
454
  addresses_list
443
455
  end
444
456
 
457
+ # The logical session timeout value in minutes.
458
+ #
459
+ # @example Get the logical session timeout in minutes.
460
+ # cluster.logical_session_timeout
461
+ #
462
+ # @return [ Integer, nil ] The logical session timeout.
463
+ #
464
+ # @since 2.5.0
465
+ def logical_session_timeout
466
+ servers.inject(nil) do |min, server|
467
+ break unless timeout = server.logical_session_timeout
468
+ [timeout, (min || timeout)].min
469
+ end
470
+ end
471
+
472
+ # Update the max cluster time seen in a response.
473
+ #
474
+ # @example Update the cluster time.
475
+ # cluster.update_cluster_time(result)
476
+ #
477
+ # @param [ Operation::Result ] The operation result containing the cluster time.
478
+ #
479
+ # @return [ Object ] The cluster time.
480
+ #
481
+ # @since 2.5.0
482
+ def update_cluster_time(result)
483
+ if cluster_time_doc = result.cluster_time
484
+ @cluster_time_lock.synchronize do
485
+ if @cluster_time.nil?
486
+ @cluster_time = cluster_time_doc
487
+ else
488
+ @cluster_time = cluster_time_doc if cluster_time_doc[CLUSTER_TIME] > @cluster_time[CLUSTER_TIME]
489
+ end
490
+ end
491
+ end
492
+ end
493
+
445
494
  private
446
495
 
447
496
  def direct_connection?(address)
@@ -457,19 +506,11 @@ module Mongo
457
506
  end
458
507
 
459
508
  def servers_list
460
- @update_lock.synchronize do
461
- @servers.reduce([]) do |servers, server|
462
- servers << server
463
- end
464
- end
509
+ @update_lock.synchronize { @servers.dup }
465
510
  end
466
511
 
467
512
  def addresses_list
468
- @update_lock.synchronize do
469
- @addresses.reduce([]) do |addresses, address|
470
- addresses << address
471
- end
472
- end
513
+ @update_lock.synchronize { @addresses.dup }
473
514
  end
474
515
  end
475
516
  end
@@ -54,6 +54,7 @@ module Mongo
54
54
  def initialize(cluster)
55
55
  @app_name = cluster.options[:app_name]
56
56
  @platform = cluster.options[:platform]
57
+ @compressors = cluster.options[:compressors] || []
57
58
  end
58
59
 
59
60
  # Get the bytes of the ismaster message including this metadata.
@@ -89,6 +90,10 @@ module Mongo
89
90
  end
90
91
 
91
92
  def serialize
93
+ Protocol::Query.new(Database::ADMIN, Database::COMMAND, document, :limit => -1).serialize
94
+ end
95
+
96
+ def document
92
97
  client_document = full_client_document
93
98
  while client_document.to_bson.to_s.size > MAX_DOCUMENT_SIZE do
94
99
  if client_document[:os][:name] || client_document[:os][:architecture]
@@ -101,8 +106,9 @@ module Mongo
101
106
  end
102
107
  end
103
108
  document = Server::Monitor::Connection::ISMASTER
104
- document = document.merge(client: client_document) if client_document
105
- Protocol::Query.new(Database::ADMIN, Database::COMMAND, document, :limit => -1).serialize
109
+ document = document.merge(compression: @compressors)
110
+ document[:client] = client_document
111
+ document
106
112
  end
107
113
 
108
114
  def driver_doc
@@ -22,7 +22,6 @@ module Mongo
22
22
  #
23
23
  # @since 2.3.0
24
24
  class CursorReaper
25
- extend Forwardable
26
25
  include Retryable
27
26
 
28
27
  # The default time interval for the cursor reaper to send pending kill cursors operations.
@@ -51,7 +51,7 @@ module Mongo
51
51
  if options.has_key?(:connect)
52
52
  OPTIONS.fetch(options[:connect].to_sym).new(options, monitoring, seeds)
53
53
  elsif options.has_key?(:replica_set)
54
- ReplicaSet.new(options, monitoring, options)
54
+ ReplicaSet.new(options, monitoring, seeds)
55
55
  else
56
56
  Unknown.new(options, monitoring, seeds)
57
57
  end
@@ -100,16 +100,28 @@ module Mongo
100
100
  @read_concern ||= options[:read_concern]
101
101
  end
102
102
 
103
+ # Get the server selector on this collection.
104
+ #
105
+ # @example Get the server selector.
106
+ # collection.server_selector
107
+ #
108
+ # @return [ Mongo::ServerSelector ] The server selector.
109
+ #
110
+ # @since 2.0.0
111
+ def server_selector
112
+ @server_selector ||= ServerSelector.get(read_preference || database.server_selector)
113
+ end
114
+
103
115
  # Get the read preference on this collection.
104
116
  #
105
117
  # @example Get the read preference.
106
118
  # collection.read_preference
107
119
  #
108
- # @return [ Mongo::ServerSelector ] The read preference.
120
+ # @return [ Hash ] The read preference.
109
121
  #
110
122
  # @since 2.0.0
111
123
  def read_preference
112
- @read_preference ||= ServerSelector.get(options[:read] || database.read_preference)
124
+ @read_preference ||= options[:read] || database.read_preference
113
125
  end
114
126
 
115
127
  # Get the write concern on this collection.
@@ -162,21 +174,28 @@ module Mongo
162
174
  # @example Force the collection to be created.
163
175
  # collection.create
164
176
  #
177
+ # @param [ Hash ] options The options for the create operation.
178
+ #
179
+ # @option options [ Session ] :session The session to use for the operation.
180
+ #
165
181
  # @return [ Result ] The result of the command.
166
182
  #
167
183
  # @since 2.0.0
168
- def create
184
+ def create(opts = {})
169
185
  operation = { :create => name }.merge(options)
170
186
  operation.delete(:write)
171
187
  server = next_primary
172
188
  if (options[:collation] || options[Operation::COLLATION]) && !server.features.collation_enabled?
173
189
  raise Error::UnsupportedCollation.new
174
190
  end
175
- Operation::Commands::Create.new({
176
- selector: operation,
177
- db_name: database.name,
178
- write_concern: write_concern
179
- }).execute(server)
191
+ client.send(:with_session, opts) do |session|
192
+ Operation::Commands::Create.new({
193
+ selector: operation,
194
+ db_name: database.name,
195
+ write_concern: write_concern,
196
+ session: session
197
+ }).execute(server)
198
+ end
180
199
  end
181
200
 
182
201
  # Drop the collection. Will also drop all indexes associated with the
@@ -187,16 +206,22 @@ module Mongo
187
206
  # @example Drop the collection.
188
207
  # collection.drop
189
208
  #
209
+ # @param [ Hash ] options The options for the drop operation.
210
+ #
211
+ # @option options [ Session ] :session The session to use for the operation.
212
+ #
190
213
  # @return [ Result ] The result of the command.
191
214
  #
192
215
  # @since 2.0.0
193
- def drop
194
- Operation::Commands::Drop.new({
195
- selector: { :drop => name },
196
- db_name: database.name,
197
- write_concern: write_concern
198
- }).execute(next_primary)
199
-
216
+ def drop(opts = {})
217
+ client.send(:with_session, opts) do |session|
218
+ Operation::Commands::Drop.new({
219
+ selector: { :drop => name },
220
+ db_name: database.name,
221
+ write_concern: write_concern,
222
+ session: session
223
+ }).execute(next_primary)
224
+ end
200
225
  rescue Error::OperationFailure => ex
201
226
  raise ex unless ex.message =~ /ns not found/
202
227
  false
@@ -235,6 +260,7 @@ module Mongo
235
260
  # @option options [ Hash ] :sort The key and direction pairs by which the result set
236
261
  # will be sorted.
237
262
  # @option options [ Hash ] :collation The collation to use.
263
+ # @option options [ Session ] :session The session to use.
238
264
  #
239
265
  # @return [ CollectionView ] The collection view.
240
266
  #
@@ -261,6 +287,7 @@ module Mongo
261
287
  # @option options [ true, false ] :bypass_document_validation Whether or
262
288
  # not to skip document level validation.
263
289
  # @option options [ Hash ] :collation The collation to use.
290
+ # @option options [ Session ] :session The session to use.
264
291
  #
265
292
  # @return [ Aggregation ] The aggregation object.
266
293
  #
@@ -269,6 +296,39 @@ module Mongo
269
296
  View.new(self, {}).aggregate(pipeline, options)
270
297
  end
271
298
 
299
+ # As of version 3.6 of the MongoDB server, a ``$changeStream`` pipeline stage is supported
300
+ # in the aggregation framework. This stage allows users to request that notifications are sent for
301
+ # all changes to a particular collection.
302
+ #
303
+ # @example Get change notifications for a given collection.
304
+ # collection.watch([{ '$match' => { operationType: { '$in' => ['insert', 'replace'] } } }])
305
+ #
306
+ # @param [ Array<Hash> ] pipeline Optional additional filter operators.
307
+ # @param [ Hash ] options The change stream options.
308
+ #
309
+ # @option options [ String ] :full_document Allowed values: ‘default’, ‘updateLookup’. Defaults to ‘default’.
310
+ # When set to ‘updateLookup’, the change notification for partial updates will include both a delta
311
+ # describing the changes to the document, as well as a copy of the entire document that was changed
312
+ # from some time after the change occurred.
313
+ # @option options [ BSON::Document, Hash ] :resume_after Specifies the logical starting point for the
314
+ # new change stream.
315
+ # @option options [ Integer ] :max_await_time_ms The maximum amount of time for the server to wait
316
+ # on new documents to satisfy a change stream query.
317
+ # @option options [ Integer ] :batch_size The number of documents to return per batch.
318
+ # @option options [ BSON::Document, Hash ] :collation The collation to use.
319
+ # @option options [ Session ] :session The session to use.
320
+ #
321
+ # @note A change stream only allows 'majority' read concern.
322
+ # @note This helper method is preferable to running a raw aggregation with a $changeStream stage,
323
+ # for the purpose of supporting resumability.
324
+ #
325
+ # @return [ ChangeStream ] The change stream object.
326
+ #
327
+ # @since 2.5.0
328
+ def watch(pipeline = [], options = {})
329
+ View::ChangeStream.new(View.new(self, {}, options), pipeline, options)
330
+ end
331
+
272
332
  # Get a count of matching documents in the collection.
273
333
  #
274
334
  # @example Get the count.
@@ -283,6 +343,7 @@ module Mongo
283
343
  # @option options [ Integer ] :skip The number of documents to skip before counting.
284
344
  # @option options [ Hash ] :read The read preference options.
285
345
  # @option options [ Hash ] :collation The collation to use.
346
+ # @option options [ Session ] :session The session to use.
286
347
  #
287
348
  # @return [ Integer ] The document count.
288
349
  #
@@ -303,6 +364,7 @@ module Mongo
303
364
  # @option options [ Integer ] :max_time_ms The maximum amount of time to allow the command to run.
304
365
  # @option options [ Hash ] :read The read preference options.
305
366
  # @option options [ Hash ] :collation The collation to use.
367
+ # @option options [ Session ] :session The session to use.
306
368
  #
307
369
  # @return [ Array<Object> ] The list of distinct values.
308
370
  #
@@ -319,6 +381,8 @@ module Mongo
319
381
  #
320
382
  # @param [ Hash ] options Options for getting a list of all indexes.
321
383
  #
384
+ # @option options [ Session ] :session The session to use.
385
+ #
322
386
  # @return [ View::Index ] The index view.
323
387
  #
324
388
  # @since 2.0.0
@@ -346,20 +410,25 @@ module Mongo
346
410
  # @param [ Hash ] document The document to insert.
347
411
  # @param [ Hash ] options The insert options.
348
412
  #
413
+ # @option options [ Session ] :session The session to use for the operation.
414
+ #
349
415
  # @return [ Result ] The database response wrapper.
350
416
  #
351
417
  # @since 2.0.0
352
418
  def insert_one(document, options = {})
353
- write_with_retry do
354
- Operation::Write::Insert.new(
355
- :documents => [ document ],
356
- :db_name => database.name,
357
- :coll_name => name,
358
- :write_concern => write_concern,
359
- :bypass_document_validation => !!options[:bypass_document_validation],
360
- :options => options,
361
- :id_generator => client.options[:id_generator]
362
- ).execute(next_primary)
419
+ client.send(:with_session, options) do |session|
420
+ write_with_retry(session, Proc.new { next_primary }) do |server|
421
+ Operation::Write::Insert.new(
422
+ :documents => [ document ],
423
+ :db_name => database.name,
424
+ :coll_name => name,
425
+ :write_concern => write_concern,
426
+ :bypass_document_validation => !!options[:bypass_document_validation],
427
+ :options => options,
428
+ :id_generator => client.options[:id_generator],
429
+ :session => session
430
+ ).execute(server)
431
+ end
363
432
  end
364
433
  end
365
434
 
@@ -371,6 +440,8 @@ module Mongo
371
440
  # @param [ Array<Hash> ] documents The documents to insert.
372
441
  # @param [ Hash ] options The insert options.
373
442
  #
443
+ # @option options [ Session ] :session The session to use for the operation.
444
+ #
374
445
  # @return [ Result ] The database response wrapper.
375
446
  #
376
447
  # @since 2.0.0
@@ -393,6 +464,7 @@ module Mongo
393
464
  # Can be :w => Integer, :fsync => Boolean, :j => Boolean.
394
465
  # @option options [ true, false ] :bypass_document_validation Whether or
395
466
  # not to skip document level validation.
467
+ # @option options [ Session ] :session The session to use for the set of operations.
396
468
  #
397
469
  # @return [ BulkWrite::Result ] The result of the operation.
398
470
  #
@@ -410,6 +482,7 @@ module Mongo
410
482
  # @param [ Hash ] options The options.
411
483
  #
412
484
  # @option options [ Hash ] :collation The collation to use.
485
+ # @option options [ Session ] :session The session to use.
413
486
  #
414
487
  # @return [ Result ] The response from the database.
415
488
  #
@@ -427,6 +500,7 @@ module Mongo
427
500
  # @param [ Hash ] options The options.
428
501
  #
429
502
  # @option options [ Hash ] :collation The collation to use.
503
+ # @option options [ Session ] :session The session to use.
430
504
  #
431
505
  # @return [ Result ] The response from the database.
432
506
  #
@@ -449,12 +523,13 @@ module Mongo
449
523
  #
450
524
  # @option options [ Integer ] :max_time_ms The maximum amount of time to allow the command
451
525
  # to run in milliseconds.
526
+ # @option options [ Session ] :session The session to use.
452
527
  #
453
528
  # @return [ Array<Cursor> ] An array of cursors.
454
529
  #
455
530
  # @since 2.1
456
531
  def parallel_scan(cursor_count, options = {})
457
- find.send(:parallel_scan, cursor_count, options)
532
+ find({}, options).send(:parallel_scan, cursor_count, options)
458
533
  end
459
534
 
460
535
  # Replaces a single document in the collection with the new document.
@@ -471,6 +546,7 @@ module Mongo
471
546
  # @option options [ true, false ] :bypass_document_validation Whether or
472
547
  # not to skip document level validation.
473
548
  # @option options [ Hash ] :collation The collation to use.
549
+ # @option options [ Session ] :session The session to use.
474
550
  #
475
551
  # @return [ Result ] The response from the database.
476
552
  #
@@ -493,6 +569,9 @@ module Mongo
493
569
  # @option options [ true, false ] :bypass_document_validation Whether or
494
570
  # not to skip document level validation.
495
571
  # @option options [ Hash ] :collation The collation to use.
572
+ # @option options [ Array ] :array_filters A set of filters specifying to which array elements
573
+ # an update should apply.
574
+ # @option options [ Session ] :session The session to use.
496
575
  #
497
576
  # @return [ Result ] The response from the database.
498
577
  #
@@ -515,6 +594,9 @@ module Mongo
515
594
  # @option options [ true, false ] :bypass_document_validation Whether or
516
595
  # not to skip document level validation.
517
596
  # @option options [ Hash ] :collation The collation to use.
597
+ # @option options [ Array ] :array_filters A set of filters specifying to which array elements
598
+ # an update should apply.
599
+ # @option options [ Session ] :session The session to use.
518
600
  #
519
601
  # @return [ Result ] The response from the database.
520
602
  #
@@ -540,12 +622,13 @@ module Mongo
540
622
  # @option options [ Hash ] :write_concern The write concern options.
541
623
  # Defaults to the collection's write concern.
542
624
  # @option options [ Hash ] :collation The collation to use.
625
+ # @option options [ Session ] :session The session to use.
543
626
  #
544
627
  # @return [ BSON::Document, nil ] The document, if found.
545
628
  #
546
629
  # @since 2.1.0
547
630
  def find_one_and_delete(filter, options = {})
548
- find(filter, options).find_one_and_delete
631
+ find(filter, options).find_one_and_delete(options)
549
632
  end
550
633
 
551
634
  # Finds a single document via findAndModify and updates it, returning the original doc unless
@@ -573,6 +656,9 @@ module Mongo
573
656
  # @option options [ Hash ] :write_concern The write concern options.
574
657
  # Defaults to the collection's write concern.
575
658
  # @option options [ Hash ] :collation The collation to use.
659
+ # @option options [ Array ] :array_filters A set of filters specifying to which array elements
660
+ # an update should apply.
661
+ # @option options [ Session ] :session The session to use.
576
662
  #
577
663
  # @return [ BSON::Document ] The document.
578
664
  #
@@ -606,6 +692,7 @@ module Mongo
606
692
  # @option options [ Hash ] :write_concern The write concern options.
607
693
  # Defaults to the collection's write concern.
608
694
  # @option options [ Hash ] :collation The collation to use.
695
+ # @option options [ Session ] :session The session to use.
609
696
  #
610
697
  # @return [ BSON::Document ] The document.
611
698
  #