Fixing write concern logic on a collection - PYTHON-474

Adding warnings in documentation about a change
in side effects when calling write_concern
This commit is contained in:
Ross Lawley 2013-03-21 09:42:50 +00:00
parent ce0345d514
commit bc6368dafa
2 changed files with 58 additions and 1 deletions

View File

@ -388,6 +388,14 @@ class BaseObject(object):
.. note:: Accessing :attr:`write_concern` returns its value
(a subclass of :class:`dict`), not a copy.
.. warning:: If you are using :class:`~pymongo.connection.Connection`
or :class:`~pymongo.replica_set_connection.ReplicaSetConnection`
make sure you explicitly set ``w`` to 1 (or a greater value) or
:attr:`safe` to ``True``. Unlike calling
:meth:`set_lasterror_options`, setting an option in
:attr:`write_concern` does not implicitly set :attr:`safe`
to ``True``.
"""
# To support dict style access we have to return the actual
# WriteConcern here, not a copy.
@ -603,7 +611,9 @@ class BaseObject(object):
# Fall back to collection level defaults.
# w=0 takes precedence over self.safe = True
if self.safe and self.__write_concern.get('w') != 0:
if self.__write_concern.get('w') == 0:
return False, {}
elif self.safe or self.__write_concern.get('w', 0) != 0:
return True, pop1(self.__write_concern.copy())
return False, {}

View File

@ -25,6 +25,7 @@ from nose.plugins.skip import SkipTest
from bson.objectid import ObjectId
from bson.son import SON
from pymongo.connection import Connection
from pymongo.mongo_client import MongoClient
from pymongo.mongo_replica_set_client import MongoReplicaSetClient
from pymongo.errors import ConfigurationError, OperationFailure
@ -56,6 +57,39 @@ class TestCommon(unittest.TestCase):
warnings.simplefilter("ignore")
# Connection tests
c = Connection(pair)
self.assertFalse(c.slave_okay)
self.assertFalse(c.safe)
self.assertEqual({}, c.get_lasterror_options())
db = c.pymongo_test
db.drop_collection("test")
self.assertFalse(db.slave_okay)
self.assertFalse(db.safe)
self.assertEqual({}, db.get_lasterror_options())
coll = db.test
self.assertFalse(coll.slave_okay)
self.assertFalse(coll.safe)
self.assertEqual({}, coll.get_lasterror_options())
self.assertEqual((False, {}), coll._get_write_mode())
coll.safe = False
coll.write_concern.update(w=1)
self.assertEqual((True, {}), coll._get_write_mode())
coll.write_concern.update(w=3)
self.assertEqual((True, {'w': 3}), coll._get_write_mode())
coll.safe = True
coll.write_concern.update(w=0)
self.assertEqual((False, {}), coll._get_write_mode())
coll = db.test
cursor = coll.find()
self.assertFalse(cursor._Cursor__slave_okay)
cursor = coll.find(slave_okay=True)
self.assertTrue(cursor._Cursor__slave_okay)
# MongoClient test
c = MongoClient(pair)
self.assertFalse(c.slave_okay)
self.assertTrue(c.safe)
@ -69,6 +103,19 @@ class TestCommon(unittest.TestCase):
self.assertFalse(coll.slave_okay)
self.assertTrue(coll.safe)
self.assertEqual({}, coll.get_lasterror_options())
self.assertEqual((True, {}), coll._get_write_mode())
coll.safe = False
coll.write_concern.update(w=1)
self.assertEqual((True, {}), coll._get_write_mode())
coll.write_concern.update(w=3)
self.assertEqual((True, {'w': 3}), coll._get_write_mode())
coll.safe = True
coll.write_concern.update(w=0)
self.assertEqual((False, {}), coll._get_write_mode())
coll = db.test
cursor = coll.find()
self.assertFalse(cursor._Cursor__slave_okay)
cursor = coll.find(slave_okay=True)