mongo 2.0.2 → 2.0.3
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- checksums.yaml.gz.sig +0 -0
- data.tar.gz.sig +0 -0
- data/lib/mongo/address.rb +70 -11
- data/lib/mongo/address/ipv4.rb +23 -22
- data/lib/mongo/address/ipv6.rb +23 -22
- data/lib/mongo/address/unix.rb +18 -18
- data/lib/mongo/auth.rb +0 -1
- data/lib/mongo/auth/cr.rb +21 -2
- data/lib/mongo/auth/cr/conversation.rb +7 -4
- data/lib/mongo/auth/ldap.rb +14 -1
- data/lib/mongo/auth/scram.rb +15 -1
- data/lib/mongo/auth/scram/conversation.rb +3 -3
- data/lib/mongo/auth/user.rb +1 -1
- data/lib/mongo/auth/x509.rb +15 -1
- data/lib/mongo/cluster.rb +22 -8
- data/lib/mongo/cluster/topology.rb +7 -6
- data/lib/mongo/cluster/topology/replica_set.rb +5 -5
- data/lib/mongo/cluster/topology/sharded.rb +5 -5
- data/lib/mongo/cluster/topology/{standalone.rb → single.rb} +26 -22
- data/lib/mongo/cluster/topology/unknown.rb +6 -5
- data/lib/mongo/collection.rb +6 -1
- data/lib/mongo/collection/view.rb +1 -0
- data/lib/mongo/collection/view/readable.rb +5 -0
- data/lib/mongo/error.rb +4 -0
- data/lib/mongo/error/invalid_document.rb +1 -1
- data/lib/mongo/error/invalid_server_preference.rb +36 -0
- data/lib/mongo/error/invalid_uri.rb +37 -0
- data/lib/mongo/error/invalid_uri_option.rb +38 -0
- data/lib/mongo/error/no_server_available.rb +37 -0
- data/lib/mongo/operation/read_preferrable.rb +20 -4
- data/lib/mongo/protocol/query.rb +14 -1
- data/lib/mongo/server.rb +12 -0
- data/lib/mongo/server/connectable.rb +5 -1
- data/lib/mongo/server/connection.rb +1 -1
- data/lib/mongo/server/context.rb +2 -1
- data/lib/mongo/server_selector.rb +0 -19
- data/lib/mongo/server_selector/selectable.rb +4 -22
- data/lib/mongo/uri.rb +9 -55
- data/lib/mongo/version.rb +1 -1
- data/spec/mongo/address/ipv4_spec.rb +27 -6
- data/spec/mongo/address/ipv6_spec.rb +27 -6
- data/spec/mongo/address/unix_spec.rb +15 -4
- data/spec/mongo/auth/cr_spec.rb +2 -2
- data/spec/mongo/auth/ldap_spec.rb +2 -2
- data/spec/mongo/auth/scram_spec.rb +2 -2
- data/spec/mongo/auth/x509_spec.rb +2 -2
- data/spec/mongo/client_spec.rb +8 -0
- data/spec/mongo/cluster/topology/replica_set_spec.rb +6 -6
- data/spec/mongo/cluster/topology/sharded_spec.rb +5 -5
- data/spec/mongo/cluster/topology/{standalone_spec.rb → single_spec.rb} +7 -7
- data/spec/mongo/cluster/topology_spec.rb +31 -5
- data/spec/mongo/cluster_spec.rb +103 -21
- data/spec/mongo/collection/view/readable_spec.rb +18 -7
- data/spec/mongo/collection/view_spec.rb +13 -0
- data/spec/mongo/collection_spec.rb +7 -0
- data/spec/mongo/database_spec.rb +2 -2
- data/spec/mongo/protocol/query_spec.rb +29 -0
- data/spec/mongo/server/connection_pool_spec.rb +4 -4
- data/spec/mongo/server/connection_spec.rb +46 -10
- data/spec/mongo/server/monitor_spec.rb +2 -2
- data/spec/mongo/server_discovery_and_monitoring_spec.rb +23 -0
- data/spec/mongo/server_selection_rtt_spec.rb +2 -1
- data/spec/mongo/server_selection_spec.rb +6 -15
- data/spec/mongo/server_selector/nearest_spec.rb +1 -1
- data/spec/mongo/server_selector_spec.rb +53 -2
- data/spec/mongo/server_spec.rb +9 -9
- data/spec/mongo/socket/ssl_spec.rb +1 -1
- data/spec/mongo/uri_spec.rb +2 -2
- data/spec/spec_helper.rb +34 -5
- data/spec/support/authorization.rb +32 -46
- data/spec/support/server_discovery_and_monitoring.rb +1 -1
- data/spec/support/server_selection.rb +1 -25
- data/spec/support/shared/operation.rb +3 -0
- data/spec/support/shared/server_selector.rb +1 -1
- metadata +10 -7
- metadata.gz.sig +0 -0
- data/lib/mongo/auth/executable.rb +0 -52
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 7b0437cd0c5d8bb2f5500c239a8814d634c80499
|
4
|
+
data.tar.gz: bed04278506ef47a820421a872f5850ab8f01a7d
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 9d790a1e9b2f1e97c2b354e22daf0ec5d6552c438f5d59c3d84e98ab57c42fec8f4cc4d81699569efde84840d3b41e5f9417c0aa536f0d51af1f39ce3c8368fa
|
7
|
+
data.tar.gz: d9417be0c394836c30d60a0bf4a1199003b56866a39f3630aea96e9647a3ef27040c9d1df9a7acc6c068718da4bee16bdb982c6feb3fae13ef7218280059e9e3
|
checksums.yaml.gz.sig
CHANGED
Binary file
|
data.tar.gz.sig
CHANGED
Binary file
|
data/lib/mongo/address.rb
CHANGED
@@ -25,13 +25,22 @@ module Mongo
|
|
25
25
|
class Address
|
26
26
|
extend Forwardable
|
27
27
|
|
28
|
-
#
|
28
|
+
# Mapping from socket family to resolver class.
|
29
29
|
#
|
30
30
|
# @since 2.0.0
|
31
|
-
|
31
|
+
FAMILY_MAP = { ::Socket::PF_UNIX => Unix,
|
32
|
+
::Socket::AF_INET6 => IPv6,
|
33
|
+
::Socket::AF_INET => IPv4
|
34
|
+
}
|
32
35
|
|
33
|
-
# @return [
|
34
|
-
attr_reader :
|
36
|
+
# @return [ String ] seed The seed address.
|
37
|
+
attr_reader :seed
|
38
|
+
|
39
|
+
# @return [ String ] host The original host name.
|
40
|
+
attr_reader :host
|
41
|
+
|
42
|
+
# @return [ Integer ] port The port.
|
43
|
+
attr_reader :port
|
35
44
|
|
36
45
|
# Check equality of the address to another.
|
37
46
|
#
|
@@ -88,12 +97,8 @@ module Mongo
|
|
88
97
|
#
|
89
98
|
# @since 2.0.0
|
90
99
|
def initialize(seed, options = {})
|
91
|
-
|
92
|
-
|
93
|
-
when Unix::MATCH then @resolver = Unix.new(address)
|
94
|
-
when IPv6::MATCH then @resolver = IPv6.new(address)
|
95
|
-
else @resolver = IPv4.new(address)
|
96
|
-
end
|
100
|
+
@seed = seed
|
101
|
+
@host, @port = parse_host_port
|
97
102
|
end
|
98
103
|
|
99
104
|
# Get a pretty printed address inspection.
|
@@ -105,7 +110,61 @@ module Mongo
|
|
105
110
|
#
|
106
111
|
# @since 2.0.0
|
107
112
|
def inspect
|
108
|
-
"#<Mongo::Address:0x#{object_id} address=#{
|
113
|
+
"#<Mongo::Address:0x#{object_id} address=#{to_s}>"
|
114
|
+
end
|
115
|
+
|
116
|
+
# Get a socket for the provided address, given the options.
|
117
|
+
#
|
118
|
+
# @example Get a socket.
|
119
|
+
# address.socket(5, :ssl => true)
|
120
|
+
#
|
121
|
+
# @param [ Float ] timeout The socket timeout.
|
122
|
+
# @param [ Hash ] ssl_options SSL options.
|
123
|
+
#
|
124
|
+
# @return [ Pool::Socket::SSL, Pool::Socket::TCP, Pool::Socket::Unix ] The socket.
|
125
|
+
#
|
126
|
+
# @since 2.0.0
|
127
|
+
def socket(timeout, ssl_options = {})
|
128
|
+
@resolver ||= initialize_resolver!(timeout, ssl_options)
|
129
|
+
@resolver.socket(timeout, ssl_options)
|
130
|
+
end
|
131
|
+
|
132
|
+
# Get the address as a string.
|
133
|
+
#
|
134
|
+
# @example Get the address as a string.
|
135
|
+
# address.to_s
|
136
|
+
#
|
137
|
+
# @return [ String ] The nice string.
|
138
|
+
#
|
139
|
+
# @since 2.0.0
|
140
|
+
def to_s
|
141
|
+
port ? "#{host}:#{port}" : host
|
142
|
+
end
|
143
|
+
|
144
|
+
private
|
145
|
+
|
146
|
+
def initialize_resolver!(timeout, ssl_options)
|
147
|
+
family = (host == 'localhost') ? ::Socket::AF_INET : ::Socket::AF_UNSPEC
|
148
|
+
error = nil
|
149
|
+
::Socket.getaddrinfo(host, nil, family, ::Socket::SOCK_STREAM).detect do |info|
|
150
|
+
begin
|
151
|
+
return FAMILY_MAP[info[4]].new(host, port).tap do |res|
|
152
|
+
res.socket(timeout, ssl_options).connect!
|
153
|
+
end
|
154
|
+
rescue IOError, SystemCallError => e
|
155
|
+
error = e
|
156
|
+
end
|
157
|
+
end
|
158
|
+
raise error
|
159
|
+
end
|
160
|
+
|
161
|
+
def parse_host_port
|
162
|
+
address = seed.downcase
|
163
|
+
case address
|
164
|
+
when Unix::MATCH then Unix.parse(address)
|
165
|
+
when IPv6::MATCH then IPv6.parse(address)
|
166
|
+
else IPv4.parse(address)
|
167
|
+
end
|
109
168
|
end
|
110
169
|
end
|
111
170
|
end
|
data/lib/mongo/address/ipv4.rb
CHANGED
@@ -27,27 +27,40 @@ module Mongo
|
|
27
27
|
# @return [ Integer ] port The port.
|
28
28
|
attr_reader :port
|
29
29
|
|
30
|
-
# @return [ String ] seed The seed address.
|
31
|
-
attr_reader :seed
|
32
|
-
|
33
30
|
# The regular expression to use to match an IPv4 ip address.
|
34
31
|
#
|
35
32
|
# @since 2.0.0
|
36
33
|
MATCH = Regexp.new('/\./').freeze
|
37
34
|
|
35
|
+
# Parse an IPv4 address into its host and port.
|
36
|
+
#
|
37
|
+
# @example Parse the address.
|
38
|
+
# IPv4.parse("127.0.0.1:28011")
|
39
|
+
#
|
40
|
+
# @param [ String ] address The address to parse.
|
41
|
+
#
|
42
|
+
# @return [ Array<String, Integer> ] The host and port pair.
|
43
|
+
#
|
44
|
+
# @since 2.0.0
|
45
|
+
def self.parse(address)
|
46
|
+
parts = address.split(':')
|
47
|
+
host = parts[0]
|
48
|
+
port = (parts[1] || 27017).to_i
|
49
|
+
[ host, port ]
|
50
|
+
end
|
51
|
+
|
38
52
|
# Initialize the IPv4 resolver.
|
39
53
|
#
|
40
54
|
# @example Initialize the resolver.
|
41
|
-
# IPv4.new("127.0.0.1:28011")
|
55
|
+
# IPv4.new("127.0.0.1", 27017, "127.0.0.1:28011")
|
42
56
|
#
|
43
|
-
# @param [ String ]
|
57
|
+
# @param [ String ] host The host.
|
58
|
+
# @param [ Integer ] port The port.
|
44
59
|
#
|
45
60
|
# @since 2.0.0
|
46
|
-
def initialize(
|
47
|
-
|
48
|
-
@
|
49
|
-
@port = (parts[1] || 27017).to_i
|
50
|
-
@seed = address
|
61
|
+
def initialize(host, port)
|
62
|
+
@host = host
|
63
|
+
@port = port
|
51
64
|
end
|
52
65
|
|
53
66
|
# Get a socket for the provided address type, given the options.
|
@@ -68,18 +81,6 @@ module Mongo
|
|
68
81
|
Socket::TCP.new(host, port, timeout, Socket::PF_INET)
|
69
82
|
end
|
70
83
|
end
|
71
|
-
|
72
|
-
# Get the address as a string.
|
73
|
-
#
|
74
|
-
# @example Get the address as a string.
|
75
|
-
# ipv4.to_s
|
76
|
-
#
|
77
|
-
# @return [ String ] The nice string.
|
78
|
-
#
|
79
|
-
# @since 2.0.0
|
80
|
-
def to_s
|
81
|
-
"#{host}:#{port}"
|
82
|
-
end
|
83
84
|
end
|
84
85
|
end
|
85
86
|
end
|
data/lib/mongo/address/ipv6.rb
CHANGED
@@ -27,27 +27,40 @@ module Mongo
|
|
27
27
|
# @return [ Integer ] port The port.
|
28
28
|
attr_reader :port
|
29
29
|
|
30
|
-
# @return [ String ] seed The seed address.
|
31
|
-
attr_reader :seed
|
32
|
-
|
33
30
|
# The regular expression to use to match an IPv6 ip address.
|
34
31
|
#
|
35
32
|
# @since 2.0.0
|
36
33
|
MATCH = Regexp.new('::').freeze
|
37
34
|
|
35
|
+
# Parse an IPv6 address into its host and port.
|
36
|
+
#
|
37
|
+
# @example Parse the address.
|
38
|
+
# IPv4.parse("[::1]:28011")
|
39
|
+
#
|
40
|
+
# @param [ String ] address The address to parse.
|
41
|
+
#
|
42
|
+
# @return [ Array<String, Integer> ] The host and port pair.
|
43
|
+
#
|
44
|
+
# @since 2.0.0
|
45
|
+
def self.parse(address)
|
46
|
+
parts = address.match(/\[(.+)\]:?(.+)?/)
|
47
|
+
host = parts[1]
|
48
|
+
port = (parts[2] || 27017).to_i
|
49
|
+
[ host, port ]
|
50
|
+
end
|
51
|
+
|
38
52
|
# Initialize the IPv6 resolver.
|
39
53
|
#
|
40
54
|
# @example Initialize the resolver.
|
41
|
-
# IPv6.new("[::1]:28011")
|
55
|
+
# IPv6.new("::1", 28011, "[::1]:28011")
|
42
56
|
#
|
43
|
-
# @param [ String ]
|
57
|
+
# @param [ String ] host The host.
|
58
|
+
# @param [ Integer ] port The port.
|
44
59
|
#
|
45
60
|
# @since 2.0.0
|
46
|
-
def initialize(
|
47
|
-
|
48
|
-
@
|
49
|
-
@port = (parts[2] || 27017).to_i
|
50
|
-
@seed = address
|
61
|
+
def initialize(host, port)
|
62
|
+
@host = host
|
63
|
+
@port = port
|
51
64
|
end
|
52
65
|
|
53
66
|
# Get a socket for the provided address type, given the options.
|
@@ -68,18 +81,6 @@ module Mongo
|
|
68
81
|
Socket::TCP.new(host, port, timeout, Socket::PF_INET6)
|
69
82
|
end
|
70
83
|
end
|
71
|
-
|
72
|
-
# Get the address as a string.
|
73
|
-
#
|
74
|
-
# @example Get the address as a string.
|
75
|
-
# ipv4.to_s
|
76
|
-
#
|
77
|
-
# @return [ String ] The nice string.
|
78
|
-
#
|
79
|
-
# @since 2.0.0
|
80
|
-
def to_s
|
81
|
-
"#{host}:#{port}"
|
82
|
-
end
|
83
84
|
end
|
84
85
|
end
|
85
86
|
end
|
data/lib/mongo/address/unix.rb
CHANGED
@@ -26,25 +26,35 @@ module Mongo
|
|
26
26
|
# @return [ nil ] port Will always be nil.
|
27
27
|
attr_reader :port
|
28
28
|
|
29
|
-
# @return [ String ] seed The seed address.
|
30
|
-
attr_reader :seed
|
31
|
-
|
32
29
|
# The regular expression to use to match a socket path.
|
33
30
|
#
|
34
31
|
# @since 2.0.0
|
35
32
|
MATCH = Regexp.new('\.sock').freeze
|
36
33
|
|
34
|
+
# Parse a socket path.
|
35
|
+
#
|
36
|
+
# @example Parse the address.
|
37
|
+
# Unix.parse("/path/to/socket.sock")
|
38
|
+
#
|
39
|
+
# @param [ String ] address The address to parse.
|
40
|
+
#
|
41
|
+
# @return [ Array<String> ] A list with the host (socket path).
|
42
|
+
#
|
43
|
+
# @since 2.0.0
|
44
|
+
def self.parse(address)
|
45
|
+
[ address ]
|
46
|
+
end
|
47
|
+
|
37
48
|
# Initialize the socket resolver.
|
38
49
|
#
|
39
50
|
# @example Initialize the resolver.
|
40
|
-
#
|
51
|
+
# Unix.new("/path/to/socket.sock", "/path/to/socket.sock")
|
41
52
|
#
|
42
|
-
# @param [ String ]
|
53
|
+
# @param [ String ] host The host.
|
43
54
|
#
|
44
55
|
# @since 2.0.0
|
45
|
-
def initialize(
|
46
|
-
@host =
|
47
|
-
@seed = address
|
56
|
+
def initialize(host)
|
57
|
+
@host = host
|
48
58
|
end
|
49
59
|
|
50
60
|
# Get a socket for the provided address type, given the options.
|
@@ -61,16 +71,6 @@ module Mongo
|
|
61
71
|
def socket(timeout, ssl_options = {})
|
62
72
|
Socket::Unix.new(host, timeout, Socket::AF_UNIX)
|
63
73
|
end
|
64
|
-
|
65
|
-
# Get the address as a string.
|
66
|
-
#
|
67
|
-
# @example Get the address as a string.
|
68
|
-
# ipv4.to_s
|
69
|
-
#
|
70
|
-
# @return [ String ] The nice string.
|
71
|
-
#
|
72
|
-
# @since 2.0.0
|
73
|
-
alias :to_s :host
|
74
74
|
end
|
75
75
|
end
|
76
76
|
end
|
data/lib/mongo/auth.rb
CHANGED
data/lib/mongo/auth/cr.rb
CHANGED
@@ -21,7 +21,26 @@ module Mongo
|
|
21
21
|
#
|
22
22
|
# @since 2.0.0
|
23
23
|
class CR
|
24
|
-
|
24
|
+
|
25
|
+
# The authentication mechinism string.
|
26
|
+
#
|
27
|
+
# @since 2.0.0
|
28
|
+
MECHANISM = 'MONGODB-CR'.freeze
|
29
|
+
|
30
|
+
# @return [ Mongo::Auth::User ] The user to authenticate.
|
31
|
+
attr_reader :user
|
32
|
+
|
33
|
+
# Instantiate a new authenticator.
|
34
|
+
#
|
35
|
+
# @example Create the authenticator.
|
36
|
+
# Mongo::Auth::CR.new(user)
|
37
|
+
#
|
38
|
+
# @param [ Mongo::Auth::User ] user The user to authenticate.
|
39
|
+
#
|
40
|
+
# @since 2.0.0
|
41
|
+
def initialize(user)
|
42
|
+
@user = user
|
43
|
+
end
|
25
44
|
|
26
45
|
# Log the user in on the given connection.
|
27
46
|
#
|
@@ -34,7 +53,7 @@ module Mongo
|
|
34
53
|
#
|
35
54
|
# @since 2.0.0
|
36
55
|
def login(connection)
|
37
|
-
conversation = Conversation.new(user
|
56
|
+
conversation = Conversation.new(user)
|
38
57
|
reply = connection.dispatch([ conversation.start ])
|
39
58
|
reply = connection.dispatch([ conversation.continue(reply) ])
|
40
59
|
conversation.finalize(reply)
|
@@ -56,7 +56,7 @@ module Mongo
|
|
56
56
|
def continue(reply)
|
57
57
|
validate!(reply)
|
58
58
|
Protocol::Query.new(
|
59
|
-
|
59
|
+
user.auth_source,
|
60
60
|
Database::COMMAND,
|
61
61
|
LOGIN.merge(user: user.name, nonce: nonce, key: user.auth_key(nonce)),
|
62
62
|
limit: -1
|
@@ -89,7 +89,11 @@ module Mongo
|
|
89
89
|
#
|
90
90
|
# @since 2.0.0
|
91
91
|
def start
|
92
|
-
Protocol::Query.new(
|
92
|
+
Protocol::Query.new(
|
93
|
+
user.auth_source,
|
94
|
+
Database::COMMAND,
|
95
|
+
Auth::GET_NONCE,
|
96
|
+
limit: -1)
|
93
97
|
end
|
94
98
|
|
95
99
|
# Create the new conversation.
|
@@ -101,9 +105,8 @@ module Mongo
|
|
101
105
|
# @param [ String ] database The database to authenticate against.
|
102
106
|
#
|
103
107
|
# @since 2.0.0
|
104
|
-
def initialize(user
|
108
|
+
def initialize(user)
|
105
109
|
@user = user
|
106
|
-
@database = database
|
107
110
|
end
|
108
111
|
|
109
112
|
private
|
data/lib/mongo/auth/ldap.rb
CHANGED
@@ -21,13 +21,26 @@ module Mongo
|
|
21
21
|
#
|
22
22
|
# @since 2.0.0
|
23
23
|
class LDAP
|
24
|
-
include Executable
|
25
24
|
|
26
25
|
# The authentication mechinism string.
|
27
26
|
#
|
28
27
|
# @since 2.0.0
|
29
28
|
MECHANISM = 'PLAIN'.freeze
|
30
29
|
|
30
|
+
# @return [ Mongo::Auth::User ] The user to authenticate.
|
31
|
+
attr_reader :user
|
32
|
+
|
33
|
+
# Instantiate a new authenticator.
|
34
|
+
#
|
35
|
+
# @example Create the authenticator.
|
36
|
+
# Mongo::Auth::LDAP.new(user)
|
37
|
+
#
|
38
|
+
# @param [ Mongo::Auth::User ] user The user to authenticate.
|
39
|
+
#
|
40
|
+
# @since 2.0.0
|
41
|
+
def initialize(user)
|
42
|
+
@user = user
|
43
|
+
end
|
31
44
|
# Log the user in on the given connection.
|
32
45
|
#
|
33
46
|
# @example Log the user in.
|
data/lib/mongo/auth/scram.rb
CHANGED
@@ -21,13 +21,27 @@ module Mongo
|
|
21
21
|
#
|
22
22
|
# @since 2.0.0
|
23
23
|
class SCRAM
|
24
|
-
include Executable
|
25
24
|
|
26
25
|
# The authentication mechinism string.
|
27
26
|
#
|
28
27
|
# @since 2.0.0
|
29
28
|
MECHANISM = 'SCRAM-SHA-1'.freeze
|
30
29
|
|
30
|
+
# @return [ Mongo::Auth::User ] The user to authenticate.
|
31
|
+
attr_reader :user
|
32
|
+
|
33
|
+
# Instantiate a new authenticator.
|
34
|
+
#
|
35
|
+
# @example Create the authenticator.
|
36
|
+
# Mongo::Auth::SCRAM.new(user)
|
37
|
+
#
|
38
|
+
# @param [ Mongo::Auth::User ] user The user to authenticate.
|
39
|
+
#
|
40
|
+
# @since 2.0.0
|
41
|
+
def initialize(user)
|
42
|
+
@user = user
|
43
|
+
end
|
44
|
+
|
31
45
|
# Log the user in on the given connection.
|
32
46
|
#
|
33
47
|
# @example Log the user in.
|