jmongo 1.0.3 → 1.1.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (96) hide show
  1. data/Gemfile +8 -0
  2. data/Gemfile.lock +43 -0
  3. data/Rakefile +72 -0
  4. data/jmongo.gemspec +84 -6
  5. data/lib/jmongo.rb +6 -14
  6. data/lib/jmongo/collection.rb +196 -114
  7. data/lib/jmongo/connection.rb +39 -13
  8. data/lib/jmongo/cursor.rb +161 -63
  9. data/lib/jmongo/db.rb +119 -30
  10. data/lib/jmongo/exceptions.rb +39 -0
  11. data/lib/jmongo/mongo-2.6.5.gb1.jar +0 -0
  12. data/lib/jmongo/mongo/bson.rb +130 -0
  13. data/lib/jmongo/mongo/collection.rb +185 -0
  14. data/lib/jmongo/mongo/connection.rb +45 -0
  15. data/lib/jmongo/mongo/db.rb +31 -0
  16. data/lib/jmongo/mongo/jmongo.rb +44 -0
  17. data/lib/jmongo/mongo/mongo.rb +98 -0
  18. data/lib/jmongo/mongo/ruby_ext.rb +38 -0
  19. data/lib/jmongo/mongo/utils.rb +136 -0
  20. data/lib/jmongo/version.rb +1 -1
  21. data/test-results.txt +98 -0
  22. data/test/auxillary/1.4_features.rb +166 -0
  23. data/test/auxillary/authentication_test.rb +68 -0
  24. data/test/auxillary/autoreconnect_test.rb +41 -0
  25. data/test/auxillary/fork_test.rb +30 -0
  26. data/test/auxillary/repl_set_auth_test.rb +58 -0
  27. data/test/auxillary/slave_connection_test.rb +36 -0
  28. data/test/auxillary/threaded_authentication_test.rb +101 -0
  29. data/test/bson/binary_test.rb +15 -0
  30. data/test/bson/bson_test.rb +657 -0
  31. data/test/bson/byte_buffer_test.rb +208 -0
  32. data/test/bson/hash_with_indifferent_access_test.rb +38 -0
  33. data/test/bson/json_test.rb +17 -0
  34. data/test/bson/object_id_test.rb +138 -0
  35. data/test/bson/ordered_hash_test.rb +245 -0
  36. data/test/bson/test_helper.rb +46 -0
  37. data/test/bson/timestamp_test.rb +46 -0
  38. data/test/collection_test.rb +933 -0
  39. data/test/connection_test.rb +325 -0
  40. data/test/conversions_test.rb +121 -0
  41. data/test/cursor_fail_test.rb +75 -0
  42. data/test/cursor_message_test.rb +43 -0
  43. data/test/cursor_test.rb +547 -0
  44. data/test/data/empty_data +0 -0
  45. data/test/data/sample_data +0 -0
  46. data/test/data/sample_file.pdf +0 -0
  47. data/test/data/small_data.txt +1 -0
  48. data/test/db_api_test.rb +739 -0
  49. data/test/db_connection_test.rb +15 -0
  50. data/test/db_test.rb +325 -0
  51. data/test/grid_file_system_test.rb +260 -0
  52. data/test/grid_io_test.rb +210 -0
  53. data/test/grid_test.rb +259 -0
  54. data/test/load/thin/config.ru +6 -0
  55. data/test/load/thin/config.yml.template +6 -0
  56. data/test/load/thin/load.rb +24 -0
  57. data/test/load/unicorn/config.ru +6 -0
  58. data/test/load/unicorn/load.rb +23 -0
  59. data/test/load/unicorn/unicorn.rb.template +29 -0
  60. data/test/replica_sets/connect_test.rb +111 -0
  61. data/test/replica_sets/connection_string_test.rb +29 -0
  62. data/test/replica_sets/count_test.rb +36 -0
  63. data/test/replica_sets/insert_test.rb +54 -0
  64. data/test/replica_sets/pooled_insert_test.rb +58 -0
  65. data/test/replica_sets/query_secondaries.rb +109 -0
  66. data/test/replica_sets/query_test.rb +52 -0
  67. data/test/replica_sets/read_preference_test.rb +43 -0
  68. data/test/replica_sets/refresh_test.rb +123 -0
  69. data/test/replica_sets/replication_ack_test.rb +71 -0
  70. data/test/replica_sets/rs_test_helper.rb +27 -0
  71. data/test/safe_test.rb +68 -0
  72. data/test/support/hash_with_indifferent_access.rb +186 -0
  73. data/test/support/keys.rb +45 -0
  74. data/test/support_test.rb +19 -0
  75. data/test/test_helper.rb +111 -0
  76. data/test/threading/threading_with_large_pool_test.rb +90 -0
  77. data/test/threading_test.rb +88 -0
  78. data/test/tools/auth_repl_set_manager.rb +14 -0
  79. data/test/tools/keyfile.txt +1 -0
  80. data/test/tools/repl_set_manager.rb +377 -0
  81. data/test/unit/collection_test.rb +128 -0
  82. data/test/unit/connection_test.rb +85 -0
  83. data/test/unit/cursor_test.rb +127 -0
  84. data/test/unit/db_test.rb +96 -0
  85. data/test/unit/grid_test.rb +51 -0
  86. data/test/unit/node_test.rb +73 -0
  87. data/test/unit/pool_manager_test.rb +47 -0
  88. data/test/unit/pool_test.rb +9 -0
  89. data/test/unit/read_test.rb +101 -0
  90. data/test/unit/safe_test.rb +125 -0
  91. data/test/uri_test.rb +92 -0
  92. metadata +170 -99
  93. data/lib/jmongo/ajrb.rb +0 -189
  94. data/lib/jmongo/jmongo_jext.rb +0 -302
  95. data/lib/jmongo/mongo-2.6.3.jar +0 -0
  96. data/lib/jmongo/utils.rb +0 -61
@@ -0,0 +1,73 @@
1
+ require './test/test_helper'
2
+
3
+ class NodeTest < Test::Unit::TestCase
4
+
5
+ def setup
6
+ @connection = stub()
7
+ end
8
+
9
+ should "refuse to connect to node without 'hosts' key" do
10
+ tcp = mock()
11
+ node = Node.new(@connection, ['localhost', 27017])
12
+ tcp.stubs(:new).returns(new_mock_socket)
13
+ @connection.stubs(:socket_class).returns(tcp)
14
+
15
+ admin_db = new_mock_db
16
+ admin_db.stubs(:command).returns({'ok' => 1, 'ismaster' => 1})
17
+ @connection.stubs(:[]).with('admin').returns(admin_db)
18
+ @connection.stubs(:connect_timeout).returns(nil)
19
+ @connection.expects(:log)
20
+
21
+ assert node.connect
22
+ node.set_config
23
+ end
24
+
25
+ should "load a node from an array" do
26
+ node = Node.new(@connection, ['power.level.com', 9001])
27
+ assert_equal 'power.level.com', node.host
28
+ assert_equal 9001, node.port
29
+ assert_equal 'power.level.com:9001', node.address
30
+ end
31
+
32
+ should "should default the port for an array" do
33
+ node = Node.new(@connection, ['power.level.com'])
34
+ assert_equal 'power.level.com', node.host
35
+ assert_equal Connection::DEFAULT_PORT, node.port
36
+ assert_equal "power.level.com:#{Connection::DEFAULT_PORT}", node.address
37
+ end
38
+
39
+ should "load a node from a string" do
40
+ node = Node.new(@connection, 'localhost:1234')
41
+ assert_equal 'localhost', node.host
42
+ assert_equal 1234, node.port
43
+ assert_equal 'localhost:1234', node.address
44
+ end
45
+
46
+ should "should default the port for a string" do
47
+ node = Node.new(@connection, '192.168.0.1')
48
+ assert_equal '192.168.0.1', node.host
49
+ assert_equal Connection::DEFAULT_PORT, node.port
50
+ assert_equal "192.168.0.1:#{Connection::DEFAULT_PORT}", node.address
51
+ end
52
+
53
+ should "two nodes with the same address should be equal" do
54
+ assert_equal Node.new(@connection, '192.168.0.1'),
55
+ Node.new(@connection, ['192.168.0.1', Connection::DEFAULT_PORT])
56
+ end
57
+
58
+ should "two nodes with the same address should have the same hash" do
59
+ assert_equal Node.new(@connection, '192.168.0.1').hash,
60
+ Node.new(@connection, ['192.168.0.1', Connection::DEFAULT_PORT]).hash
61
+ end
62
+
63
+ should "two nodes with different addresses should not be equal" do
64
+ assert_not_equal Node.new(@connection, '192.168.0.2'),
65
+ Node.new(@connection, ['192.168.0.1', Connection::DEFAULT_PORT])
66
+ end
67
+
68
+ should "two nodes with the same address should have the same hash negate" do
69
+ assert_not_equal Node.new(@connection, '192.168.0.1').hash,
70
+ Node.new(@connection, '1239.33.4.2393:29949').hash
71
+ end
72
+
73
+ end
@@ -0,0 +1,47 @@
1
+ require './test/test_helper'
2
+ include Mongo
3
+
4
+ class PoolManagerTest < Test::Unit::TestCase
5
+
6
+ context "Initialization: " do
7
+
8
+ should "populate pools correctly" do
9
+ TCPSocket.stubs(:new).returns(new_mock_socket)
10
+ @db = new_mock_db
11
+
12
+ @connection = stub("Connection")
13
+ @connection.stubs(:connect_timeout).returns(5000)
14
+ @connection.stubs(:pool_size).returns(2)
15
+ @connection.stubs(:socket_class).returns(TCPSocket)
16
+ @connection.stubs(:[]).returns(@db)
17
+
18
+ @connection.stubs(:replica_set_name).returns(nil)
19
+ @connection.stubs(:log)
20
+ @arbiters = ['localhost:27020']
21
+ @hosts = ['localhost:27017', 'localhost:27018', 'localhost:27019',
22
+ 'localhost:27020']
23
+
24
+ @db.stubs(:command).returns(
25
+ # First call to get a socket.
26
+ {'ismaster' => true, 'hosts' => @hosts, 'arbiters' => @arbiters},
27
+
28
+ # Subsequent calls to configure pools.
29
+ {'ismaster' => true, 'hosts' => @hosts, 'arbiters' => @arbiters},
30
+ {'secondary' => true, 'hosts' => @hosts, 'arbiters' => @arbiters},
31
+ {'secondary' => true, 'hosts' => @hosts, 'arbiters' => @arbiters},
32
+ {'arbiterOnly' => true, 'hosts' => @hosts, 'arbiters' => @arbiters})
33
+
34
+ seeds = [['localhost', 27017]]
35
+ manager = Mongo::PoolManager.new(@connection, seeds)
36
+ manager.connect
37
+
38
+ assert_equal ['localhost', 27017], manager.primary
39
+ assert_equal 27017, manager.primary_pool.port
40
+ assert_equal 2, manager.secondaries.length
41
+ assert_equal 27018, manager.secondary_pools[0].port
42
+ assert_equal [['localhost', 27020]], manager.arbiters
43
+ end
44
+
45
+ end
46
+
47
+ end
@@ -0,0 +1,9 @@
1
+ require './test/test_helper'
2
+ include Mongo
3
+
4
+ class PoolTest < Test::Unit::TestCase
5
+ context "Initialization: " do
6
+ should "do" do
7
+ end
8
+ end
9
+ end
@@ -0,0 +1,101 @@
1
+ require './test/test_helper'
2
+
3
+ class ReadTest < Test::Unit::TestCase
4
+
5
+ context "Read mode on standard connection: " do
6
+ setup do
7
+ @read_preference = :secondary
8
+ @con = Mongo::Connection.new('localhost', 27017, :read => @read_preference, :connect => false)
9
+ end
10
+
11
+ end
12
+
13
+ context "Read mode on connection: " do
14
+ setup do
15
+ @read_preference = :secondary
16
+ @con = Mongo::ReplSetConnection.new(['localhost', 27017], :read => @read_preference, :connect => false)
17
+ end
18
+
19
+ should "store read preference on Connection" do
20
+ assert_equal @read_preference, @con.read_preference
21
+ end
22
+
23
+ should "propogate to DB" do
24
+ db = @con['foo']
25
+ assert_equal @read_preference, db.read_preference
26
+
27
+ db = @con.db('foo')
28
+ assert_equal @read_preference, db.read_preference
29
+
30
+ db = DB.new('foo', @con)
31
+ assert_equal @read_preference, db.read_preference
32
+ end
33
+
34
+ should "allow db override" do
35
+ db = DB.new('foo', @con, :read => :primary)
36
+ assert_equal :primary, db.read_preference
37
+
38
+ db = @con.db('foo', :read => :primary)
39
+ assert_equal :primary, db.read_preference
40
+ end
41
+
42
+ context "on DB: " do
43
+ setup do
44
+ @db = @con['foo']
45
+ end
46
+
47
+ should "propogate to collection" do
48
+ col = @db.collection('bar')
49
+ assert_equal @read_preference, col.read_preference
50
+
51
+ col = @db['bar']
52
+ assert_equal @read_preference, col.read_preference
53
+
54
+ col = Collection.new('bar', @db)
55
+ assert_equal @read_preference, col.read_preference
56
+ end
57
+
58
+ should "allow override on collection" do
59
+ col = @db.collection('bar', :read => :primary)
60
+ assert_equal :primary, col.read_preference
61
+
62
+ col = Collection.new('bar', @db, :read => :primary)
63
+ assert_equal :primary, col.read_preference
64
+ end
65
+ end
66
+
67
+ context "on read mode ops" do
68
+ setup do
69
+ @col = @con['foo']['bar']
70
+ @mock_socket = stub()
71
+ end
72
+
73
+ should "use default value on query" do
74
+ @con.expects(:receive_message).with do |o, m, l, s, c, r|
75
+ r == :secondary
76
+ end.returns([[], 0, 0])
77
+
78
+ @col.find_one({:a => 1})
79
+ end
80
+
81
+ should "allow override default value on query" do
82
+ @con.expects(:receive_message).with do |o, m, l, s, c, r|
83
+ r == :primary
84
+ end.returns([[], 0, 0])
85
+
86
+ @col.find_one({:a => 1}, :read => :primary)
87
+ end
88
+
89
+ should "allow override alternate value on query" do
90
+ # TODO: enable this test once we enable reading from tags.
91
+ # @con.expects(:receive_message).with do |o, m, l, s, c, r|
92
+ # tags = {:dc => "ny"}
93
+ # end.returns([[], 0, 0])
94
+
95
+ assert_raise MongoArgumentError do
96
+ @col.find_one({:a => 1}, :read => {:dc => "ny"})
97
+ end
98
+ end
99
+ end
100
+ end
101
+ end
@@ -0,0 +1,125 @@
1
+ require './test/test_helper'
2
+
3
+ class SafeTest < Test::Unit::TestCase
4
+
5
+ context "Safe mode on connection: " do
6
+ setup do
7
+ @safe_value = {:w => 7}
8
+ @con = Mongo::Connection.new('localhost', 27017, :safe => @safe_value, :connect => false)
9
+ end
10
+
11
+ should "propogate to DB" do
12
+ db = @con['foo']
13
+ assert_equal @safe_value, db.safe
14
+
15
+
16
+ db = @con.db('foo')
17
+ assert_equal @safe_value, db.safe
18
+
19
+ db = DB.new('foo', @con)
20
+ assert_equal @safe_value, db.safe
21
+ end
22
+
23
+ should "allow db override" do
24
+ db = DB.new('foo', @con, :safe => false)
25
+ assert_equal false, db.safe
26
+
27
+ db = @con.db('foo', :safe => false)
28
+ assert_equal false, db.safe
29
+ end
30
+
31
+ context "on DB: " do
32
+ setup do
33
+ @db = @con['foo']
34
+ end
35
+
36
+ should "propogate to collection" do
37
+ col = @db.collection('bar')
38
+ assert_equal @safe_value, col.safe
39
+
40
+ col = @db['bar']
41
+ assert_equal @safe_value, col.safe
42
+
43
+ col = Collection.new('bar', @db)
44
+ assert_equal @safe_value, col.safe
45
+ end
46
+
47
+ should "allow override on collection" do
48
+ col = @db.collection('bar', :safe => false)
49
+ assert_equal false, col.safe
50
+
51
+ col = Collection.new('bar', @db, :safe => false)
52
+ assert_equal false, col.safe
53
+ end
54
+ end
55
+
56
+ context "on operations supporting safe mode" do
57
+ setup do
58
+ @col = @con['foo']['bar']
59
+ end
60
+
61
+ should "use default value on insert" do
62
+ @con.expects(:send_message_with_safe_check).with do |op, msg, log, n, safe|
63
+ safe == @safe_value
64
+ end
65
+
66
+ @col.insert({:a => 1})
67
+ end
68
+
69
+ should "allow override alternate value on insert" do
70
+ @con.expects(:send_message_with_safe_check).with do |op, msg, log, n, safe|
71
+ safe == {:w => 100}
72
+ end
73
+
74
+ @col.insert({:a => 1}, :safe => {:w => 100})
75
+ end
76
+
77
+ should "allow override to disable on insert" do
78
+ @con.expects(:send_message)
79
+ @col.insert({:a => 1}, :safe => false)
80
+ end
81
+
82
+ should "use default value on update" do
83
+ @con.expects(:send_message_with_safe_check).with do |op, msg, log, n, safe|
84
+ safe == @safe_value
85
+ end
86
+
87
+ @col.update({:a => 1}, {:a => 2})
88
+ end
89
+
90
+ should "allow override alternate value on update" do
91
+ @con.expects(:send_message_with_safe_check).with do |op, msg, log, n, safe|
92
+ safe == {:w => 100}
93
+ end
94
+
95
+ @col.update({:a => 1}, {:a => 2}, :safe => {:w => 100})
96
+ end
97
+
98
+ should "allow override to disable on update" do
99
+ @con.expects(:send_message)
100
+ @col.update({:a => 1}, {:a => 2}, :safe => false)
101
+ end
102
+
103
+ should "use default value on remove" do
104
+ @con.expects(:send_message_with_safe_check).with do |op, msg, log, n, safe|
105
+ safe == @safe_value
106
+ end
107
+
108
+ @col.remove
109
+ end
110
+
111
+ should "allow override alternate value on remove" do
112
+ @con.expects(:send_message_with_safe_check).with do |op, msg, log, n, safe|
113
+ safe == {:w => 100}
114
+ end
115
+
116
+ @col.remove({}, :safe => {:w => 100})
117
+ end
118
+
119
+ should "allow override to disable on remove" do
120
+ @con.expects(:send_message)
121
+ @col.remove({}, :safe => false)
122
+ end
123
+ end
124
+ end
125
+ end
@@ -0,0 +1,92 @@
1
+ __END__
2
+ require './test/test_helper'
3
+
4
+ class TestThreading < Test::Unit::TestCase
5
+ include Mongo
6
+
7
+ def test_uri_without_port
8
+ parser = Mongo::URIParser.new('mongodb://localhost')
9
+ assert_equal 1, parser.nodes.length
10
+ assert_equal 'localhost', parser.nodes[0][0]
11
+ assert_equal 27017, parser.nodes[0][1]
12
+ end
13
+
14
+ def test_basic_uri
15
+ parser = Mongo::URIParser.new('mongodb://localhost:27018')
16
+ assert_equal 1, parser.nodes.length
17
+ assert_equal 'localhost', parser.nodes[0][0]
18
+ assert_equal 27018, parser.nodes[0][1]
19
+ end
20
+
21
+ def test_multiple_uris
22
+ parser = Mongo::URIParser.new('mongodb://a.example.com:27018,b.example.com')
23
+ assert_equal 2, parser.nodes.length
24
+ assert_equal 'a.example.com', parser.nodes[0][0]
25
+ assert_equal 27018, parser.nodes[0][1]
26
+ assert_equal 'b.example.com', parser.nodes[1][0]
27
+ assert_equal 27017, parser.nodes[1][1]
28
+ end
29
+
30
+ def test_complex_passwords
31
+ parser = Mongo::URIParser.new('mongodb://bob:secret.word@a.example.com:27018/test')
32
+ assert_equal "bob", parser.auths[0]["username"]
33
+ assert_equal "secret.word", parser.auths[0]["password"]
34
+
35
+ parser = Mongo::URIParser.new('mongodb://bob:s-_3#%R.t@a.example.com:27018/test')
36
+ assert_equal "bob", parser.auths[0]["username"]
37
+ assert_equal "s-_3#%R.t", parser.auths[0]["password"]
38
+ end
39
+
40
+ def test_passwords_contain_no_commas
41
+ assert_raise MongoArgumentError do
42
+ Mongo::URIParser.new('mongodb://bob:a,b@a.example.com:27018/test')
43
+ end
44
+ end
45
+
46
+ def test_multiple_uris_with_auths
47
+ parser = Mongo::URIParser.new('mongodb://bob:secret@a.example.com:27018/test,joe:secret2@b.example.com/test2')
48
+ assert_equal 2, parser.nodes.length
49
+ assert_equal 'a.example.com', parser.nodes[0][0]
50
+ assert_equal 27018, parser.nodes[0][1]
51
+ assert_equal 'b.example.com', parser.nodes[1][0]
52
+ assert_equal 27017, parser.nodes[1][1]
53
+ assert_equal 2, parser.auths.length
54
+ assert_equal "bob", parser.auths[0]["username"]
55
+ assert_equal "secret", parser.auths[0]["password"]
56
+ assert_equal "test", parser.auths[0]["db_name"]
57
+ assert_equal "joe", parser.auths[1]["username"]
58
+ assert_equal "secret2", parser.auths[1]["password"]
59
+ assert_equal "test2", parser.auths[1]["db_name"]
60
+ end
61
+
62
+ def test_opts_basic
63
+ parser = Mongo::URIParser.new('mongodb://localhost:27018?connect=direct;slaveok=true;safe=true')
64
+ assert_equal 'direct', parser.connect
65
+ assert parser.slaveok
66
+ assert parser.safe
67
+ end
68
+
69
+ def test_opts_with_amp_separator
70
+ parser = Mongo::URIParser.new('mongodb://localhost:27018?connect=direct&slaveok=true&safe=true')
71
+ assert_equal 'direct', parser.connect
72
+ assert parser.slaveok
73
+ assert parser.safe
74
+ end
75
+
76
+ def test_opts_safe
77
+ parser = Mongo::URIParser.new('mongodb://localhost:27018?safe=true;w=2;wtimeout=200;fsync=true')
78
+ assert parser.safe
79
+ assert_equal 2, parser.w
80
+ assert_equal 200, parser.wtimeout
81
+ assert parser.fsync
82
+ end
83
+
84
+ def test_opts_replica_set
85
+ assert_raise_error MongoArgumentError, "specify that connect=replicaset" do
86
+ Mongo::URIParser.new('mongodb://localhost:27018?replicaset=foo')
87
+ end
88
+ parser = Mongo::URIParser.new('mongodb://localhost:27018?connect=replicaset;replicaset=foo')
89
+ assert_equal 'foo', parser.replicaset
90
+ assert_equal 'replicaset', parser.connect
91
+ end
92
+ end