mongo 2.11.6 → 2.12.0.rc0
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 +2 -2
- data.tar.gz.sig +0 -0
- data/CONTRIBUTING.md +1 -1
- data/lib/mongo.rb +3 -0
- data/lib/mongo/address.rb +13 -2
- data/lib/mongo/auth.rb +1 -0
- data/lib/mongo/auth/credential_cache.rb +51 -0
- data/lib/mongo/auth/scram/conversation.rb +20 -16
- data/lib/mongo/auth/user.rb +0 -8
- data/lib/mongo/auth/user/view.rb +4 -4
- data/lib/mongo/background_thread.rb +1 -1
- data/lib/mongo/bulk_write.rb +5 -5
- data/lib/mongo/client.rb +126 -11
- data/lib/mongo/client_encryption.rb +103 -0
- data/lib/mongo/cluster.rb +2 -2
- data/lib/mongo/cluster/reapers/cursor_reaper.rb +18 -6
- data/lib/mongo/cluster/sdam_flow.rb +54 -58
- data/lib/mongo/cluster/srv_monitor.rb +1 -1
- data/lib/mongo/collection.rb +3 -3
- data/lib/mongo/collection/view.rb +1 -1
- data/lib/mongo/collection/view/aggregation.rb +1 -1
- data/lib/mongo/collection/view/change_stream.rb +12 -3
- data/lib/mongo/collection/view/iterable.rb +14 -5
- data/lib/mongo/collection/view/map_reduce.rb +2 -2
- data/lib/mongo/collection/view/readable.rb +7 -9
- data/lib/mongo/collection/view/writable.rb +7 -7
- data/lib/mongo/crypt.rb +33 -0
- data/lib/mongo/crypt/auto_decryption_context.rb +42 -0
- data/lib/mongo/crypt/auto_encrypter.rb +169 -0
- data/lib/mongo/crypt/auto_encryption_context.rb +44 -0
- data/lib/mongo/crypt/binary.rb +155 -0
- data/lib/mongo/crypt/binding.rb +1162 -0
- data/lib/mongo/crypt/context.rb +135 -0
- data/lib/mongo/crypt/data_key_context.rb +162 -0
- data/lib/mongo/crypt/encryption_io.rb +283 -0
- data/lib/mongo/crypt/explicit_decryption_context.rb +40 -0
- data/lib/mongo/crypt/explicit_encrypter.rb +117 -0
- data/lib/mongo/crypt/explicit_encryption_context.rb +89 -0
- data/lib/mongo/crypt/handle.rb +293 -0
- data/lib/mongo/crypt/hooks.rb +90 -0
- data/lib/mongo/crypt/kms_context.rb +67 -0
- data/lib/mongo/crypt/status.rb +131 -0
- data/lib/mongo/cursor.rb +64 -32
- data/lib/mongo/database.rb +13 -6
- data/lib/mongo/database/view.rb +13 -4
- data/lib/mongo/dbref.rb +9 -2
- data/lib/mongo/error.rb +5 -1
- data/lib/mongo/error/crypt_error.rb +31 -0
- data/lib/mongo/error/{failed_stringprep_validation.rb → failed_string_prep_validation.rb} +0 -0
- data/lib/mongo/error/invalid_cursor_operation.rb +27 -0
- data/lib/mongo/error/kms_error.rb +22 -0
- data/lib/mongo/error/max_bson_size.rb +14 -3
- data/lib/mongo/error/mongocryptd_spawn_error.rb +22 -0
- data/lib/mongo/error/no_server_available.rb +8 -3
- data/lib/mongo/error/operation_failure.rb +1 -0
- data/lib/mongo/grid/file.rb +0 -5
- data/lib/mongo/grid/file/chunk.rb +0 -2
- data/lib/mongo/grid/file/info.rb +2 -1
- data/lib/mongo/grid/fs_bucket.rb +13 -15
- data/lib/mongo/grid/stream/write.rb +3 -9
- data/lib/mongo/index/view.rb +3 -3
- data/lib/mongo/monitoring/event/command_started.rb +6 -1
- data/lib/mongo/operation/collections_info.rb +6 -3
- data/lib/mongo/operation/delete/op_msg.rb +1 -1
- data/lib/mongo/operation/find/op_msg.rb +4 -1
- data/lib/mongo/operation/get_more/op_msg.rb +4 -1
- data/lib/mongo/operation/insert/command.rb +2 -2
- data/lib/mongo/operation/insert/legacy.rb +2 -2
- data/lib/mongo/operation/insert/op_msg.rb +3 -3
- data/lib/mongo/operation/result.rb +36 -27
- data/lib/mongo/operation/shared/executable.rb +10 -8
- data/lib/mongo/operation/shared/executable_no_validate.rb +2 -2
- data/lib/mongo/operation/shared/op_msg_or_command.rb +2 -2
- data/lib/mongo/operation/shared/op_msg_or_find_command.rb +2 -2
- data/lib/mongo/operation/shared/op_msg_or_list_indexes_command.rb +2 -2
- data/lib/mongo/operation/shared/write.rb +17 -10
- data/lib/mongo/operation/update/op_msg.rb +1 -1
- data/lib/mongo/protocol/compressed.rb +6 -5
- data/lib/mongo/protocol/insert.rb +3 -1
- data/lib/mongo/protocol/message.rb +72 -8
- data/lib/mongo/protocol/msg.rb +191 -37
- data/lib/mongo/protocol/query.rb +7 -9
- data/lib/mongo/protocol/serializers.rb +6 -2
- data/lib/mongo/server.rb +10 -4
- data/lib/mongo/server/connection.rb +20 -9
- data/lib/mongo/server/connection_base.rb +81 -12
- data/lib/mongo/server/connection_common.rb +61 -0
- data/lib/mongo/server/connection_pool.rb +37 -1
- data/lib/mongo/server/description.rb +9 -11
- data/lib/mongo/server/monitor.rb +2 -0
- data/lib/mongo/server/monitor/connection.rb +3 -18
- data/lib/mongo/server/pending_connection.rb +2 -1
- data/lib/mongo/session.rb +2 -2
- data/lib/mongo/session/session_pool.rb +8 -3
- data/lib/mongo/socket.rb +29 -16
- data/lib/mongo/socket/ssl.rb +23 -8
- data/lib/mongo/socket/tcp.rb +12 -3
- data/lib/mongo/timeout.rb +49 -0
- data/lib/mongo/uri.rb +30 -1
- data/lib/mongo/version.rb +1 -1
- data/mongo.gemspec +1 -1
- data/spec/README.md +134 -7
- data/spec/integration/auth_spec.rb +53 -0
- data/spec/integration/{client_options_spec.rb → client_authentication_options_spec.rb} +10 -10
- data/spec/integration/client_construction_spec.rb +76 -1
- data/spec/integration/client_side_encryption/auto_encryption_bulk_writes_spec.rb +351 -0
- data/spec/integration/client_side_encryption/auto_encryption_command_monitoring_spec.rb +301 -0
- data/spec/integration/client_side_encryption/auto_encryption_mongocryptd_spawn_spec.rb +71 -0
- data/spec/integration/client_side_encryption/auto_encryption_old_wire_version_spec.rb +76 -0
- data/spec/integration/client_side_encryption/auto_encryption_reconnect_spec.rb +216 -0
- data/spec/integration/client_side_encryption/auto_encryption_spec.rb +600 -0
- data/spec/integration/client_side_encryption/bson_size_limit_spec.rb +183 -0
- data/spec/integration/client_side_encryption/bypass_mongocryptd_spawn_spec.rb +74 -0
- data/spec/integration/client_side_encryption/client_close_spec.rb +59 -0
- data/spec/integration/client_side_encryption/corpus_spec.rb +228 -0
- data/spec/integration/client_side_encryption/custom_endpoint_spec.rb +132 -0
- data/spec/integration/client_side_encryption/data_key_spec.rb +163 -0
- data/spec/integration/client_side_encryption/explicit_encryption_spec.rb +114 -0
- data/spec/integration/client_side_encryption/external_key_vault_spec.rb +137 -0
- data/spec/integration/client_side_encryption/views_spec.rb +42 -0
- data/spec/integration/client_update_spec.rb +120 -0
- data/spec/integration/command_monitoring_spec.rb +3 -1
- data/spec/integration/command_spec.rb +44 -10
- data/spec/integration/connection_spec.rb +57 -0
- data/spec/integration/reconnect_spec.rb +7 -6
- data/spec/integration/size_limit_spec.rb +94 -0
- data/spec/integration/srv_monitoring_spec.rb +14 -6
- data/spec/lite_spec_helper.rb +31 -22
- data/spec/mongo/auth/cr_spec.rb +8 -0
- data/spec/mongo/auth/ldap_spec.rb +5 -1
- data/spec/mongo/auth/scram/conversation_spec.rb +5 -6
- data/spec/mongo/auth/scram/negotiation_spec.rb +74 -75
- data/spec/mongo/auth/scram_spec.rb +45 -35
- data/spec/mongo/auth/x509_spec.rb +5 -1
- data/spec/mongo/client_construction_spec.rb +206 -3
- data/spec/mongo/client_encryption_spec.rb +408 -0
- data/spec/mongo/cluster/cursor_reaper_spec.rb +12 -8
- data/spec/mongo/cluster/socket_reaper_spec.rb +14 -3
- data/spec/mongo/collection/view/aggregation_spec.rb +0 -2
- data/spec/mongo/collection/view/change_stream_spec.rb +7 -7
- data/spec/mongo/collection/view/map_reduce_spec.rb +3 -3
- data/spec/mongo/collection/view_spec.rb +1 -1
- data/spec/mongo/collection_spec.rb +4 -33
- data/spec/mongo/crypt/auto_decryption_context_spec.rb +90 -0
- data/spec/mongo/crypt/auto_encrypter_spec.rb +182 -0
- data/spec/mongo/crypt/auto_encryption_context_spec.rb +107 -0
- data/spec/mongo/crypt/binary_spec.rb +115 -0
- data/spec/mongo/crypt/binding/binary_spec.rb +56 -0
- data/spec/mongo/crypt/binding/context_spec.rb +257 -0
- data/spec/mongo/crypt/binding/helpers_spec.rb +46 -0
- data/spec/mongo/crypt/binding/mongocrypt_spec.rb +144 -0
- data/spec/mongo/crypt/binding/status_spec.rb +99 -0
- data/spec/mongo/crypt/binding/version_spec.rb +22 -0
- data/spec/mongo/crypt/binding_unloaded_spec.rb +20 -0
- data/spec/mongo/crypt/data_key_context_spec.rb +213 -0
- data/spec/mongo/crypt/encryption_io_spec.rb +136 -0
- data/spec/mongo/crypt/explicit_decryption_context_spec.rb +72 -0
- data/spec/mongo/crypt/explicit_encryption_context_spec.rb +170 -0
- data/spec/mongo/crypt/handle_spec.rb +198 -0
- data/spec/mongo/crypt/helpers/mongo_crypt_spec_helper.rb +108 -0
- data/spec/mongo/crypt/status_spec.rb +152 -0
- data/spec/mongo/cursor_spec.rb +24 -4
- data/spec/mongo/database_spec.rb +20 -0
- data/spec/mongo/error/crypt_error_spec.rb +26 -0
- data/spec/mongo/error/max_bson_size_spec.rb +35 -0
- data/spec/mongo/error/no_server_available_spec.rb +11 -1
- data/spec/mongo/error/operation_failure_spec.rb +6 -6
- data/spec/mongo/operation/aggregate_spec.rb +1 -1
- data/spec/mongo/operation/collections_info_spec.rb +1 -1
- data/spec/mongo/operation/command_spec.rb +3 -3
- data/spec/mongo/operation/create_index_spec.rb +3 -3
- data/spec/mongo/operation/create_user_spec.rb +3 -3
- data/spec/mongo/operation/delete/bulk_spec.rb +6 -6
- data/spec/mongo/operation/delete/op_msg_spec.rb +1 -6
- data/spec/mongo/operation/delete_spec.rb +7 -7
- data/spec/mongo/operation/drop_index_spec.rb +2 -2
- data/spec/mongo/operation/find/legacy_spec.rb +1 -1
- data/spec/mongo/operation/get_more_spec.rb +1 -1
- data/spec/mongo/operation/indexes_spec.rb +1 -1
- data/spec/mongo/operation/insert/bulk_spec.rb +7 -7
- data/spec/mongo/operation/insert/op_msg_spec.rb +3 -6
- data/spec/mongo/operation/insert_spec.rb +12 -12
- data/spec/mongo/operation/map_reduce_spec.rb +2 -2
- data/spec/mongo/operation/remove_user_spec.rb +3 -3
- data/spec/mongo/operation/update/bulk_spec.rb +6 -6
- data/spec/mongo/operation/update/op_msg_spec.rb +3 -6
- data/spec/mongo/operation/update_spec.rb +7 -7
- data/spec/mongo/operation/update_user_spec.rb +1 -1
- data/spec/mongo/protocol/compressed_spec.rb +2 -3
- data/spec/mongo/protocol/delete_spec.rb +9 -8
- data/spec/mongo/protocol/get_more_spec.rb +9 -8
- data/spec/mongo/protocol/insert_spec.rb +9 -8
- data/spec/mongo/protocol/kill_cursors_spec.rb +6 -5
- data/spec/mongo/protocol/msg_spec.rb +57 -53
- data/spec/mongo/protocol/query_spec.rb +12 -12
- data/spec/mongo/protocol/registry_spec.rb +1 -1
- data/spec/mongo/protocol/reply_spec.rb +1 -1
- data/spec/mongo/protocol/update_spec.rb +10 -9
- data/spec/mongo/server/connection_pool_spec.rb +1 -1
- data/spec/mongo/server/connection_spec.rb +28 -7
- data/spec/mongo/socket_spec.rb +1 -1
- data/spec/mongo/timeout_spec.rb +85 -0
- data/spec/mongo/uri/srv_protocol_spec.rb +2 -2
- data/spec/mongo/uri_spec.rb +52 -5
- data/spec/mongo/write_concern_spec.rb +13 -1
- data/spec/{support → runners}/auth.rb +14 -1
- data/spec/{support → runners}/change_streams.rb +1 -1
- data/spec/{support → runners}/change_streams/operation.rb +0 -0
- data/spec/{support → runners}/cmap.rb +1 -1
- data/spec/{support → runners}/cmap/verifier.rb +0 -0
- data/spec/{support → runners}/command_monitoring.rb +0 -0
- data/spec/runners/connection_string.rb +358 -4
- data/spec/{support → runners}/crud.rb +9 -9
- data/spec/{support → runners}/crud/context.rb +0 -0
- data/spec/{support → runners}/crud/operation.rb +7 -3
- data/spec/{support → runners}/crud/outcome.rb +0 -0
- data/spec/{support → runners}/crud/requirement.rb +1 -1
- data/spec/{support → runners}/crud/spec.rb +12 -1
- data/spec/{support → runners}/crud/test.rb +0 -0
- data/spec/{support → runners}/crud/test_base.rb +0 -0
- data/spec/{support → runners}/crud/verifier.rb +10 -12
- data/spec/{support → runners}/gridfs.rb +0 -0
- data/spec/{support → runners}/sdam_monitoring.rb +0 -0
- data/spec/{support → runners}/server_discovery_and_monitoring.rb +0 -0
- data/spec/{support → runners}/server_selection.rb +0 -0
- data/spec/{support → runners}/server_selection_rtt.rb +0 -0
- data/spec/{support → runners}/transactions.rb +4 -4
- data/spec/{support → runners}/transactions/context.rb +0 -0
- data/spec/{support → runners}/transactions/operation.rb +0 -0
- data/spec/{support → runners}/transactions/spec.rb +0 -0
- data/spec/{support → runners}/transactions/test.rb +37 -5
- data/spec/spec_helper.rb +0 -5
- data/spec/spec_tests/auth_spec.rb +3 -3
- data/spec/spec_tests/client_side_encryption_spec.rb +13 -0
- data/spec/spec_tests/connection_string_spec.rb +1 -1
- data/spec/spec_tests/data/auth/connection-string.yml +13 -0
- data/spec/spec_tests/data/client_side_encryption/aggregate.yml +134 -0
- data/spec/spec_tests/data/client_side_encryption/badQueries.yml +526 -0
- data/spec/spec_tests/data/client_side_encryption/badSchema.yml +73 -0
- data/spec/spec_tests/data/client_side_encryption/basic.yml +116 -0
- data/spec/spec_tests/data/client_side_encryption/bulk.yml +85 -0
- data/spec/spec_tests/data/client_side_encryption/bypassAutoEncryption.yml +100 -0
- data/spec/spec_tests/data/client_side_encryption/bypassedCommand.yml +42 -0
- data/spec/spec_tests/data/client_side_encryption/count.yml +61 -0
- data/spec/spec_tests/data/client_side_encryption/countDocuments.yml +59 -0
- data/spec/spec_tests/data/client_side_encryption/delete.yml +105 -0
- data/spec/spec_tests/data/client_side_encryption/distinct.yml +73 -0
- data/spec/spec_tests/data/client_side_encryption/explain.yml +64 -0
- data/spec/spec_tests/data/client_side_encryption/find.yml +119 -0
- data/spec/spec_tests/data/client_side_encryption/findOneAndDelete.yml +57 -0
- data/spec/spec_tests/data/client_side_encryption/findOneAndReplace.yml +57 -0
- data/spec/spec_tests/data/client_side_encryption/findOneAndUpdate.yml +57 -0
- data/spec/spec_tests/data/client_side_encryption/getMore.yml +68 -0
- data/spec/spec_tests/data/client_side_encryption/insert.yml +102 -0
- data/spec/spec_tests/data/client_side_encryption/keyAltName.yml +71 -0
- data/spec/spec_tests/data/client_side_encryption/localKMS.yml +54 -0
- data/spec/spec_tests/data/client_side_encryption/localSchema.yml +72 -0
- data/spec/spec_tests/data/client_side_encryption/malformedCiphertext.yml +69 -0
- data/spec/spec_tests/data/client_side_encryption/maxWireVersion.yml +20 -0
- data/spec/spec_tests/data/client_side_encryption/missingKey.yml +49 -0
- data/spec/spec_tests/data/client_side_encryption/replaceOne.yml +61 -0
- data/spec/spec_tests/data/client_side_encryption/types.yml +527 -0
- data/spec/spec_tests/data/client_side_encryption/unsupportedCommand.yml +25 -0
- data/spec/spec_tests/data/client_side_encryption/updateMany.yml +77 -0
- data/spec/spec_tests/data/client_side_encryption/updateOne.yml +168 -0
- data/spec/spec_tests/data/read_write_concern/connection-string/write-concern.yml +1 -4
- data/spec/spec_tests/data/retryable_writes/insertOne-serverErrors.yml +21 -0
- data/spec/spec_tests/data/sdam/rs/incompatible_ghost.yml +2 -4
- data/spec/spec_tests/data/sdam/rs/incompatible_other.yml +1 -1
- data/spec/spec_tests/data/sdam/rs/primary_mismatched_me_not_removed.yml +73 -0
- data/spec/spec_tests/data/sdam/rs/primary_to_no_primary_mismatched_me.yml +1 -2
- data/spec/spec_tests/data/sdam/rs/repeated.yml +101 -0
- data/spec/spec_tests/data/sdam/rs/{primary_address_change.yml → ruby_primary_address_change.yml} +2 -0
- data/spec/spec_tests/data/sdam/rs/{secondary_wrong_set_name_with_primary_second.yml → ruby_secondary_wrong_set_name_with_primary_second.yml} +0 -0
- data/spec/spec_tests/data/sdam/sharded/ruby_discovered_single_mongos.yml +27 -0
- data/spec/spec_tests/data/sdam/sharded/{primary_address_change.yml → ruby_primary_different_address.yml} +1 -1
- data/spec/spec_tests/data/sdam/sharded/{primary_mismatched_me.yml → ruby_primary_mismatched_me.yml} +1 -1
- data/spec/spec_tests/data/sdam/single/{primary_address_change.yml → ruby_primary_different_address.yml} +1 -1
- data/spec/spec_tests/data/sdam/single/{primary_mismatched_me.yml → ruby_primary_mismatched_me.yml} +1 -1
- data/spec/spec_tests/data/sdam_monitoring/{replica_set_with_primary_change.yml → replica_set_primary_address_change.yml} +27 -5
- data/spec/spec_tests/data/sdam_monitoring/replica_set_with_me_mismatch.yml +26 -74
- data/spec/spec_tests/data/sdam_monitoring/replica_set_with_removal.yml +20 -16
- data/spec/spec_tests/data/sdam_monitoring/standalone_suppress_equal_description_changes.yml +73 -0
- data/spec/spec_tests/data/transactions/pin-mongos.yml +2 -3
- data/spec/spec_tests/data/uri_options/auth-options.yml +10 -0
- data/spec/spec_tests/data/uri_options/tls-options.yml +75 -4
- data/spec/spec_tests/read_write_concern_connection_string_spec.rb +1 -1
- data/spec/spec_tests/uri_options_spec.rb +6 -8
- data/spec/stress/connection_pool_timing_spec.rb +6 -3
- data/spec/support/certificates/README.md +4 -0
- data/spec/support/certificates/server-second-level-bundle.pem +77 -77
- data/spec/support/certificates/server-second-level.crt +52 -52
- data/spec/support/certificates/server-second-level.key +25 -25
- data/spec/support/certificates/server-second-level.pem +77 -77
- data/spec/support/client_registry.rb +19 -3
- data/spec/support/cluster_config.rb +9 -1
- data/spec/support/common_shortcuts.rb +12 -0
- data/spec/support/constraints.rb +16 -0
- data/spec/support/crypt.rb +140 -0
- data/spec/support/crypt/corpus/corpus-key-aws.json +33 -0
- data/spec/support/crypt/corpus/corpus-key-local.json +31 -0
- data/spec/support/crypt/corpus/corpus-schema.json +2057 -0
- data/spec/support/crypt/corpus/corpus.json +3657 -0
- data/spec/support/crypt/corpus/corpus_encrypted.json +4152 -0
- data/spec/support/crypt/data_keys/key_document_aws.json +34 -0
- data/spec/support/crypt/data_keys/key_document_local.json +31 -0
- data/spec/support/crypt/external/external-key.json +31 -0
- data/spec/support/crypt/external/external-schema.json +19 -0
- data/spec/support/crypt/limits/limits-doc.json +102 -0
- data/spec/support/crypt/limits/limits-key.json +31 -0
- data/spec/support/crypt/limits/limits-schema.json +1405 -0
- data/spec/support/crypt/schema_maps/schema_map_aws.json +17 -0
- data/spec/support/crypt/schema_maps/schema_map_aws_key_alt_names.json +12 -0
- data/spec/support/crypt/schema_maps/schema_map_local.json +18 -0
- data/spec/support/crypt/schema_maps/schema_map_local_key_alt_names.json +12 -0
- data/spec/support/lite_constraints.rb +17 -1
- data/spec/support/matchers.rb +19 -0
- data/spec/support/shared/protocol.rb +2 -0
- data/spec/support/spec_config.rb +43 -13
- data/spec/support/utils.rb +132 -10
- metadata +277 -81
- metadata.gz.sig +0 -0
- data/spec/integration/grid_fs_bucket_spec.rb +0 -48
- data/spec/integration/zlib_compression_spec.rb +0 -25
- data/spec/spec_tests/data/sdam/sharded/single_mongos.yml +0 -33
- data/spec/support/connection_string.rb +0 -354
@@ -46,8 +46,10 @@ module Mongo
|
|
46
46
|
# @param options [Hash] Additional options for the insertion.
|
47
47
|
#
|
48
48
|
# @option options :flags [Array] The flags for the insertion message.
|
49
|
-
#
|
50
49
|
# Supported flags: +:continue_on_error+
|
50
|
+
# @option options [ true, false ] validating_keys Whether keys should be
|
51
|
+
# validated for being valid document keys (i.e. not begin with $ and
|
52
|
+
# not contain dots).
|
51
53
|
def initialize(database, collection, documents, options = {})
|
52
54
|
@database = database
|
53
55
|
@namespace = "#{database}.#{collection}"
|
@@ -95,27 +95,84 @@ module Mongo
|
|
95
95
|
false
|
96
96
|
end
|
97
97
|
|
98
|
-
# Compress
|
98
|
+
# Compress the message, if supported by the wire protocol used and if
|
99
|
+
# the command being sent permits compression. Otherwise returns self.
|
99
100
|
#
|
100
101
|
# @param [ String, Symbol ] compressor The compressor to use.
|
101
102
|
# @param [ Integer ] zlib_compression_level The zlib compression level to use.
|
102
103
|
#
|
103
|
-
# @return [ self ] Always returns self. Other message types should
|
104
|
+
# @return [ self ] Always returns self. Other message types should
|
105
|
+
# override this method.
|
104
106
|
#
|
105
107
|
# @since 2.5.0
|
106
|
-
|
108
|
+
# @api private
|
109
|
+
def maybe_compress(compressor, zlib_compression_level = nil)
|
107
110
|
self
|
108
111
|
end
|
109
112
|
|
110
|
-
#
|
113
|
+
# Compress the message, if the command being sent permits compression.
|
114
|
+
# Otherwise returns self.
|
111
115
|
#
|
112
|
-
# @
|
116
|
+
# @param [ String ] command_name Command name extracted from the message.
|
117
|
+
# @param [ String | Symbol ] compressor The compressor to use.
|
118
|
+
# @param [ Integer ] zlib_compression_level Zlib compression level to use.
|
119
|
+
#
|
120
|
+
# @return [ Message ] A Protocol::Compressed message or self,
|
121
|
+
# depending on whether this message can be compressed.
|
122
|
+
#
|
123
|
+
# @since 2.5.0
|
124
|
+
private def compress_if_possible(command_name, compressor, zlib_compression_level)
|
125
|
+
if compressor && compression_allowed?(command_name)
|
126
|
+
Compressed.new(self, compressor, zlib_compression_level)
|
127
|
+
else
|
128
|
+
self
|
129
|
+
end
|
130
|
+
end
|
131
|
+
|
132
|
+
# Inflate a message if it is compressed.
|
133
|
+
#
|
134
|
+
# @return [ Protocol::Message ] Always returns self. Subclasses should
|
135
|
+
# override this method as necessary.
|
113
136
|
#
|
114
137
|
# @since 2.5.0
|
115
|
-
|
138
|
+
# @api private
|
139
|
+
def maybe_inflate
|
140
|
+
self
|
141
|
+
end
|
142
|
+
|
143
|
+
def maybe_decrypt(client)
|
144
|
+
# TODO determine if we should be decrypting data coming from pre-4.2
|
145
|
+
# servers, potentially using legacy wire protocols. If so we need
|
146
|
+
# to implement decryption for those wire protocols as our current
|
147
|
+
# encryption/decryption code is OP_MSG-specific.
|
116
148
|
self
|
117
149
|
end
|
118
150
|
|
151
|
+
def maybe_encrypt(server, client)
|
152
|
+
# Do nothing if the Message subclass has not implemented this method
|
153
|
+
self
|
154
|
+
end
|
155
|
+
|
156
|
+
private def merge_sections
|
157
|
+
cmd = if @sections.length > 1
|
158
|
+
cmd = @sections.detect { |section| section[:type] == 0 }[:payload]
|
159
|
+
identifier = @sections.detect { |section| section[:type] == 1}[:payload][:identifier]
|
160
|
+
cmd.merge(identifier.to_sym =>
|
161
|
+
@sections.select { |section| section[:type] == 1 }.
|
162
|
+
map { |section| section[:payload][:sequence] }.
|
163
|
+
inject([]) { |arr, documents| arr + documents }
|
164
|
+
)
|
165
|
+
elsif @sections.first[:payload]
|
166
|
+
@sections.first[:payload]
|
167
|
+
else
|
168
|
+
@sections.first
|
169
|
+
end
|
170
|
+
if cmd.nil?
|
171
|
+
raise "The command should never be nil here"
|
172
|
+
end
|
173
|
+
cmd
|
174
|
+
end
|
175
|
+
|
119
176
|
# Serializes message into bytes that can be sent on the wire
|
120
177
|
#
|
121
178
|
# @param buffer [String] buffer where the message should be inserted
|
@@ -129,7 +186,11 @@ module Mongo
|
|
129
186
|
|
130
187
|
alias_method :to_s, :serialize
|
131
188
|
|
132
|
-
# Deserializes messages from an IO stream
|
189
|
+
# Deserializes messages from an IO stream.
|
190
|
+
#
|
191
|
+
# This method returns decompressed messages (i.e. if the message on the
|
192
|
+
# wire was OP_COMPRESSED, this method would typically return the OP_MSG
|
193
|
+
# message that is the result of decompression).
|
133
194
|
#
|
134
195
|
# @param [ Integer ] max_message_size The max message size.
|
135
196
|
# @param [ IO ] io Stream containing a message
|
@@ -160,7 +221,10 @@ module Mongo
|
|
160
221
|
deserialize_field(message, buffer, field)
|
161
222
|
end
|
162
223
|
end
|
163
|
-
message.
|
224
|
+
if message.is_a?(Msg)
|
225
|
+
message.fix_after_deserialization
|
226
|
+
end
|
227
|
+
message.maybe_inflate
|
164
228
|
end
|
165
229
|
|
166
230
|
# Tests for equality between two wire protocol messages
|
data/lib/mongo/protocol/msg.rb
CHANGED
@@ -35,7 +35,7 @@ module Mongo
|
|
35
35
|
# moved to the end of the hash for better logging.
|
36
36
|
#
|
37
37
|
# @api private
|
38
|
-
INTERNAL_KEYS = Set.new(%w($clusterTime lsid signature txnNumber)).freeze
|
38
|
+
INTERNAL_KEYS = Set.new(%w($clusterTime $db lsid signature txnNumber)).freeze
|
39
39
|
|
40
40
|
# Creates a new OP_MSG protocol message
|
41
41
|
#
|
@@ -44,25 +44,42 @@ module Mongo
|
|
44
44
|
# { type: 1, payload: { identifier: 'documents', sequence: [..] } })
|
45
45
|
#
|
46
46
|
# @param [ Array<Symbol> ] flags The flag bits. Current supported values
|
47
|
-
#
|
48
|
-
# @param [ Hash ] options The options.
|
49
|
-
#
|
50
|
-
#
|
51
|
-
#
|
52
|
-
# @param [
|
53
|
-
#
|
54
|
-
# { type: 0, payload: <BSON::Document, Hash> }
|
47
|
+
# are :more_to_come and :checksum_present.
|
48
|
+
# @param [ Hash ] options The options.
|
49
|
+
# @param [ BSON::Document, Hash ] main_document The document that will
|
50
|
+
# become the payload type 0 section. Can contain global args as they
|
51
|
+
# are defined in the OP_MSG specification.
|
52
|
+
# @param [ Protocol::Msg::Section1 ] sequences Zero or more payload type 1
|
53
|
+
# sections.
|
55
54
|
#
|
56
|
-
# @option options [ true, false ] validating_keys Whether keys should be
|
55
|
+
# @option options [ true, false ] validating_keys Whether keys should be
|
56
|
+
# validated for being valid document keys (i.e. not begin with $ and
|
57
|
+
# not contain dots).
|
57
58
|
#
|
58
59
|
# @api private
|
59
60
|
#
|
60
61
|
# @since 2.5.0
|
61
|
-
def initialize(flags, options,
|
62
|
+
def initialize(flags, options, main_document, *sequences)
|
62
63
|
@flags = flags || []
|
63
64
|
@options = options
|
64
|
-
|
65
|
-
|
65
|
+
unless main_document.is_a?(Hash)
|
66
|
+
raise ArgumentError, "Main document must be a Hash, given: #{main_document.class}"
|
67
|
+
end
|
68
|
+
@main_document = main_document
|
69
|
+
sequences.each_with_index do |section, index|
|
70
|
+
unless section.is_a?(Section1)
|
71
|
+
raise ArgumentError, "All sequences must be Section1 instances, got: #{section} at index #{index}"
|
72
|
+
end
|
73
|
+
end
|
74
|
+
@sequences = sequences
|
75
|
+
@sections = [
|
76
|
+
{type: 0, payload: @main_document}
|
77
|
+
] + @sequences.map do |section|
|
78
|
+
{type: 1, payload: {
|
79
|
+
identifier: section.identifier,
|
80
|
+
sequence: section.documents,
|
81
|
+
}}
|
82
|
+
end
|
66
83
|
@request_id = nil
|
67
84
|
super
|
68
85
|
end
|
@@ -88,11 +105,11 @@ module Mongo
|
|
88
105
|
#
|
89
106
|
# @since 2.5.0
|
90
107
|
def payload
|
91
|
-
# Reorder keys in
|
108
|
+
# Reorder keys in main_document for better logging - see
|
92
109
|
# https://jira.mongodb.org/browse/RUBY-1591.
|
93
110
|
# Note that even without the reordering, the payload is not an exact
|
94
111
|
# match to what is sent over the wire because the command as used in
|
95
|
-
# the published
|
112
|
+
# the published event combines keys from multiple sections of the
|
96
113
|
# payload sent over the wire.
|
97
114
|
ordered_command = {}
|
98
115
|
skipped_command = {}
|
@@ -107,10 +124,10 @@ module Mongo
|
|
107
124
|
|
108
125
|
BSON::Document.new(
|
109
126
|
command_name: ordered_command.keys.first.to_s,
|
110
|
-
database_name:
|
127
|
+
database_name: @main_document[DATABASE_IDENTIFIER],
|
111
128
|
command: ordered_command,
|
112
129
|
request_id: request_id,
|
113
|
-
reply:
|
130
|
+
reply: @main_document,
|
114
131
|
)
|
115
132
|
end
|
116
133
|
|
@@ -128,35 +145,142 @@ module Mongo
|
|
128
145
|
buffer
|
129
146
|
end
|
130
147
|
|
131
|
-
# Compress
|
148
|
+
# Compress the message, if the command being sent permits compression.
|
149
|
+
# Otherwise returns self.
|
132
150
|
#
|
133
151
|
# @param [ String, Symbol ] compressor The compressor to use.
|
134
152
|
# @param [ Integer ] zlib_compression_level The zlib compression level to use.
|
135
153
|
#
|
136
|
-
# @return [
|
137
|
-
# this message can be compressed.
|
154
|
+
# @return [ Message ] A Protocol::Compressed message or self,
|
155
|
+
# depending on whether this message can be compressed.
|
138
156
|
#
|
139
157
|
# @since 2.5.0
|
140
|
-
|
141
|
-
|
142
|
-
|
158
|
+
# @api private
|
159
|
+
def maybe_compress(compressor, zlib_compression_level = nil)
|
160
|
+
compress_if_possible(command.keys.first, compressor, zlib_compression_level)
|
161
|
+
end
|
162
|
+
|
163
|
+
# Reverse-populates the instance variables after deserialization sets
|
164
|
+
# @sections to the list of documents.
|
165
|
+
#
|
166
|
+
# TODO fix deserialization so that this method is not needed.
|
167
|
+
#
|
168
|
+
# @api private
|
169
|
+
def fix_after_deserialization
|
170
|
+
if @sections.nil?
|
171
|
+
raise NotImplementedError, "After deserializations @sections should have been initialized"
|
172
|
+
end
|
173
|
+
if @sections.length != 1
|
174
|
+
raise NotImplementedError, "Deserialization must have produced exactly one section, but it produced #{sections.length} sections"
|
175
|
+
end
|
176
|
+
@main_document = @sections.first
|
177
|
+
@sequences = []
|
178
|
+
@sections = [{type: 0, payload: @main_document}]
|
179
|
+
end
|
180
|
+
|
181
|
+
def documents
|
182
|
+
[@main_document]
|
183
|
+
end
|
184
|
+
|
185
|
+
# Possibly encrypt this message with libmongocrypt. Message will only be
|
186
|
+
# encrypted if the specified client exists, that client has been given
|
187
|
+
# auto-encryption options, the client has not been instructed to bypass
|
188
|
+
# auto-encryption, and mongocryptd determines that this message is
|
189
|
+
# eligible for encryption. A message is eligible for encryption if it
|
190
|
+
# represents one of the command types whitelisted by libmongocrypt and it
|
191
|
+
# contains data that is required to be encrypted by a local or remote json schema.
|
192
|
+
#
|
193
|
+
# @param [ Mongo::Client | nil ] client The client used to make the original
|
194
|
+
# command. This client may have auto-encryption options specified.
|
195
|
+
#
|
196
|
+
# @return [ Mongo::Protocol::Msg ] The encrypted message, or the original
|
197
|
+
# message if encryption was not possible or necessary.
|
198
|
+
def maybe_encrypt(server, client)
|
199
|
+
# TODO verify compression happens later, i.e. when this method runs
|
200
|
+
# the message is not compressed.
|
201
|
+
if client && client.encrypter && client.encrypter.encrypt?
|
202
|
+
if server.max_wire_version < 8
|
203
|
+
raise Error::CryptError.new(
|
204
|
+
"Cannot perform encryption against a MongoDB server older than " +
|
205
|
+
"4.2 (wire version less than 8). Currently connected to server " +
|
206
|
+
"with max wire version #{server.max_wire_version}} " +
|
207
|
+
"(Auto-encryption requires a minimum MongoDB version of 4.2)"
|
208
|
+
)
|
209
|
+
end
|
210
|
+
|
211
|
+
db_name = @main_document[DATABASE_IDENTIFIER]
|
212
|
+
cmd = merge_sections
|
213
|
+
enc_cmd = client.encrypter.encrypt(db_name, cmd)
|
214
|
+
if cmd.key?('$db') && !enc_cmd.key?('$db')
|
215
|
+
enc_cmd['$db'] = cmd['$db']
|
216
|
+
end
|
217
|
+
# This will be investigtated in RUBY-2119
|
218
|
+
if enc_cmd['txnNumber'].is_a?(Integer) && cmd[:txnNumber].is_a?(BSON::Int64)
|
219
|
+
enc_cmd['txnNumber'] = BSON::Int64.new(enc_cmd[:txnNumber])
|
220
|
+
end
|
221
|
+
Msg.new(@flags, @options, enc_cmd)
|
143
222
|
else
|
144
223
|
self
|
145
224
|
end
|
146
225
|
end
|
147
226
|
|
227
|
+
# Possibly decrypt this message with libmongocrypt. Message will only be
|
228
|
+
# decrypted if the specified client exists, that client has been given
|
229
|
+
# auto-encryption options, and this message is eligible for decryption.
|
230
|
+
# A message is eligible for decryption if it represents one of the command
|
231
|
+
# types whitelisted by libmongocrypt and it contains data that is required
|
232
|
+
# to be encrypted by a local or remote json schema.
|
233
|
+
#
|
234
|
+
# @param [ Mongo::Client | nil ] client The client used to make the original
|
235
|
+
# command. This client may have auto-encryption options specified.
|
236
|
+
#
|
237
|
+
# @return [ Mongo::Protocol::Msg ] The decryption message, or the original
|
238
|
+
# message if decryption was not possible or necessary.
|
239
|
+
def maybe_decrypt(client)
|
240
|
+
if client && client.encrypter
|
241
|
+
cmd = merge_sections
|
242
|
+
enc_cmd = client.encrypter.decrypt(cmd)
|
243
|
+
Msg.new(@flags, @options, enc_cmd)
|
244
|
+
else
|
245
|
+
self
|
246
|
+
end
|
247
|
+
end
|
248
|
+
|
249
|
+
# Whether this message represents a bulk write. A bulk write is an insert,
|
250
|
+
# update, or delete operation that encompasses multiple operations of
|
251
|
+
# the same type.
|
252
|
+
#
|
253
|
+
# @return [ Boolean ] Whether this message represents a bulk write.
|
254
|
+
#
|
255
|
+
# @note This method was written to support client-side encryption
|
256
|
+
# functionality. It is not recommended that this method be used in
|
257
|
+
# service of any other feature or behavior.
|
258
|
+
#
|
259
|
+
# @api private
|
260
|
+
def bulk_write?
|
261
|
+
inserts = @main_document['documents']
|
262
|
+
updates = @main_document['updates']
|
263
|
+
deletes = @main_document['deletes']
|
264
|
+
|
265
|
+
num_inserts = inserts && inserts.length || 0
|
266
|
+
num_updates = updates && updates.length || 0
|
267
|
+
num_deletes = deletes && deletes.length || 0
|
268
|
+
|
269
|
+
num_inserts > 1 || num_updates > 1 || num_deletes > 1
|
270
|
+
end
|
271
|
+
|
148
272
|
private
|
149
273
|
|
150
274
|
def command
|
151
|
-
@command ||=
|
152
|
-
cmd
|
153
|
-
|
154
|
-
|
155
|
-
identifier
|
156
|
-
cmd[identifier] ||= []
|
157
|
-
cmd[identifier] += section[:payload][:sequence]
|
275
|
+
@command ||= if @main_document
|
276
|
+
@main_document.dup.tap do |cmd|
|
277
|
+
@sequences.each do |section|
|
278
|
+
cmd[section.identifier] ||= []
|
279
|
+
cmd[section.identifier] += section.documents
|
158
280
|
end
|
159
281
|
end
|
282
|
+
else
|
283
|
+
documents.first
|
160
284
|
end
|
161
285
|
end
|
162
286
|
|
@@ -166,8 +290,24 @@ module Mongo
|
|
166
290
|
end
|
167
291
|
end
|
168
292
|
|
169
|
-
|
170
|
-
|
293
|
+
# Encapsulates a type 1 OP_MSG section.
|
294
|
+
#
|
295
|
+
# @see https://github.com/mongodb/specifications/blob/master/source/message/OP_MSG.rst#sections
|
296
|
+
#
|
297
|
+
# @api private
|
298
|
+
class Section1
|
299
|
+
def initialize(identifier, documents)
|
300
|
+
@identifier, @documents = identifier, documents
|
301
|
+
end
|
302
|
+
|
303
|
+
attr_reader :identifier, :documents
|
304
|
+
|
305
|
+
def ==(other)
|
306
|
+
other.is_a?(Section1) &&
|
307
|
+
identifier == other.identifier && documents == other.documents
|
308
|
+
end
|
309
|
+
|
310
|
+
alias :eql? :==
|
171
311
|
end
|
172
312
|
|
173
313
|
# The operation code required to specify a OP_MSG message.
|
@@ -177,19 +317,33 @@ module Mongo
|
|
177
317
|
OP_CODE = 2013
|
178
318
|
|
179
319
|
# Available flags for a OP_MSG message.
|
180
|
-
FLAGS = Array.new(16).tap
|
320
|
+
FLAGS = Array.new(16).tap do |arr|
|
181
321
|
arr[0] = :checksum_present
|
182
322
|
arr[1] = :more_to_come
|
183
|
-
|
323
|
+
end.freeze
|
184
324
|
|
185
325
|
# @!attribute
|
186
326
|
# @return [Array<Symbol>] The flags for this message.
|
187
327
|
field :flags, BitVector.new(FLAGS)
|
188
328
|
|
189
|
-
#
|
190
|
-
#
|
329
|
+
# The sections that will be serialized, or the documents have been
|
330
|
+
# deserialized.
|
331
|
+
#
|
332
|
+
# Usually the sections contain OP_MSG-compliant sections derived
|
333
|
+
# from @main_document and @sequences. The information in @main_document
|
334
|
+
# and @sequences is duplicated in the sections.
|
335
|
+
#
|
336
|
+
# When deserializing Msg instances, sections temporarily is an array
|
337
|
+
# of documents returned in the type 0 section of the OP_MSG wire
|
338
|
+
# protocol message. #fix_after_deserialization method mutates this
|
339
|
+
# object to have sections, @main_document and @sequences be what
|
340
|
+
# they would have been had the Msg instance been constructed using
|
341
|
+
# the constructor (rather than having been deserialized).
|
342
|
+
#
|
343
|
+
# @return [ Array<Hash> | Array<BSON::Document> ] The sections of
|
344
|
+
# payload type 1 or 0.
|
345
|
+
# @api private
|
191
346
|
field :sections, Sections
|
192
|
-
alias :documents :sections
|
193
347
|
|
194
348
|
Registry.register(OP_CODE, self)
|
195
349
|
end
|
data/lib/mongo/protocol/query.rb
CHANGED
@@ -100,21 +100,19 @@ module Mongo
|
|
100
100
|
true
|
101
101
|
end
|
102
102
|
|
103
|
-
# Compress
|
103
|
+
# Compress the message, if the command being sent permits compression.
|
104
|
+
# Otherwise returns self.
|
104
105
|
#
|
105
106
|
# @param [ String, Symbol ] compressor The compressor to use.
|
106
107
|
# @param [ Integer ] zlib_compression_level The zlib compression level to use.
|
107
108
|
#
|
108
|
-
# @return [
|
109
|
-
# this message can be compressed.
|
109
|
+
# @return [ Message ] A Protocol::Compressed message or self,
|
110
|
+
# depending on whether this message can be compressed.
|
110
111
|
#
|
111
112
|
# @since 2.5.0
|
112
|
-
|
113
|
-
|
114
|
-
|
115
|
-
else
|
116
|
-
self
|
117
|
-
end
|
113
|
+
# @api private
|
114
|
+
def maybe_compress(compressor, zlib_compression_level = nil)
|
115
|
+
compress_if_possible(selector.keys.first, compressor, zlib_compression_level)
|
118
116
|
end
|
119
117
|
|
120
118
|
protected
|