PYTHON-715 Fix tests for MongoDB >= 2.7.1 when running with auth enabled.

This commit is contained in:
Luke Lovett 2014-06-25 02:21:24 +00:00
parent c2e6471ee6
commit d7ec3a7704
17 changed files with 322 additions and 255 deletions

View File

@ -787,8 +787,9 @@ class Database(common.BaseObject):
# users.
if exc.code in common.COMMAND_NOT_FOUND_CODES:
self._legacy_add_user(name, password, read_only, **kwargs)
# Unauthorized. MongoDB >= 2.7.1 has a narrow localhost exception,
# and we must add a user before sending commands.
return
# Unauthorized. Attempt to create the user in case of
# localhost exception.
elif exc.code == 13:
self._create_or_update_user(
True, name, password, read_only, **kwargs)

View File

@ -45,6 +45,9 @@ port2 = int(os.environ.get("DB_PORT2", 27018))
host3 = _unicode(os.environ.get("DB_IP3", 'localhost'))
port3 = int(os.environ.get("DB_PORT3", 27019))
db_user = _unicode(os.environ.get("DB_USER", "user"))
db_pwd = _unicode(os.environ.get("DB_PASSWORD", "password"))
class ClientContext(object):
@ -70,12 +73,31 @@ class ClientContext(object):
self.w = len(self.ismaster.get("hosts", [])) or 1
self.setname = self.ismaster.get('setName', '')
self.rs_client = None
self.version = Version.from_client(self.client)
if self.setname:
self.rs_client = pymongo.MongoReplicaSetClient(
pair, replicaSet=self.setname)
self.cmd_line = self.client.admin.command('getCmdLineOpts')
self.version = Version.from_client(self.client)
self.auth_enabled = self._server_started_with_auth()
try:
self.cmd_line = self.client.admin.command('getCmdLineOpts')
except pymongo.errors.OperationFailure as e:
if e.code == 13:
# Unauthorized.
self.auth_enabled = True
else:
raise
else:
self.auth_enabled = self._server_started_with_auth()
if self.auth_enabled:
roles = {}
if self.version.at_least(2, 5, 3, -1):
roles = {'roles': ['root']}
self.client.admin.add_user(db_user, db_pwd, **roles)
self.client.admin.authenticate(db_user, db_pwd)
if self.rs_client:
self.rs_client.admin.authenticate(db_user, db_pwd)
self.cmd_line = self.client.admin.command('getCmdLineOpts')
# May not have this if OperationFailure was raised earlier.
self.cmd_line = self.client.admin.command('getCmdLineOpts')
self.test_commands_enabled = ('testCommandsEnabled=1'
in self.cmd_line['argv'])
self.is_mongos = (self.ismaster.get('msg') == 'isdbgrid')
@ -143,6 +165,12 @@ class ClientContext(object):
"Authentication is not enabled on the server",
func=func))
def require_no_auth(self, func):
"""Run a test only if the server is running without auth enabled."""
return self._require(not self.auth_enabled,
"Authentication must not be enabled on the server",
func=func)
def require_replica_set(self, func):
"""Run a test only if the client is connected to a replica set."""
return self._require(self.rs_client is not None,
@ -183,25 +211,27 @@ class IntegrationTest(unittest.TestCase):
pass
def connection_string(seeds=[pair]):
if client_context.auth_enabled:
return "mongodb://%s:%s@%s" % (db_user, db_pwd, ','.join(seeds))
return "mongodb://%s" % pair
def setup():
warnings.resetwarnings()
warnings.simplefilter("always")
def teardown():
try:
c = pymongo.MongoClient(host, port)
except pymongo.errors.ConnectionFailure:
# Tests where ssl=True can cause connection failures here.
# Ignore and continue.
return
c = client_context.client
c.drop_database("pymongo-pooling-tests")
c.drop_database("pymongo_test")
c.drop_database("pymongo_test1")
c.drop_database("pymongo_test2")
c.drop_database("pymongo_test_mike")
c.drop_database("pymongo_test_bernie")
if client_context.auth_enabled:
c.admin.remove_user(db_user)
class PymongoTestRunner(unittest.TextTestRunner):

View File

@ -235,10 +235,11 @@ class TestAuthURIOptions(unittest.TestCase):
client = MongoClient(host, port)
response = client.admin.command('ismaster')
self.set_name = str(response.get('setName', ''))
client.admin.add_user('admin', 'pass', roles=['userAdminAnyDatabase',
'dbAdminAnyDatabase',
'readWriteAnyDatabase',
'clusterAdmin'])
client_context.client.admin.add_user('admin', 'pass',
roles=['userAdminAnyDatabase',
'dbAdminAnyDatabase',
'readWriteAnyDatabase',
'clusterAdmin'])
client.admin.authenticate('admin', 'pass')
client.pymongo_test.add_user('user', 'pass',
roles=['userAdmin', 'readWrite'])
@ -314,26 +315,14 @@ class TestDelegatedAuth(unittest.TestCase):
@client_context.require_version_max(2, 5, 3)
@client_context.require_version_min(2, 4, 0)
def setUp(self):
self.client = MongoClient(host, port)
# Give admin all privileges.
self.client.admin.add_user('admin', 'pass',
roles=['readAnyDatabase',
'readWriteAnyDatabase',
'userAdminAnyDatabase',
'dbAdminAnyDatabase',
'clusterAdmin'])
self.client = client_context.client
def tearDown(self):
self.client.admin.authenticate('admin', 'pass')
self.client.pymongo_test.remove_user('user')
self.client.pymongo_test2.remove_user('user')
self.client.pymongo_test2.foo.remove()
self.client.admin.remove_user('admin')
self.client.admin.logout()
self.client = None
self.client.pymongo_test2.foo.drop()
def test_delegated_auth(self):
self.client.admin.authenticate('admin', 'pass')
self.client.pymongo_test2.foo.remove()
self.client.pymongo_test2.foo.insert({})
# User definition with no roles in pymongo_test.
@ -342,27 +331,27 @@ class TestDelegatedAuth(unittest.TestCase):
self.client.pymongo_test2.add_user('user',
userSource='pymongo_test',
roles=['read'])
self.client.admin.logout()
auth_c = MongoClient(host, port)
self.assertRaises(OperationFailure,
self.client.pymongo_test2.foo.find_one)
auth_c.pymongo_test2.foo.find_one)
# Auth must occur on the db where the user is defined.
self.assertRaises(OperationFailure,
self.client.pymongo_test2.authenticate,
auth_c.pymongo_test2.authenticate,
'user', 'pass')
# Auth directly
self.assertTrue(self.client.pymongo_test.authenticate('user', 'pass'))
self.assertTrue(self.client.pymongo_test2.foo.find_one())
self.client.pymongo_test.logout()
self.assertTrue(auth_c.pymongo_test.authenticate('user', 'pass'))
self.assertTrue(auth_c.pymongo_test2.foo.find_one())
auth_c.pymongo_test.logout()
self.assertRaises(OperationFailure,
self.client.pymongo_test2.foo.find_one)
auth_c.pymongo_test2.foo.find_one)
# Auth using source
self.assertTrue(self.client.pymongo_test2.authenticate(
self.assertTrue(auth_c.pymongo_test2.authenticate(
'user', 'pass', source='pymongo_test'))
self.assertTrue(self.client.pymongo_test2.foo.find_one())
self.assertTrue(auth_c.pymongo_test2.foo.find_one())
# Must logout from the db authenticate was called on.
self.client.pymongo_test2.logout()
auth_c.pymongo_test2.logout()
self.assertRaises(OperationFailure,
self.client.pymongo_test2.foo.find_one)
auth_c.pymongo_test2.foo.find_one)
if __name__ == "__main__":

View File

@ -20,8 +20,9 @@ sys.path[0:0] = [""]
from bson import InvalidDocument, SON
from bson.py3compat import string_type
from pymongo import MongoClient
from pymongo.errors import BulkWriteError, InvalidOperation, OperationFailure
from test import client_context, unittest
from test import client_context, unittest, host, port
from test.utils import oid_generated_on_client, remove_all_users
@ -1151,8 +1152,6 @@ class TestBulkAuthorization(BulkTestBase):
super(TestBulkAuthorization, self).setUp()
self.coll.remove()
self.db.add_user('dbOwner', 'pw', roles=['dbOwner'])
self.db.authenticate('dbOwner', 'pw')
self.db.add_user('readonly', 'pw', roles=['read'])
self.db.command(
'createRole', 'noremove',
@ -1163,31 +1162,30 @@ class TestBulkAuthorization(BulkTestBase):
roles=[])
self.db.add_user('noremove', 'pw', roles=['noremove'])
self.db.logout()
def tearDown(self):
self.db.logout()
self.db.authenticate('dbOwner', 'pw')
self.db.command('dropRole', 'noremove')
remove_all_users(self.db)
self.db.logout()
self.db.connection.disconnect()
def test_readonly(self):
# We test that an authorization failure aborts the batch and is raised
# as OperationFailure.
db = client_context.client.pymongo_test
cli = MongoClient(host, port)
db = cli.pymongo_test
coll = db.test
db.authenticate('readonly', 'pw')
bulk = self.coll.initialize_ordered_bulk_op()
bulk = coll.initialize_ordered_bulk_op()
bulk.insert({'x': 1})
self.assertRaises(OperationFailure, bulk.execute)
def test_no_remove(self):
# We test that an authorization failure aborts the batch and is raised
# as OperationFailure.
db = client_context.client.pymongo_test
cli = MongoClient(host, port)
db = cli.pymongo_test
coll = db.test
db.authenticate('noremove', 'pw')
bulk = self.coll.initialize_ordered_bulk_op()
bulk = coll.initialize_ordered_bulk_op()
bulk.insert({'x': 1})
bulk.find({'x': 2}).upsert().replace_one({'x': 2})
bulk.find({}).remove() # Prohibited.
@ -1195,6 +1193,5 @@ class TestBulkAuthorization(BulkTestBase):
self.assertRaises(OperationFailure, bulk.execute)
self.assertEqual(set([1, 2]), set(self.coll.distinct('x')))
if __name__ == "__main__":
unittest.main()

View File

@ -29,7 +29,7 @@ from bson.tz_util import utc
from pymongo.mongo_client import MongoClient
from pymongo.database import Database
from pymongo.pool import SocketInfo
from pymongo import thread_util, common
from pymongo import thread_util
from pymongo.errors import (AutoReconnect,
ConfigurationError,
ConnectionFailure,
@ -37,6 +37,7 @@ from pymongo.errors import (AutoReconnect,
OperationFailure,
PyMongoError)
from test import (client_context,
connection_string,
host,
pair,
port,
@ -46,6 +47,7 @@ from test import (client_context,
from test.pymongo_mocks import MockClient
from test.utils import (assertRaisesExactly,
delay,
get_client,
remove_all_users,
server_is_master_with_slave,
TestRequestMixin,
@ -55,13 +57,7 @@ from test.utils import (assertRaisesExactly,
get_pool)
def get_client(*args, **kwargs):
return MongoClient(host, port, *args, **kwargs)
class TestClientNoConnect(unittest.TestCase):
"""MongoClient unit tests that don't require connecting to MongoDB."""
class TestClient(unittest.TestCase, TestRequestMixin):
@classmethod
def setUpClass(cls):
cls.client = MongoClient(host, port, _connect=False)
@ -158,7 +154,7 @@ class TestClient(IntegrationTest, TestRequestMixin):
self.assertEqual(None, c.host)
self.assertEqual(None, c.port)
c.pymongo_test.test.find_one() # Auto-connect.
c.pymongo_test.command('ismaster') # Auto-connect.
self.assertEqual(host, c.host)
self.assertEqual(port, c.port)
@ -282,8 +278,8 @@ class TestClient(IntegrationTest, TestRequestMixin):
c.end_request()
self.assertFalse(c.in_request())
c.copy_database("pymongo_test", "pymongo_test2",
"%s:%d" % (host, port))
c.copy_database("pymongo_test", "pymongo_test2")
# copy_database() didn't accidentally restart the request
self.assertFalse(c.in_request())
@ -295,30 +291,30 @@ class TestClient(IntegrationTest, TestRequestMixin):
c.drop_database("pymongo_test1")
c.admin.add_user("admin", "password")
c.admin.authenticate("admin", "password")
auth_c = MongoClient(host, port)
auth_c.admin.authenticate("admin", "password")
try:
c.pymongo_test.add_user("mike", "password")
auth_c.pymongo_test.add_user("mike", "password")
self.assertRaises(OperationFailure, c.copy_database,
self.assertRaises(OperationFailure, auth_c.copy_database,
"pymongo_test", "pymongo_test1",
username="foo", password="bar")
self.assertFalse("pymongo_test1" in c.database_names())
self.assertFalse("pymongo_test1" in auth_c.database_names())
self.assertRaises(OperationFailure, c.copy_database,
self.assertRaises(OperationFailure, auth_c.copy_database,
"pymongo_test", "pymongo_test1",
username="mike", password="bar")
self.assertFalse("pymongo_test1" in c.database_names())
self.assertFalse("pymongo_test1" in auth_c.database_names())
c.copy_database("pymongo_test", "pymongo_test1",
username="mike", password="password")
self.assertTrue("pymongo_test1" in c.database_names())
self.assertEqual("bar", c.pymongo_test1.test.find_one()["foo"])
auth_c.copy_database("pymongo_test", "pymongo_test1",
username="mike", password="password")
self.assertTrue("pymongo_test1" in auth_c.database_names())
self.assertEqual("bar",
auth_c.pymongo_test1.test.find_one()["foo"])
finally:
# Cleanup
remove_all_users(c.pymongo_test)
c.admin.remove_user("admin")
c.admin.logout()
c.disconnect()
def test_disconnect(self):
coll = self.client.pymongo_test.bar
@ -340,7 +336,6 @@ class TestClient(IntegrationTest, TestRequestMixin):
@client_context.require_auth
def test_auth_from_uri(self):
self.client.admin.add_user("admin", "pass")
self.client.admin.authenticate("admin", "pass")
try:
self.client.pymongo_test.add_user(
"user", "pass", roles=['userAdmin', 'readWrite'])
@ -378,9 +373,7 @@ class TestClient(IntegrationTest, TestRequestMixin):
finally:
# Clean up.
remove_all_users(self.client.pymongo_test)
remove_all_users(self.client.admin)
self.client.admin.logout()
self.client.disconnect()
self.client.admin.remove_user('admin')
@client_context.require_auth
def test_lazy_auth_raises_operation_failure(self):
@ -394,7 +387,9 @@ class TestClient(IntegrationTest, TestRequestMixin):
def test_unix_socket(self):
if not hasattr(socket, "AF_UNIX"):
raise SkipTest("UNIX-sockets are not supported on this system")
if sys.platform == 'darwin' and client_context.auth_enabled:
if (sys.platform == 'darwin' and
client_context.auth_enabled and
not client_context.version.at_least(2, 7, 1)):
raise SkipTest("SERVER-8492")
mongodb_socket = '/tmp/mongodb-27017.sock'
@ -491,7 +486,7 @@ class TestClient(IntegrationTest, TestRequestMixin):
finally:
c.document_class = dict
c = MongoClient(host, port, document_class=SON)
c = get_client(pair, document_class=SON)
db = c.pymongo_test
self.assertEqual(SON, c.document_class)
@ -511,29 +506,28 @@ class TestClient(IntegrationTest, TestRequestMixin):
self.assertEqual(10.5, get_pool(client).opts.socket_timeout)
def test_socket_timeout_ms_validation(self):
c = get_client(socketTimeoutMS=10 * 1000)
c = get_client(pair, socketTimeoutMS=10 * 1000)
self.assertEqual(10, c._MongoClient__pool_opts.socket_timeout)
c = get_client(socketTimeoutMS=None)
c = get_client(pair, socketTimeoutMS=None)
self.assertEqual(None, c._MongoClient__pool_opts.socket_timeout)
self.assertRaises(ConfigurationError,
get_client, socketTimeoutMS=0)
get_client, pair, socketTimeoutMS=0)
self.assertRaises(ConfigurationError,
get_client, socketTimeoutMS=-1)
get_client, pair, socketTimeoutMS=-1)
self.assertRaises(ConfigurationError,
get_client, socketTimeoutMS=1e10)
get_client, pair, socketTimeoutMS=1e10)
self.assertRaises(ConfigurationError,
get_client, socketTimeoutMS='foo')
get_client, pair, socketTimeoutMS='foo')
def test_socket_timeout(self):
no_timeout = self.client
timeout_sec = 1
timeout = MongoClient(
host, port, socketTimeoutMS=1000 * timeout_sec)
timeout = get_client(pair, socketTimeoutMS=1000 * timeout_sec)
no_timeout.pymongo_test.drop_collection("test")
no_timeout.pymongo_test.test.insert({"x": 1})
@ -560,7 +554,7 @@ class TestClient(IntegrationTest, TestRequestMixin):
def test_tz_aware(self):
self.assertRaises(ConfigurationError, MongoClient, tz_aware='foo')
aware = MongoClient(host, port, tz_aware=True)
aware = get_client(pair, tz_aware=True)
naive = self.client
aware.pymongo_test.drop_collection("test")
@ -622,7 +616,7 @@ class TestClient(IntegrationTest, TestRequestMixin):
def test_contextlib(self):
import contextlib
client = get_client(auto_start_request=False)
client = get_client(pair, auto_start_request=False)
client.pymongo_test.drop_collection("test")
client.pymongo_test.test.insert({"foo": "bar"})
@ -675,13 +669,13 @@ class TestClient(IntegrationTest, TestRequestMixin):
for bad_horrible_value in (None, 5, 'hi!'):
self.assertRaises(
(TypeError, ConfigurationError),
lambda: get_client(auto_start_request=bad_horrible_value)
lambda: get_client(pair, auto_start_request=bad_horrible_value)
)
# auto_start_request should default to False
self.assertFalse(self.client.auto_start_request)
client = get_client(auto_start_request=True)
client = get_client(pair, auto_start_request=True)
self.assertTrue(client.auto_start_request)
# Assure we acquire a request socket.
@ -834,7 +828,7 @@ class TestClient(IntegrationTest, TestRequestMixin):
def test_operation_failure_with_request(self):
# Ensure MongoClient doesn't close socket after it gets an error
# response to getLastError. PYTHON-395.
c = get_client(auto_start_request=True)
c = get_client(pair, auto_start_request=True)
pool = get_pool(c)
# Pool reserves a socket for this thread.
@ -867,7 +861,7 @@ class TestClient(IntegrationTest, TestRequestMixin):
_connect=False)
c.set_wire_version_range('a:1', 1, 5)
c.db.collection.find_one() # Connect.
c.db.command('ismaster') # Connect.
self.assertEqual(c.min_wire_version, 1)
self.assertEqual(c.max_wire_version, 5)
@ -889,7 +883,7 @@ class TestClient(IntegrationTest, TestRequestMixin):
# Starts with default max batch size.
self.assertEqual(1000, c.max_write_batch_size)
c.db.collection.find_one() # Connect.
c.db.command('ismaster') # Connect.
# Uses primary's max batch size.
self.assertEqual(c.max_write_batch_size, 1)
@ -897,7 +891,7 @@ class TestClient(IntegrationTest, TestRequestMixin):
c.mock_primary = 'b:2'
c.disconnect()
self.assertEqual(1000, c.max_write_batch_size)
c.db.collection.find_one() # Connect.
c.db.command('ismaster') # Connect.
self.assertEqual(c.max_write_batch_size, 2)
def test_wire_version_mongos_ha(self):
@ -911,7 +905,7 @@ class TestClient(IntegrationTest, TestRequestMixin):
c.set_wire_version_range('a:1', 2, 5)
c.set_wire_version_range('b:2', 2, 2)
c.set_wire_version_range('c:3', 1, 1)
c.db.collection.find_one() # Connect.
c.db.command('ismaster') # Connect.
# Which member did we use?
used_host = '%s:%s' % (c.host, c.port)
@ -923,7 +917,7 @@ class TestClient(IntegrationTest, TestRequestMixin):
c.set_wire_version_range('b:2', 0, 0)
c.set_wire_version_range('c:3', 0, 0)
c.disconnect()
c.db.collection.find_one()
c.db.command('ismaster')
used_host = '%s:%s' % (c.host, c.port)
expected_min, expected_max = c.mock_wire_versions[used_host]
self.assertEqual(expected_min, c.min_wire_version)
@ -939,20 +933,20 @@ class TestClient(IntegrationTest, TestRequestMixin):
MongoClient, host, port, replicaSet='bad' + name)
def test_lazy_connect_w0(self):
client = get_client(_connect=False)
client = get_client(connection_string(), _connect=False)
client.pymongo_test.test.insert({}, w=0)
client = get_client(_connect=False)
client = get_client(connection_string(), _connect=False)
client.pymongo_test.test.update({}, {'$set': {'x': 1}}, w=0)
client = get_client(_connect=False)
client = get_client(connection_string(), _connect=False)
client.pymongo_test.test.remove(w=0)
class TestClientLazyConnect(IntegrationTest, _TestLazyConnectMixin):
def _get_client(self, **kwargs):
return get_client(**kwargs)
return get_client(connection_string(), **kwargs)
class TestClientLazyConnectBadSeeds(IntegrationTest):
@ -962,7 +956,7 @@ class TestClientLazyConnectBadSeeds(IntegrationTest):
# Assume there are no open mongods listening on a.com, b.com, ....
bad_seeds = ['%s.com' % chr(ord('a') + i) for i in range(10)]
return MongoClient(bad_seeds, **kwargs)
return get_client(bad_seeds, **kwargs)
def test_connect(self):
def reset(dummy):
@ -993,7 +987,7 @@ class TestClientLazyConnectOneGoodSeed(
# MongoClient puts the seeds in a set before iterating, so order is
# undefined.
return MongoClient(seeds, **kwargs)
return get_client(connection_string(seeds=seeds), **kwargs)
def test_insert(self):
def reset(collection):
@ -1030,7 +1024,7 @@ class TestMongoClientFailover(IntegrationTest):
# Force reconnect.
c.disconnect()
c.db.collection.find_one()
c.db.command('ismaster')
self.assertEqual('b', c.host)
self.assertEqual(2, c.port)
@ -1059,7 +1053,7 @@ class TestMongoClientFailover(IntegrationTest):
# So it can reconnect.
c.revive_host('a:1')
c.db.collection.find_one()
c.db.command('ismaster')
if __name__ == "__main__":

View File

@ -39,7 +39,6 @@ from pymongo import message as message_module
from pymongo import MongoClient
from pymongo.collection import Collection
from pymongo.command_cursor import CommandCursor
from pymongo.database import Database
from pymongo.read_preferences import ReadPreference
from pymongo.son_manipulator import SONManipulator
from pymongo.errors import (DocumentTooLarge,
@ -52,7 +51,7 @@ from pymongo.errors import (DocumentTooLarge,
from test.test_client import get_client, IntegrationTest
from test.utils import (is_mongos, joinall, enable_text_search, get_pool,
oid_generated_on_client)
from test import client_context, host, port, qcheck, unittest
from test import client_context, host, port, pair, qcheck, unittest
class TestCollectionNoConnect(unittest.TestCase):
@ -1715,7 +1714,7 @@ class TestCollection(IntegrationTest):
# Insert enough documents to require more than one batch
self.db.test.insert([{'i': i} for i in range(150)])
client = get_client(max_pool_size=1)
client = get_client(pair, max_pool_size=1)
socks = get_pool(client).sockets
self.assertEqual(1, len(socks))

View File

@ -27,6 +27,7 @@ from pymongo.mongo_client import MongoClient
from pymongo.mongo_replica_set_client import MongoReplicaSetClient
from pymongo.errors import ConfigurationError, OperationFailure
from test import client_context, pair, unittest
from test.utils import get_client, get_rs_client
@client_context.require_connection
@ -208,7 +209,7 @@ class TestCommon(unittest.TestCase):
self.assertEqual(wc.to_dict(), coll.write_concern)
def test_mongo_client(self):
m = MongoClient(pair, w=0)
m = get_client(pair, w=0)
coll = m.pymongo_test.write_concern_test
coll.drop()
doc = {"_id": ObjectId()}
@ -217,16 +218,16 @@ class TestCommon(unittest.TestCase):
self.assertTrue(coll.insert(doc))
self.assertRaises(OperationFailure, coll.insert, doc, w=1)
m = MongoClient(pair)
m = get_client(pair)
coll = m.pymongo_test.write_concern_test
self.assertTrue(coll.insert(doc, w=0))
self.assertRaises(OperationFailure, coll.insert, doc)
self.assertRaises(OperationFailure, coll.insert, doc, w=1)
m = MongoClient("mongodb://%s/" % (pair,))
m = get_client("mongodb://%s/" % (pair,))
coll = m.pymongo_test.write_concern_test
self.assertRaises(OperationFailure, coll.insert, doc)
m = MongoClient("mongodb://%s/?w=0" % (pair,))
m = get_client("mongodb://%s/?w=0" % (pair,))
coll = m.pymongo_test.write_concern_test
self.assertTrue(coll.insert(doc))
@ -237,7 +238,7 @@ class TestCommon(unittest.TestCase):
@client_context.require_replica_set
def test_mongo_replica_set_client(self):
setname = client_context.setname
m = MongoReplicaSetClient(pair, replicaSet=setname, w=0)
m = get_rs_client(pair, replicaSet=setname, w=0)
coll = m.pymongo_test.write_concern_test
coll.drop()
doc = {"_id": ObjectId()}

View File

@ -46,7 +46,13 @@ from pymongo.son_manipulator import (AutoReference,
NamespaceInjector,
SONManipulator,
ObjectIdShuffler)
from test import client_context, SkipTest, unittest, host, port, IntegrationTest
from test import (client_context,
SkipTest,
unittest,
host,
port,
pair,
IntegrationTest)
from test.utils import remove_all_users, server_started_with_auth
from test.test_client import get_client
@ -378,7 +384,9 @@ class TestDatabase(IntegrationTest):
"user", "password", digestPassword=True)
self.client.admin.add_user("admin", "password")
self.client.admin.authenticate("admin", "password")
auth_c = MongoClient(pair)
auth_c.admin.authenticate("admin", "password")
db = auth_c.pymongo_test
try:
# Add / authenticate / remove
@ -420,18 +428,17 @@ class TestDatabase(IntegrationTest):
# Cleanup
finally:
remove_all_users(db)
self.client.pymongo_test.logout()
self.client.admin.remove_user("admin")
self.client.admin.logout()
self.client.disconnect()
db.logout()
auth_c.admin.remove_user("admin")
@client_context.require_auth
def test_make_user_readonly(self):
admin = self.client.admin
admin.add_user('admin', 'pw')
auth_c = MongoClient(pair)
admin = auth_c.admin
self.client.admin.add_user('admin', 'pw')
admin.authenticate('admin', 'pw')
db = self.client.pymongo_test
db = auth_c.pymongo_test
try:
# Make a read-write user.
@ -455,16 +462,14 @@ class TestDatabase(IntegrationTest):
admin.authenticate('admin', 'pw')
remove_all_users(db)
admin.remove_user("admin")
admin.logout()
db.logout()
self.client.disconnect()
@client_context.require_version_min(2, 5, 3, -1)
@client_context.require_auth
def test_default_roles(self):
# "Admin" user
db = self.client.admin
db.add_user('admin', 'pass')
self.client.admin.add_user('admin', 'pass')
auth_c = MongoClient(pair)
db = auth_c.admin
try:
db.authenticate('admin', 'pass')
info = db.command('usersInfo', 'admin')['users'][0]
@ -481,22 +486,24 @@ class TestDatabase(IntegrationTest):
# Cleanup
finally:
db.authenticate('admin', 'pass')
remove_all_users(db)
db.remove_user('ro-admin')
db.remove_user('admin')
db.logout()
db.connection.disconnect()
# "Non-admin" user
db = self.client.pymongo_test
db.add_user('user', 'pass')
db = auth_c.pymongo_test
client_context.client.pymongo_test.add_user('user', 'pass')
try:
db.authenticate('user', 'pass')
info = db.command('usersInfo', 'user')['users'][0]
self.assertEqual("dbOwner", info['roles'][0]['role'])
db.logout()
# Read only "Non-admin" user
db.add_user('ro-user', 'pass', read_only=True)
db.logout()
client_context.client.pymongo_test.add_user('ro-user', 'pass',
read_only=True)
db.authenticate('ro-user', 'pass')
info = db.command('usersInfo', 'ro-user')['users'][0]
self.assertEqual("read", info['roles'][0]['role'])
@ -506,14 +513,15 @@ class TestDatabase(IntegrationTest):
finally:
db.authenticate('user', 'pass')
remove_all_users(db)
db.logout()
self.client.disconnect()
@client_context.require_version_min(2, 5, 3, -1)
@client_context.require_auth
def test_new_user_cmds(self):
db = self.client.pymongo_test
db.add_user("amalia", "password", roles=["userAdmin"])
auth_c = MongoClient(pair)
db = auth_c.pymongo_test
client_context.client.pymongo_test.add_user("amalia", "password",
roles=["userAdmin"])
db.authenticate("amalia", "password")
try:
# This tests the ability to update user attributes.
@ -527,15 +535,15 @@ class TestDatabase(IntegrationTest):
self.assertEqual(amalia_user["customData"], {"secret": "koalas"})
finally:
db.remove_user("amalia")
db.logout()
self.client.disconnect()
@client_context.require_auth
def test_authenticate_and_safe(self):
db = self.client.auth_test
auth_c = MongoClient(pair)
db = auth_c.auth_test
db.add_user("bernie", "password",
roles=["userAdmin", "dbAdmin", "readWrite"])
client_context.client.auth_test.add_user(
"bernie", "password",
roles=["userAdmin", "dbAdmin", "readWrite"])
db.authenticate("bernie", "password")
try:
db.test.remove({})
@ -552,8 +560,6 @@ class TestDatabase(IntegrationTest):
self.assertEqual(0, db.test.count())
finally:
db.remove_user("bernie")
db.logout()
self.client.disconnect()
@client_context.require_auth
def test_authenticate_and_request(self):
@ -561,37 +567,38 @@ class TestDatabase(IntegrationTest):
# always runs in a request, and that it restores the request state
# (in or not in a request) properly when it's finished.
self.assertFalse(self.client.auto_start_request)
db = self.client.pymongo_test
db.add_user("mike", "password",
roles=["userAdmin", "dbAdmin", "readWrite"])
auth_c = MongoClient(pair)
db = auth_c.pymongo_test
client_context.client.pymongo_test.add_user(
"mike", "password",
roles=["userAdmin", "dbAdmin", "readWrite"])
try:
self.assertFalse(self.client.in_request())
self.assertFalse(auth_c.in_request())
self.assertTrue(db.authenticate("mike", "password"))
self.assertFalse(self.client.in_request())
self.assertFalse(auth_c.in_request())
request_cx = get_client(auto_start_request=True)
request_cx = get_client(pair, auto_start_request=True)
request_db = request_cx.pymongo_test
self.assertTrue(request_db.authenticate("mike", "password"))
self.assertTrue(request_cx.in_request())
finally:
db.authenticate("mike", "password")
db.remove_user("mike")
db.logout()
request_db.logout()
self.client.disconnect()
@client_context.require_auth
def test_authenticate_multiple(self):
# Setup
users_db = self.client.pymongo_test
admin_db = self.client.admin
other_db = self.client.pymongo_test1
users_db.test.remove()
other_db.test.remove()
client_context.client.drop_database("pymongo_test")
client_context.client.drop_database("pymongo_test1")
auth_c = MongoClient(pair)
users_db = auth_c.pymongo_test
admin_db = auth_c.admin
other_db = auth_c.pymongo_test1
admin_db.add_user('admin', 'pass',
roles=["userAdminAnyDatabase", "dbAdmin",
"clusterAdmin", "readWrite"])
client_context.client.admin.add_user(
'admin', 'pass',
roles=["userAdminAnyDatabase", "dbAdmin",
"clusterAdmin", "readWrite"])
try:
self.assertTrue(admin_db.authenticate('admin', 'pass'))
@ -621,7 +628,7 @@ class TestDatabase(IntegrationTest):
other_db.test.insert, {})
# Force close all sockets
self.client.disconnect()
auth_c.disconnect()
# We should still be able to write to the regular user's db
self.assertTrue(users_db.test.remove())
@ -634,10 +641,8 @@ class TestDatabase(IntegrationTest):
# Cleanup
finally:
remove_all_users(users_db)
remove_all_users(admin_db)
admin_db.logout()
users_db.logout()
self.client.disconnect()
client_context.client.admin.remove_user('ro-admin')
client_context.client.admin.remove_user('admin')
def test_id_ordering(self):
# PyMongo attempts to have _id show up first
@ -679,6 +684,7 @@ class TestDatabase(IntegrationTest):
db.test.save(obj)
self.assertEqual(obj, db.dereference(DBRef("test", 4)))
@client_context.require_no_auth
def test_eval(self):
db = self.client.pymongo_test
db.test.remove({})
@ -843,6 +849,7 @@ class TestDatabase(IntegrationTest):
self.assertEqual("buzz", db.users.find_one()["messages"][0]["title"])
self.assertEqual("bar", db.users.find_one()["messages"][1]["title"])
@client_context.require_no_auth
def test_system_js(self):
db = self.client.pymongo_test
db.system.js.remove()

View File

@ -32,8 +32,13 @@ import gridfs
from bson.py3compat import u, StringIO, string_type
from gridfs.errors import (FileExists,
NoFile)
from test import client_context, unittest, host, port, IntegrationTest
from test.utils import joinall
from test import (client_context,
connection_string,
unittest,
host,
port,
IntegrationTest)
from test.utils import joinall, get_client
class JustWrite(threading.Thread):
@ -418,29 +423,30 @@ class TestGridfsReplicaSet(TestReplicaSetClientBase):
def test_gridfs_secondary(self):
primary_host, primary_port = self.primary
primary_connection = MongoClient(primary_host, primary_port)
primary_connection = get_client(primary_host, primary_port)
secondary_host, secondary_port = self.secondaries[0]
for secondary_connection in [
MongoClient(secondary_host, secondary_port,
read_preference=ReadPreference.SECONDARY),
]:
primary_connection.pymongo_test.drop_collection("fs.files")
primary_connection.pymongo_test.drop_collection("fs.chunks")
secondary_connection = get_client(
secondary_host, secondary_port,
read_preference=ReadPreference.SECONDARY)
# Should detect it's connected to secondary and not attempt to
# create index
fs = gridfs.GridFS(secondary_connection.pymongo_test)
primary_connection.pymongo_test.drop_collection("fs.files")
primary_connection.pymongo_test.drop_collection("fs.chunks")
# This won't detect secondary, raises error
self.assertRaises(ConnectionFailure, fs.put, b'foo')
# Should detect it's connected to secondary and not attempt to
# create index
fs = gridfs.GridFS(secondary_connection.pymongo_test)
# This won't detect secondary, raises error
self.assertRaises(ConnectionFailure, fs.put, b'foo')
def test_gridfs_secondary_lazy(self):
# Should detect it's connected to secondary and not attempt to
# create index.
secondary_host, secondary_port = self.secondaries[0]
secondary_pair = '%s:%d' % (secondary_host, secondary_port)
client = MongoClient(
secondary_host, secondary_port,
connection_string(seeds=[secondary_pair]),
read_preference=ReadPreference.SECONDARY,
_connect=False)

View File

@ -29,19 +29,20 @@ def setUpModule():
pass
class FindOne(threading.Thread):
class SimpleOp(threading.Thread):
def __init__(self, client):
super(FindOne, self).__init__()
super(SimpleOp, self).__init__()
self.client = client
self.passed = False
def run(self):
self.client.db.collection.find_one()
self.client.db.command('ismaster')
self.passed = True # No exception raised.
def do_find_one(client, nthreads):
threads = [FindOne(client) for _ in range(nthreads)]
def do_simple_op(client, nthreads):
threads = [SimpleOp(client) for _ in range(nthreads)]
for t in threads:
t.start()
@ -67,7 +68,7 @@ class TestMongosHA(unittest.TestCase):
self.assertEqual(0, len(client.nodes))
# Trigger initial connection.
do_find_one(client, nthreads)
do_simple_op(client, nthreads)
self.assertEqual(3, len(client.nodes))
def test_reconnect(self):
@ -77,7 +78,7 @@ class TestMongosHA(unittest.TestCase):
# Trigger reconnect.
client.disconnect()
do_find_one(client, nthreads)
do_simple_op(client, nthreads)
self.assertEqual(3, len(client.nodes))
def test_failover(self):
@ -102,12 +103,12 @@ class TestMongosHA(unittest.TestCase):
def f():
try:
client.db.collection.find_one()
client.db.command('ismaster')
except AutoReconnect:
errors.append(True)
# Second attempt succeeds.
client.db.collection.find_one()
client.db.command('ismaster')
passed.append(True)

View File

@ -345,7 +345,7 @@ class _TestPoolingBase(object):
def get_client(self, *args, **kwargs):
opts = kwargs.copy()
opts['use_greenlets'] = self.use_greenlets
return get_client(*args, **opts)
return get_client(host, port, *args, **opts)
def get_pool(self, pair, *args, **kwargs):
kwargs['use_greenlets'] = self.use_greenlets
@ -1156,6 +1156,7 @@ class _TestPoolSocketSharing(_TestPoolingBase):
gr0: get results
"""
cx = get_client(
host, port,
use_greenlets=self.use_greenlets,
auto_start_request=False
)
@ -1189,16 +1190,7 @@ class _TestPoolSocketSharing(_TestPoolingBase):
# Javascript function that pauses N seconds per document
fn = delay(10)
if (is_mongos(db.connection) or not
Version.from_client(db.connection).at_least(1, 7, 2)):
# mongos doesn't support eval so we have to use $where
# which is less reliable in this context.
self.assertEqual(1, db.test.find({"$where": fn}).count())
else:
# 'nolock' allows find_fast to start and finish while we're
# waiting for this to complete.
self.assertEqual({'ok': 1.0, 'retval': True},
db.command('eval', fn, nolock=True))
self.assertEqual(1, db.test.find({"$where": fn}).count())
history.append('find_slow done')

View File

@ -38,7 +38,9 @@ from test import (client_context,
SkipTest,
unittest,
utils,
IntegrationTest)
IntegrationTest,
db_user,
db_pwd)
from test.version import Version
@ -212,6 +214,8 @@ class TestCommandAndReadPreference(TestReplicaSetClientBase):
# Effectively ignore members' ping times so we can test the effect
# of ReadPreference modes only
latencyThresholdMS=1000*1000)
if client_context.auth_enabled:
self.c.admin.authenticate(db_user, db_pwd)
self.client_version = Version.from_client(self.c)
def tearDown(self):
@ -516,7 +520,7 @@ class TestMovingAverage(unittest.TestCase):
class TestMongosConnection(IntegrationTest):
def test_mongos_connection(self):
c = get_client()
c = get_client(host, port)
is_mongos = utils.is_mongos(c)
# Test default mode, PRIMARY
@ -547,7 +551,8 @@ class TestMongosConnection(IntegrationTest):
None, [{}]
):
# Create a client e.g. with read_preference=NEAREST
c = get_client(read_preference=mode(tag_sets=tag_sets))
c = get_client(host, port,
read_preference=mode(tag_sets=tag_sets))
self.assertEqual(is_mongos, c.is_mongos)
cursor = c.pymongo_test.test.find()
@ -586,7 +591,8 @@ class TestMongosConnection(IntegrationTest):
[{'dc': 'la'}, {'dc': 'sf'}],
[{'dc': 'la'}, {'dc': 'sf'}, {}],
):
c = get_client(read_preference=mode(tag_sets=tag_sets))
c = get_client(host, port,
read_preference=mode(tag_sets=tag_sets))
self.assertEqual(is_mongos, c.is_mongos)
cursor = c.pymongo_test.test.find()
@ -599,7 +605,7 @@ class TestMongosConnection(IntegrationTest):
'$readPreference' in cursor._Cursor__query_spec())
def test_only_secondary_ok_commands_have_read_prefs(self):
c = get_client(read_preference=ReadPreference.SECONDARY)
c = get_client(host, port, read_preference=ReadPreference.SECONDARY)
with warnings.catch_warnings():
warnings.simplefilter("ignore", UserWarning)

View File

@ -39,13 +39,18 @@ from pymongo.errors import (AutoReconnect,
ConnectionFailure,
InvalidName,
OperationFailure, InvalidOperation)
from test import client_context, pair, port, SkipTest, unittest
from test import (client_context,
connection_string,
pair,
port,
SkipTest,
unittest)
from test.pymongo_mocks import MockReplicaSetClient
from test.utils import (
delay, assertReadFrom, assertReadFromAll, read_from_which_host,
remove_all_users, assertRaisesExactly, TestRequestMixin, one,
server_started_with_auth, pools_from_rs_client, get_pool,
_TestLazyConnectMixin)
get_rs_client, _TestLazyConnectMixin)
from test.version import Version
@ -90,9 +95,8 @@ class TestReplicaSetClientBase(unittest.TestCase):
]
def _get_client(self, **kwargs):
return MongoReplicaSetClient(pair,
replicaSet=self.name,
**kwargs)
return get_rs_client(connection_string(),
replicaSet=self.name, **kwargs)
class TestReplicaSetClient(TestReplicaSetClientBase, TestRequestMixin):
@ -168,11 +172,9 @@ class TestReplicaSetClient(TestReplicaSetClientBase, TestRequestMixin):
@client_context.require_auth
def test_init_disconnected_with_auth(self):
c = client_context.rs_client
c.admin.add_user("admin", "pass")
c.admin.authenticate("admin", "pass")
try:
c.pymongo_test.add_user("user", "pass", roles=['readWrite', 'userAdmin'])
c.pymongo_test.add_user("user", "pass",
roles=['readWrite', 'userAdmin'])
# Auth with lazy connection.
host = one(self.hosts)
@ -193,9 +195,6 @@ class TestReplicaSetClient(TestReplicaSetClientBase, TestRequestMixin):
finally:
# Clean up.
remove_all_users(c.pymongo_test)
remove_all_users(c.admin)
c.admin.logout()
c.disconnect()
def test_connect(self):
assertRaisesExactly(ConnectionFailure, MongoReplicaSetClient,
@ -418,7 +417,8 @@ class TestReplicaSetClient(TestReplicaSetClientBase, TestRequestMixin):
self.assertEqual("bar", c.pymongo_test1.test.find_one()["foo"])
self.assertFalse(c.in_request())
c.copy_database("pymongo_test", "pymongo_test2", pair)
c.copy_database("pymongo_test", "pymongo_test2")
# copy_database() didn't accidentally restart the request
self.assertFalse(c.in_request())
@ -431,8 +431,6 @@ class TestReplicaSetClient(TestReplicaSetClientBase, TestRequestMixin):
server_started_with_auth(c)):
c.drop_database("pymongo_test1")
c.admin.add_user("admin", "password")
c.admin.authenticate("admin", "password")
try:
c.pymongo_test.add_user("mike", "password")
@ -455,10 +453,6 @@ class TestReplicaSetClient(TestReplicaSetClientBase, TestRequestMixin):
finally:
# Cleanup
remove_all_users(c.pymongo_test)
c.admin.remove_user("admin")
c.admin.logout()
c.pymongo_test.logout()
c.disconnect()
def test_get_default_database(self):
host = one(self.hosts)
@ -1090,7 +1084,7 @@ class TestReplicaSetWireVersion(unittest.TestCase):
c.set_wire_version_range('a:1', 1, 5)
c.set_wire_version_range('b:2', 0, 1)
c.set_wire_version_range('c:3', 1, 2)
c.db.collection.find_one() # Connect.
c.db.command('ismaster') # Connect.
self.assertEqual(c.min_wire_version, 1)
self.assertEqual(c.max_wire_version, 5)
@ -1113,9 +1107,13 @@ class TestReplicaSetClientLazyConnect(
TestReplicaSetClientBase,
_TestLazyConnectMixin):
@classmethod
def setUpClass(cls):
TestReplicaSetClientBase.setUpClass()
def test_read_mode_secondary(self):
client = MongoReplicaSetClient(
pair, replicaSet=self.name, _connect=False,
connection_string(), replicaSet=self.name, _connect=False,
read_preference=ReadPreference.SECONDARY)
# No error.
@ -1128,18 +1126,27 @@ class TestReplicaSetClientLazyConnectGevent(
_TestLazyConnectMixin):
use_greenlets = True
@classmethod
def setUpClass(cls):
TestReplicaSetClientBase.setUpClass()
class TestReplicaSetClientLazyConnectBadSeeds(
TestReplicaSetClientBase,
_TestLazyConnectMixin):
@classmethod
def setUpClass(cls):
TestReplicaSetClientBase.setUpClass()
def _get_client(self, **kwargs):
kwargs.setdefault('connectTimeoutMS', 500)
# Assume there are no open mongods listening on a.com, b.com, ....
bad_seeds = ['%s.com' % chr(ord('a') + i) for i in range(5)]
seeds = ','.join(bad_seeds + [pair])
client = MongoReplicaSetClient(seeds, replicaSet=self.name, **kwargs)
client = MongoReplicaSetClient(
connection_string(seeds=(bad_seeds + [pair])),
replicaSet=self.name, **kwargs)
# In case of a slow test machine.
client._refresh_timeout_sec = 30
@ -1180,7 +1187,7 @@ class TestReplicaSetClientMaxWriteBatchSize(unittest.TestCase):
# Starts with default max batch size.
self.assertEqual(1000, c.max_write_batch_size)
c.db.collection.find_one() # Connect.
c.db.command('ismaster') # Connect.
# Uses primary's max batch size.
self.assertEqual(c.max_write_batch_size, 1)

View File

@ -57,7 +57,7 @@ class TestSecondaryBecomesStandalone(unittest.TestCase):
c.disconnect()
try:
c.db.collection.find_one()
c.db.command('ismaster')
except ConfigurationError as e:
self.assertTrue('not a member of replica set' in str(e))
else:
@ -147,7 +147,7 @@ class TestSecondaryAdded(unittest.TestCase):
c.mock_ismaster_hosts.append('c:3')
c.disconnect()
c.db.collection.find_one()
c.db.command('ismaster')
self.assertEqual('a', c.host)
self.assertEqual(1, c.port)

View File

@ -17,9 +17,8 @@
import threading
import traceback
from test import SkipTest, unittest, client_context
from test.utils import (joinall, remove_all_users,
server_started_with_auth, RendezvousThread)
from test import unittest, client_context, pair
from test.utils import joinall, remove_all_users, RendezvousThread
from test.test_client import get_client
from test.utils import get_pool
from pymongo.pool import SocketInfo, _closed
@ -185,7 +184,7 @@ class BaseTestThreads(object):
test_threads_replica_set_connection.py.
"""
# Regular test client
return get_client()
return get_client(pair)
def test_threading(self):
self.db.drop_collection("test")
@ -253,7 +252,7 @@ class BaseTestThreads(object):
#
# If we've fixed PYTHON-345, then only one AutoReconnect is raised,
# and all the threads get new request sockets.
cx = get_client(auto_start_request=True)
cx = get_client(pair, auto_start_request=True)
collection = cx.db.pymongo_test
# acquire a request socket for the main thread
@ -310,6 +309,11 @@ class BaseTestThreadsAuth(object):
unittest imports this module, and once when unittest imports
test_threads_replica_set_connection.py, which imports this module.)
"""
@classmethod
@client_context.require_auth
def setUpClass(cls):
pass
def _get_client(self):
"""
Intended for overriding in TestThreadsAuthReplicaSet. This method
@ -317,18 +321,19 @@ class BaseTestThreadsAuth(object):
test_threads_replica_set_connection.py.
"""
# Regular test client
return get_client()
return get_client(pair)
def setUp(self):
client = self._get_client()
if not server_started_with_auth(client):
raise SkipTest("Authentication is not enabled on server")
self.client = client
self.client.admin.add_user('admin-user', 'password',
roles=['clusterAdmin',
'dbAdminAnyDatabase',
'readWriteAnyDatabase',
'userAdminAnyDatabase'])
# client returned from self._get_client() may already be authenticated
# to get around restricted localhost exception in MongoDB >= 2.7.1.
self.client.admin.logout()
self.client.admin.authenticate("admin-user", "password")
self.client.auth_test.add_user("test-user", "password",
roles=['readWrite'])
@ -338,17 +343,20 @@ class BaseTestThreadsAuth(object):
self.client.admin.authenticate("admin-user", "password")
remove_all_users(self.client.auth_test)
self.client.drop_database('auth_test')
remove_all_users(self.client.admin)
self.client.admin.remove_user('admin-user')
self.client.admin.logout()
# Clear client reference so that RSC's monitor thread
# dies.
self.client = None
def test_auto_auth_login(self):
client = self._get_client()
client.admin.logout()
self.assertRaises(OperationFailure, client.auth_test.test.find_one)
# Admin auth
client = self._get_client()
client.admin.logout()
client.admin.authenticate("admin-user", "password")
nthreads = 10
@ -365,6 +373,7 @@ class BaseTestThreadsAuth(object):
# Database-specific auth
client = self._get_client()
client.admin.logout()
client.auth_test.authenticate("test-user", "password")
threads = []

View File

@ -14,11 +14,10 @@
"""Test that pymongo is thread safe."""
from pymongo.mongo_replica_set_client import MongoReplicaSetClient
from test import unittest
from test.test_threads import BaseTestThreads, BaseTestThreadsAuth
from test.test_replica_set_client import TestReplicaSetClientBase, pair
from test.utils import get_rs_client
class TestThreadsReplicaSet(TestReplicaSetClientBase, BaseTestThreads):
@ -40,6 +39,15 @@ class TestThreadsReplicaSet(TestReplicaSetClientBase, BaseTestThreads):
class TestThreadsAuthReplicaSet(TestReplicaSetClientBase, BaseTestThreadsAuth):
@classmethod
def setUpClass(cls):
TestReplicaSetClientBase.setUpClass()
BaseTestThreadsAuth.setUpClass()
@classmethod
def tearDownClass(cls):
TestReplicaSetClientBase.tearDownClass()
def setUp(self):
"""
Prepare to test all the same things that TestThreads tests, but do it
@ -57,7 +65,7 @@ class TestThreadsAuthReplicaSet(TestReplicaSetClientBase, BaseTestThreadsAuth):
Override TestThreadsAuth, so its tests run on a MongoReplicaSetClient
instead of a regular MongoClient.
"""
return MongoReplicaSetClient(pair, replicaSet=self.name)
return get_rs_client(pair, replicaSet=self.name)
if __name__ == "__main__":

View File

@ -23,7 +23,10 @@ import threading
from pymongo import MongoClient, MongoReplicaSetClient
from pymongo.errors import AutoReconnect
from pymongo.pool import NO_REQUEST, NO_SOCKET_YET, SocketInfo
from test import host, port, SkipTest
from test import (SkipTest,
client_context,
db_user,
db_pwd)
from test.version import Version
@ -34,6 +37,20 @@ except ImportError:
has_gevent = False
def get_client(*args, **kwargs):
client = MongoClient(*args, **kwargs)
if client_context.auth_enabled and kwargs.get("_connect", True):
client.admin.authenticate(db_user, db_pwd)
return client
def get_rs_client(*args, **kwargs):
client = MongoReplicaSetClient(*args, **kwargs)
if client_context.auth_enabled and kwargs.get("_connect", True):
client.admin.authenticate(db_user, db_pwd)
return client
# No functools in Python 2.4
def my_partial(f, *args, **kwargs):
def _f(*new_args, **new_kwargs):
@ -126,9 +143,10 @@ def drop_collections(db):
def remove_all_users(db):
if Version.from_client(db.connection).at_least(2, 5, 3, -1):
db.command({"dropAllUsersFromDatabase": 1})
db.command({"dropAllUsersFromDatabase": 1,
"writeConcern": {"w": "majority"}})
else:
db.system.users.remove({})
db.system.users.remove({}, w="majority")
def joinall(threads):
@ -147,8 +165,10 @@ def enable_text_search(client):
if isinstance(client, MongoReplicaSetClient):
for host, port in client.secondaries:
MongoClient(host, port).admin.command(
'setParameter', textSearchEnabled=True)
client = MongoClient(host, port)
if client_context.auth_enabled:
client.admin.authenticate(db_user, db_pwd)
client.admin.command('setParameter', textSearchEnabled=True)
def assertRaisesExactly(cls, fn, *args, **kwargs):
"""
@ -448,7 +468,7 @@ def lazy_client_trial(reset, target, test, get_client, use_greenlets):
if use_greenlets and not has_gevent:
raise SkipTest('Gevent not installed')
collection = MongoClient(host, port).pymongo_test.test
collection = client_context.client.pymongo_test.test
# Make concurrency bugs more likely to manifest.
interval = None
@ -463,8 +483,8 @@ def lazy_client_trial(reset, target, test, get_client, use_greenlets):
try:
for i in range(NTRIALS):
reset(collection)
lazy_client = get_client(
_connect=False, use_greenlets=use_greenlets)
lazy_client = get_client(_connect=False,
use_greenlets=use_greenlets)
lazy_collection = lazy_client.pymongo_test.test
run_threads(lazy_collection, target, use_greenlets)