mongo 1.10.0-java

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 (116) hide show
  1. checksums.yaml +7 -0
  2. checksums.yaml.gz.sig +0 -0
  3. data.tar.gz.sig +0 -0
  4. data/LICENSE +190 -0
  5. data/README.md +149 -0
  6. data/Rakefile +31 -0
  7. data/VERSION +1 -0
  8. data/bin/mongo_console +43 -0
  9. data/ext/jsasl/target/jsasl.jar +0 -0
  10. data/lib/mongo.rb +90 -0
  11. data/lib/mongo/bulk_write_collection_view.rb +380 -0
  12. data/lib/mongo/collection.rb +1164 -0
  13. data/lib/mongo/collection_writer.rb +364 -0
  14. data/lib/mongo/connection.rb +19 -0
  15. data/lib/mongo/connection/node.rb +239 -0
  16. data/lib/mongo/connection/pool.rb +347 -0
  17. data/lib/mongo/connection/pool_manager.rb +325 -0
  18. data/lib/mongo/connection/sharding_pool_manager.rb +67 -0
  19. data/lib/mongo/connection/socket.rb +18 -0
  20. data/lib/mongo/connection/socket/socket_util.rb +37 -0
  21. data/lib/mongo/connection/socket/ssl_socket.rb +95 -0
  22. data/lib/mongo/connection/socket/tcp_socket.rb +86 -0
  23. data/lib/mongo/connection/socket/unix_socket.rb +39 -0
  24. data/lib/mongo/cursor.rb +719 -0
  25. data/lib/mongo/db.rb +735 -0
  26. data/lib/mongo/exception.rb +88 -0
  27. data/lib/mongo/functional.rb +21 -0
  28. data/lib/mongo/functional/authentication.rb +318 -0
  29. data/lib/mongo/functional/logging.rb +85 -0
  30. data/lib/mongo/functional/read_preference.rb +174 -0
  31. data/lib/mongo/functional/sasl_java.rb +48 -0
  32. data/lib/mongo/functional/uri_parser.rb +374 -0
  33. data/lib/mongo/functional/write_concern.rb +66 -0
  34. data/lib/mongo/gridfs.rb +18 -0
  35. data/lib/mongo/gridfs/grid.rb +112 -0
  36. data/lib/mongo/gridfs/grid_ext.rb +53 -0
  37. data/lib/mongo/gridfs/grid_file_system.rb +163 -0
  38. data/lib/mongo/gridfs/grid_io.rb +484 -0
  39. data/lib/mongo/legacy.rb +140 -0
  40. data/lib/mongo/mongo_client.rb +702 -0
  41. data/lib/mongo/mongo_replica_set_client.rb +523 -0
  42. data/lib/mongo/mongo_sharded_client.rb +159 -0
  43. data/lib/mongo/networking.rb +370 -0
  44. data/lib/mongo/utils.rb +19 -0
  45. data/lib/mongo/utils/conversions.rb +110 -0
  46. data/lib/mongo/utils/core_ext.rb +70 -0
  47. data/lib/mongo/utils/server_version.rb +69 -0
  48. data/lib/mongo/utils/support.rb +80 -0
  49. data/lib/mongo/utils/thread_local_variable_manager.rb +25 -0
  50. data/mongo.gemspec +36 -0
  51. data/test/functional/authentication_test.rb +35 -0
  52. data/test/functional/bulk_api_stress_test.rb +133 -0
  53. data/test/functional/bulk_write_collection_view_test.rb +1129 -0
  54. data/test/functional/client_test.rb +565 -0
  55. data/test/functional/collection_test.rb +2073 -0
  56. data/test/functional/collection_writer_test.rb +83 -0
  57. data/test/functional/conversions_test.rb +163 -0
  58. data/test/functional/cursor_fail_test.rb +63 -0
  59. data/test/functional/cursor_message_test.rb +57 -0
  60. data/test/functional/cursor_test.rb +625 -0
  61. data/test/functional/db_api_test.rb +819 -0
  62. data/test/functional/db_connection_test.rb +27 -0
  63. data/test/functional/db_test.rb +344 -0
  64. data/test/functional/grid_file_system_test.rb +285 -0
  65. data/test/functional/grid_io_test.rb +252 -0
  66. data/test/functional/grid_test.rb +273 -0
  67. data/test/functional/pool_test.rb +62 -0
  68. data/test/functional/safe_test.rb +98 -0
  69. data/test/functional/ssl_test.rb +29 -0
  70. data/test/functional/support_test.rb +62 -0
  71. data/test/functional/timeout_test.rb +58 -0
  72. data/test/functional/uri_test.rb +330 -0
  73. data/test/functional/write_concern_test.rb +118 -0
  74. data/test/helpers/general.rb +50 -0
  75. data/test/helpers/test_unit.rb +317 -0
  76. data/test/replica_set/authentication_test.rb +35 -0
  77. data/test/replica_set/basic_test.rb +174 -0
  78. data/test/replica_set/client_test.rb +341 -0
  79. data/test/replica_set/complex_connect_test.rb +77 -0
  80. data/test/replica_set/connection_test.rb +138 -0
  81. data/test/replica_set/count_test.rb +64 -0
  82. data/test/replica_set/cursor_test.rb +212 -0
  83. data/test/replica_set/insert_test.rb +140 -0
  84. data/test/replica_set/max_values_test.rb +145 -0
  85. data/test/replica_set/pinning_test.rb +55 -0
  86. data/test/replica_set/query_test.rb +73 -0
  87. data/test/replica_set/read_preference_test.rb +214 -0
  88. data/test/replica_set/refresh_test.rb +175 -0
  89. data/test/replica_set/replication_ack_test.rb +94 -0
  90. data/test/replica_set/ssl_test.rb +32 -0
  91. data/test/sharded_cluster/basic_test.rb +197 -0
  92. data/test/shared/authentication/basic_auth_shared.rb +286 -0
  93. data/test/shared/authentication/bulk_api_auth_shared.rb +259 -0
  94. data/test/shared/authentication/gssapi_shared.rb +164 -0
  95. data/test/shared/authentication/sasl_plain_shared.rb +96 -0
  96. data/test/shared/ssl_shared.rb +235 -0
  97. data/test/test_helper.rb +56 -0
  98. data/test/threading/basic_test.rb +120 -0
  99. data/test/tools/mongo_config.rb +608 -0
  100. data/test/tools/mongo_config_test.rb +160 -0
  101. data/test/unit/client_test.rb +347 -0
  102. data/test/unit/collection_test.rb +166 -0
  103. data/test/unit/connection_test.rb +325 -0
  104. data/test/unit/cursor_test.rb +299 -0
  105. data/test/unit/db_test.rb +136 -0
  106. data/test/unit/grid_test.rb +76 -0
  107. data/test/unit/mongo_sharded_client_test.rb +48 -0
  108. data/test/unit/node_test.rb +93 -0
  109. data/test/unit/pool_manager_test.rb +142 -0
  110. data/test/unit/read_pref_test.rb +115 -0
  111. data/test/unit/read_test.rb +159 -0
  112. data/test/unit/safe_test.rb +158 -0
  113. data/test/unit/sharding_pool_manager_test.rb +84 -0
  114. data/test/unit/write_concern_test.rb +175 -0
  115. metadata +260 -0
  116. metadata.gz.sig +0 -0
@@ -0,0 +1,35 @@
1
+ # Copyright (C) 2009-2013 MongoDB, Inc.
2
+ #
3
+ # Licensed under the Apache License, Version 2.0 (the "License");
4
+ # you may not use this file except in compliance with the License.
5
+ # You may obtain a copy of the License at
6
+ #
7
+ # http://www.apache.org/licenses/LICENSE-2.0
8
+ #
9
+ # Unless required by applicable law or agreed to in writing, software
10
+ # distributed under the License is distributed on an "AS IS" BASIS,
11
+ # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12
+ # See the License for the specific language governing permissions and
13
+ # limitations under the License.
14
+
15
+ require 'test_helper'
16
+ require 'shared/authentication/basic_auth_shared'
17
+ require 'shared/authentication/sasl_plain_shared'
18
+ require 'shared/authentication/bulk_api_auth_shared'
19
+ require 'shared/authentication/gssapi_shared'
20
+
21
+ class ReplicaSetAuthenticationTest < Test::Unit::TestCase
22
+ include Mongo
23
+ include BasicAuthTests
24
+ include SASLPlainTests
25
+ include BulkAPIAuthTests
26
+ include GSSAPITests
27
+
28
+ def setup
29
+ ensure_cluster(:rs)
30
+ @client = MongoReplicaSetClient.new(@rs.repl_set_seeds)
31
+ @version = @client.server_version
32
+ @db = @client[TEST_DB]
33
+ @host_info = @rs.repl_set_seeds.join(',')
34
+ end
35
+ end
@@ -0,0 +1,174 @@
1
+ # Copyright (C) 2009-2013 MongoDB, Inc.
2
+ #
3
+ # Licensed under the Apache License, Version 2.0 (the "License");
4
+ # you may not use this file except in compliance with the License.
5
+ # You may obtain a copy of the License at
6
+ #
7
+ # http://www.apache.org/licenses/LICENSE-2.0
8
+ #
9
+ # Unless required by applicable law or agreed to in writing, software
10
+ # distributed under the License is distributed on an "AS IS" BASIS,
11
+ # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12
+ # See the License for the specific language governing permissions and
13
+ # limitations under the License.
14
+
15
+ require 'test_helper'
16
+
17
+ class ReplicaSetBasicTest < Test::Unit::TestCase
18
+
19
+ def setup
20
+ ensure_cluster(:rs)
21
+ end
22
+
23
+ def test_connect
24
+ client = MongoReplicaSetClient.new(@rs.repl_set_seeds, :name => @rs.repl_set_name)
25
+ assert client.connected?
26
+ assert_equal @rs.primary_name, client.primary.join(':')
27
+ assert_equal @rs.secondary_names.sort, client.secondaries.collect{|s| s.join(':')}.sort
28
+ assert_equal @rs.arbiter_names.sort, client.arbiters.collect{|s| s.join(':')}.sort
29
+ client.close
30
+
31
+ silently do
32
+ client = MongoReplicaSetClient.new(@rs.repl_set_seeds_old, :name => @rs.repl_set_name)
33
+ end
34
+
35
+ assert client.connected?
36
+ client.close
37
+ end
38
+
39
+ def test_safe_option
40
+ client = MongoReplicaSetClient.new(@rs.repl_set_seeds, :name => @rs.repl_set_name)
41
+ assert client.connected?
42
+ assert client.write_concern[:w] > 0
43
+ client.close
44
+ client = MongoReplicaSetClient.new(@rs.repl_set_seeds, :name => @rs.repl_set_name, :w => 0)
45
+ assert client.connected?
46
+ assert client.write_concern[:w] < 1
47
+ client.close
48
+ client = MongoReplicaSetClient.new(@rs.repl_set_seeds, :name => @rs.repl_set_name, :w => 2)
49
+ assert client.connected?
50
+ assert client.write_concern[:w] > 0
51
+ client.close
52
+ end
53
+
54
+ def test_multiple_concurrent_replica_set_connection
55
+ client1 = MongoReplicaSetClient.new(@rs.repl_set_seeds, :name => @rs.repl_set_name)
56
+ client2 = MongoReplicaSetClient.new(@rs.repl_set_seeds, :name => @rs.repl_set_name)
57
+ assert client1.connected?
58
+ assert client2.connected?
59
+ assert client1.manager != client2.manager
60
+ assert client1.local_manager != client2.local_manager
61
+ client1.close
62
+ client2.close
63
+ end
64
+
65
+ def test_cache_original_seed_nodes
66
+ host = @rs.servers.first.host
67
+ seeds = @rs.repl_set_seeds << "#{host}:19356"
68
+ client = MongoReplicaSetClient.new(seeds, :name => @rs.repl_set_name)
69
+ assert client.connected?
70
+ assert client.seeds.include?([host, 19356]), "Original seed nodes not cached!"
71
+ assert_equal [host, 19356], client.seeds.last, "Original seed nodes not cached!"
72
+ client.close
73
+ end
74
+
75
+ def test_accessors
76
+ seeds = @rs.repl_set_seeds
77
+ args = {:name => @rs.repl_set_name}
78
+ client = MongoReplicaSetClient.new(seeds, args)
79
+ assert_equal @rs.primary_name, [client.host, client.port].join(':')
80
+ assert_equal client.host, client.primary_pool.host
81
+ assert_equal client.port, client.primary_pool.port
82
+ assert_equal 2, client.secondaries.length
83
+ assert_equal 2, client.secondary_pools.length
84
+ assert_equal @rs.repl_set_name, client.replica_set_name
85
+ assert client.secondary_pools.include?(client.read_pool({:mode => :secondary}))
86
+ assert_equal 90, client.refresh_interval
87
+ assert_equal client.refresh_mode, false
88
+ client.close
89
+ end
90
+
91
+ def test_write_commands_and_operations
92
+ seeds = @rs.repl_set_seeds
93
+ args = {:name => @rs.repl_set_name}
94
+ @client = MongoReplicaSetClient.new(seeds, args)
95
+ @coll = @client[TEST_DB]['test-write-commands-and-operations']
96
+ with_write_commands_and_operations(@client) do
97
+ @coll.remove
98
+ @coll.insert({:foo => "bar"})
99
+ assert_equal(1, @coll.count)
100
+ end
101
+ end
102
+
103
+ context "Socket pools" do
104
+ context "checking out writers" do
105
+ setup do
106
+ seeds = @rs.repl_set_seeds
107
+ args = {:name => @rs.repl_set_name}
108
+ @client = MongoReplicaSetClient.new(seeds, args)
109
+ @coll = @client[TEST_DB]['test-connection-exceptions']
110
+ end
111
+
112
+ should "close the connection on send_message for major exceptions" do
113
+ with_write_operations(@client) do # explicit even if w 0 maps to write operations
114
+ @client.expects(:checkout_writer).raises(SystemStackError)
115
+ @client.expects(:close)
116
+ begin
117
+ @coll.insert({:foo => "bar"}, :w => 0)
118
+ rescue SystemStackError
119
+ end
120
+ end
121
+ end
122
+
123
+ should "close the connection on send_write_command for major exceptions" do
124
+ with_write_commands(@client) do
125
+ @client.expects(:checkout_reader).raises(SystemStackError)
126
+ @client.expects(:close)
127
+ begin
128
+ @coll.insert({:foo => "bar"})
129
+ rescue SystemStackError
130
+ end
131
+ end
132
+ end
133
+
134
+ should "close the connection on send_message_with_gle for major exceptions" do
135
+ with_write_operations(@client) do
136
+ @client.expects(:checkout_writer).raises(SystemStackError)
137
+ @client.expects(:close)
138
+ begin
139
+ @coll.insert({:foo => "bar"})
140
+ rescue SystemStackError
141
+ end
142
+ end
143
+ end
144
+
145
+ should "close the connection on receive_message for major exceptions" do
146
+ @client.expects(:checkout_reader).raises(SystemStackError)
147
+ @client.expects(:close)
148
+ begin
149
+ @coll.find({}, :read => :primary).next
150
+ rescue SystemStackError
151
+ end
152
+ end
153
+ end
154
+
155
+ context "checking out readers" do
156
+ setup do
157
+ seeds = @rs.repl_set_seeds
158
+ args = {:name => @rs.repl_set_name}
159
+ @client = MongoReplicaSetClient.new(seeds, args)
160
+ @coll = @client[TEST_DB]['test-connection-exceptions']
161
+ end
162
+
163
+ should "close the connection on receive_message for major exceptions" do
164
+ @client.expects(:checkout_reader).raises(SystemStackError)
165
+ @client.expects(:close)
166
+ begin
167
+ @coll.find({}, :read => :secondary).next
168
+ rescue SystemStackError
169
+ end
170
+ end
171
+ end
172
+ end
173
+
174
+ end
@@ -0,0 +1,341 @@
1
+ # Copyright (C) 2009-2013 MongoDB, Inc.
2
+ #
3
+ # Licensed under the Apache License, Version 2.0 (the "License");
4
+ # you may not use this file except in compliance with the License.
5
+ # You may obtain a copy of the License at
6
+ #
7
+ # http://www.apache.org/licenses/LICENSE-2.0
8
+ #
9
+ # Unless required by applicable law or agreed to in writing, software
10
+ # distributed under the License is distributed on an "AS IS" BASIS,
11
+ # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12
+ # See the License for the specific language governing permissions and
13
+ # limitations under the License.
14
+
15
+ require 'test_helper'
16
+
17
+ class ReplicaSetClientTest < Test::Unit::TestCase
18
+
19
+ def setup
20
+ ensure_cluster(:rs)
21
+ @client = nil
22
+ end
23
+
24
+ def teardown
25
+ @client.close if @client
26
+ end
27
+
28
+ def test_reconnection
29
+ @client = MongoReplicaSetClient.new @rs.repl_set_seeds
30
+ assert @client.connected?
31
+
32
+ manager = @client.local_manager
33
+
34
+ @client.close
35
+ assert !@client.connected?
36
+ assert !@client.local_manager
37
+
38
+ @client.connect
39
+ assert @client.connected?
40
+ assert_equal @client.local_manager, manager
41
+ end
42
+
43
+ # TODO: test connect timeout.
44
+
45
+ def test_connect_with_deprecated_multi
46
+ silently do
47
+ # guaranteed to have one data-holding member
48
+ @client = MongoClient.multi(@rs.repl_set_seeds_old, :name => @rs.repl_set_name)
49
+ end
50
+ assert !@client.nil?
51
+ assert @client.connected?
52
+ end
53
+
54
+ def test_connect_bad_name
55
+ assert_raise_error(ReplicaSetConnectionError, "-wrong") do
56
+ @client = MongoReplicaSetClient.new(@rs.repl_set_seeds, :name => @rs.repl_set_name + "-wrong")
57
+ end
58
+ end
59
+
60
+ def test_connect_with_first_secondary_node_terminated
61
+ @rs.secondaries.first.stop
62
+
63
+ rescue_connection_failure do
64
+ @client = MongoReplicaSetClient.new @rs.repl_set_seeds
65
+ end
66
+ assert @client.connected?
67
+ end
68
+
69
+ def test_connect_with_last_secondary_node_terminated
70
+ @rs.secondaries.last.stop
71
+
72
+ rescue_connection_failure do
73
+ @client = MongoReplicaSetClient.new @rs.repl_set_seeds
74
+ end
75
+ assert @client.connected?
76
+ end
77
+
78
+ def test_connect_with_primary_stepped_down
79
+ @client = MongoReplicaSetClient.new @rs.repl_set_seeds
80
+ @client[TEST_DB]['bar'].save({:a => 1}, {:w => 3})
81
+ assert @client[TEST_DB]['bar'].find_one
82
+
83
+ primary = Mongo::MongoClient.new(*@client.primary)
84
+ assert_raise Mongo::ConnectionFailure do
85
+ perform_step_down(primary)
86
+ end
87
+ assert @client.connected?
88
+
89
+ rescue_connection_failure do
90
+ @client[TEST_DB]['bar'].find_one
91
+ end
92
+ @client[TEST_DB]['bar'].find_one
93
+ end
94
+
95
+ def test_connect_with_primary_killed
96
+ @client = MongoReplicaSetClient.new @rs.repl_set_seeds
97
+ assert @client.connected?
98
+ @client[TEST_DB]['bar'].save({:a => 1}, {:w => 3})
99
+ assert @client[TEST_DB]['bar'].find_one
100
+
101
+ @rs.primary.kill(Signal.list['KILL'])
102
+
103
+ sleep(3)
104
+
105
+ rescue_connection_failure do
106
+ @client[TEST_DB]['bar'].find_one
107
+ end
108
+ @client[TEST_DB]['bar'].find_one
109
+ end
110
+
111
+ def test_save_with_primary_stepped_down
112
+ @client = MongoReplicaSetClient.new @rs.repl_set_seeds
113
+ assert @client.connected?
114
+
115
+ primary = Mongo::MongoClient.new(*@client.primary)
116
+ assert_raise Mongo::ConnectionFailure do
117
+ perform_step_down(primary)
118
+ end
119
+
120
+ rescue_connection_failure do
121
+ @client[TEST_DB]['bar'].save({:a => 1}, {:w => 2})
122
+ end
123
+ @client[TEST_DB]['bar'].find_one
124
+ end
125
+
126
+ # def test_connect_with_first_node_removed
127
+ # @client = MongoReplicaSetClient.new @rs.repl_set_seeds
128
+ # @client[TEST_DB]['bar'].save({:a => 1}, {:w => 3})
129
+
130
+ # # Make sure everyone's views of optimes are caught up
131
+ # loop do
132
+ # break if @rs.repl_set_get_status.all? do |status|
133
+ # members = status['members']
134
+ # primary_optime = members.find{|m| m['state'] == 1}['optime'].seconds
135
+ # members.any?{|m| m['state'] == 2 && primary_optime - m['optime'].seconds < 5}
136
+ # end
137
+ # sleep 1
138
+ # end
139
+
140
+ # old_primary = [@client.primary_pool.host, @client.primary_pool.port]
141
+ # old_primary_conn = Mongo::MongoClient.new(*old_primary)
142
+
143
+ # assert_raise Mongo::ConnectionFailure do
144
+ # perform_step_down(old_primary_conn)
145
+ # end
146
+
147
+ # # Wait for new primary
148
+ # rescue_connection_failure do
149
+ # sleep 1 until @rs.primary
150
+ # end
151
+
152
+ # new_primary = [@rs.primary.host, @rs.primary.port]
153
+ # new_primary_conn = Mongo::MongoClient.new(*new_primary)
154
+
155
+ # assert new_primary != old_primary
156
+
157
+ # config = nil
158
+
159
+ # # Remove old primary from replset
160
+ # rescue_connection_failure do
161
+ # config = @client['local']['system.replset'].find_one
162
+ # end
163
+
164
+ # old_member = config['members'].select {|m| m['host'] == old_primary.join(':')}.first
165
+ # config['members'].reject! {|m| m['host'] == old_primary.join(':')}
166
+ # config['version'] += 1
167
+
168
+ # begin
169
+ # new_primary_conn['admin'].command({'replSetReconfig' => config})
170
+ # rescue Mongo::ConnectionFailure
171
+ # end
172
+
173
+ # # Wait for the dust to settle
174
+ # rescue_connection_failure do
175
+ # assert @client[TEST_DB]['bar'].find_one
176
+ # end
177
+
178
+ # begin
179
+ # # Make sure a new connection skips the old primary
180
+ # @new_conn = MongoReplicaSetClient.new @rs.repl_set_seeds
181
+ # @new_conn.connect
182
+ # new_nodes = @new_conn.secondaries + [@new_conn.primary]
183
+ # assert !new_nodes.include?(old_primary)
184
+ # ensure
185
+ # # Add the old primary back
186
+ # config['members'] << old_member
187
+ # config['version'] += 1
188
+
189
+ # begin
190
+ # new_primary_conn['admin'].command({'replSetReconfig' => config})
191
+ # rescue Mongo::ConnectionFailure
192
+ # end
193
+ # end
194
+ # end
195
+
196
+ def test_connect_with_hung_first_node
197
+ hung_node = nil
198
+ begin
199
+ hung_node = IO.popen('nc -lk 127.0.0.1 29999 >/dev/null 2>&1')
200
+
201
+ Timeout.timeout(3) do
202
+ @client = MongoReplicaSetClient.new(['localhost:29999'] + @rs.repl_set_seeds,
203
+ :connect_timeout => 2)
204
+ @client.connect
205
+ end
206
+ assert ['localhost:29999'] != @client.primary
207
+ assert !@client.secondaries.include?('localhost:29999')
208
+ ensure
209
+ Process.kill("KILL", hung_node.pid) if hung_node
210
+ end
211
+ end
212
+
213
+ def test_connect_with_connection_string
214
+ @client = MongoClient.from_uri("mongodb://#{@rs.replicas[0].host_port},#{@rs.replicas[1].host_port}?replicaset=#{@rs.repl_set_name}")
215
+ assert !@client.nil?
216
+ assert @client.connected?
217
+ end
218
+
219
+ def test_connect_with_connection_string_in_env_var
220
+ uri = "mongodb://#{@rs.replicas[0].host_port},#{@rs.replicas[1].host_port}?replicaset=#{@rs.repl_set_name}"
221
+ with_preserved_env_uri(uri) do
222
+ @client = MongoReplicaSetClient.new
223
+ assert !@client.nil?
224
+ assert_equal 2, @client.seeds.length
225
+ assert_equal @rs.replicas[0].host, @client.seeds[0][0]
226
+ assert_equal @rs.replicas[1].host, @client.seeds[1][0]
227
+ assert_equal @rs.replicas[0].port, @client.seeds[0][1]
228
+ assert_equal @rs.replicas[1].port, @client.seeds[1][1]
229
+ assert_equal @rs.repl_set_name, @client.replica_set_name
230
+ assert @client.connected?
231
+ end
232
+ end
233
+
234
+ def test_connect_with_connection_string_in_implicit_mongodb_uri
235
+ uri = "mongodb://#{@rs.replicas[0].host_port},#{@rs.replicas[1].host_port}?replicaset=#{@rs.repl_set_name}"
236
+ with_preserved_env_uri(uri) do
237
+ @client = MongoClient.from_uri
238
+ assert !@client.nil?
239
+ assert_equal 2, @client.seeds.length
240
+ assert_equal @rs.replicas[0].host, @client.seeds[0][0]
241
+ assert_equal @rs.replicas[1].host, @client.seeds[1][0]
242
+ assert_equal @rs.replicas[0].port, @client.seeds[0][1]
243
+ assert_equal @rs.replicas[1].port, @client.seeds[1][1]
244
+ assert_equal @rs.repl_set_name, @client.replica_set_name
245
+ assert @client.connected?
246
+ end
247
+ end
248
+
249
+ def test_connect_with_new_seed_format
250
+ @client = MongoReplicaSetClient.new @rs.repl_set_seeds
251
+ assert @client.connected?
252
+ end
253
+
254
+ def test_connect_with_old_seed_format
255
+ silently do
256
+ @client = MongoReplicaSetClient.new(@rs.repl_set_seeds_old)
257
+ end
258
+ assert @client.connected?
259
+ end
260
+
261
+ def test_connect_with_full_connection_string
262
+ @client = MongoClient.from_uri("mongodb://#{@rs.replicas[0].host_port},#{@rs.replicas[1].host_port}?replicaset=#{@rs.repl_set_name};w=2;fsync=true;slaveok=true")
263
+ assert !@client.nil?
264
+ assert @client.connected?
265
+ assert_equal 2, @client.write_concern[:w]
266
+ assert @client.write_concern[:fsync]
267
+ assert @client.read_pool
268
+ end
269
+
270
+ def test_connect_with_full_connection_string_in_env_var
271
+ uri = "mongodb://#{@rs.replicas[0].host_port},#{@rs.replicas[1].host_port}?replicaset=#{@rs.repl_set_name};w=2;fsync=true;slaveok=true"
272
+ with_preserved_env_uri(uri) do
273
+ @client = MongoReplicaSetClient.new
274
+ assert !@client.nil?
275
+ assert @client.connected?
276
+ assert_equal 2, @client.write_concern[:w]
277
+ assert @client.write_concern[:fsync]
278
+ assert @client.read_pool
279
+ end
280
+ end
281
+
282
+ def test_connect_options_override_env_var
283
+ uri = "mongodb://#{@rs.replicas[0].host_port},#{@rs.replicas[1].host_port}?replicaset=#{@rs.repl_set_name};w=2;fsync=true;slaveok=true"
284
+ with_preserved_env_uri(uri) do
285
+ @client = MongoReplicaSetClient.new({:w => 0})
286
+ assert !@client.nil?
287
+ assert @client.connected?
288
+ assert_equal 0, @client.write_concern[:w]
289
+ end
290
+ end
291
+
292
+ def test_ipv6
293
+ @client = MongoReplicaSetClient.new(@rs.repl_set_seeds)
294
+ with_ipv6_enabled(@client) do
295
+ assert MongoReplicaSetClient.new(["[::1]:#{@rs.replicas[0].port}"])
296
+ end
297
+ end
298
+
299
+ def test_ipv6_with_uri
300
+ @client = MongoReplicaSetClient.new(@rs.repl_set_seeds)
301
+ with_ipv6_enabled(@client) do
302
+ uri = "mongodb://[::1]:#{@rs.replicas[0].port},[::1]:#{@rs.replicas[1].port}"
303
+ with_preserved_env_uri(uri) do
304
+ assert MongoReplicaSetClient.new
305
+ end
306
+ end
307
+ end
308
+
309
+ def test_ipv6_with_uri_opts
310
+ @client = MongoReplicaSetClient.new(@rs.repl_set_seeds)
311
+ with_ipv6_enabled(@client) do
312
+ uri = "mongodb://[::1]:#{@rs.replicas[0].port},[::1]:#{@rs.replicas[1].port}/?safe=true;"
313
+ with_preserved_env_uri(uri) do
314
+ assert MongoReplicaSetClient.new
315
+ end
316
+ end
317
+ end
318
+
319
+ def test_ipv6_with_different_formats
320
+ @client = MongoReplicaSetClient.new(@rs.repl_set_seeds)
321
+ with_ipv6_enabled(@client) do
322
+ uri = "mongodb://[::1]:#{@rs.replicas[0].port},localhost:#{@rs.replicas[1].port}"
323
+ with_preserved_env_uri(uri) do
324
+ assert MongoReplicaSetClient.new
325
+ end
326
+ end
327
+ end
328
+
329
+ def test_find_and_modify_with_secondary_read_preference
330
+ @client = MongoReplicaSetClient.new @rs.repl_set_seeds
331
+ collection = @client[TEST_DB].collection('test', :read => :secondary)
332
+ id = BSON::ObjectId.new
333
+ collection << { :a => id, :processed => false }
334
+
335
+ collection.find_and_modify(
336
+ :query => { 'a' => id },
337
+ :update => { "$set" => { :processed => true }}
338
+ )
339
+ assert_equal true, collection.find_one({ 'a' => id }, :read => :primary)['processed']
340
+ end
341
+ end