PYTHON-808 Prevent use of Database and Collection in boolean expressions (#728)

This commit is contained in:
Julius Park 2021-09-16 15:52:14 -07:00 committed by GitHub
parent fbd5599deb
commit 88e744d506
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
6 changed files with 50 additions and 1 deletions

View File

@ -134,8 +134,13 @@ decodes datetime as naive by default.
- The ``hint`` option is now required when using ``min`` or ``max`` queries
with :meth:`~pymongo.collection.Collection.find`.
- ``name`` is now a required argument for the :class:`pymongo.driver_info.DriverInfo` class.
- :class:`~pymongo.collection.Collection` and :class:`~pymongo.database.Database`
now raises an error upon evaluating as a Boolean, please use the
syntax ``if collection is not None:`` or ``if database is not None:`` as
opposed to
the previous syntax which was simply ``if collection:`` or ``if database:``.
You must now explicitly compare with None.
d
Notable improvements
....................

View File

@ -321,6 +321,19 @@ Can be changed to this::
.. _'system.profile' collection: https://docs.mongodb.com/manual/reference/database-profiler/
Database.__bool__ raises NotImplementedError
............................................
:class:`~pymongo.database.Database` now raises an error upon evaluating as a
Boolean. Code like this::
if database:
Can be changed to this::
if database is not None:
You must now explicitly compare with None.
Collection
----------
@ -621,6 +634,19 @@ can be changed to this::
cursor = coll.find({}, min={'x', min_value}, hint=[('x', ASCENDING)])
Collection.__bool__ raises NotImplementedError
..............................................
:class:`~pymongo.collection.Collection` now raises an error upon evaluating
as a Boolean. Code like this::
if collection:
Can be changed to this::
if collection is not None:
You must now explicitly compare with None.
SONManipulator is removed
-------------------------

View File

@ -289,6 +289,11 @@ class Collection(common.BaseObject):
def __hash__(self):
return hash((self.__database, self.__name))
def __bool__(self):
raise NotImplementedError("Collection objects do not implement truth "
"value testing or bool(). Please compare "
"with None instead: collection is not None")
@property
def full_name(self):
"""The full name of this :class:`Collection`.

View File

@ -840,6 +840,11 @@ class Database(common.BaseObject):
next = __next__
def __bool__(self):
raise NotImplementedError("Database objects do not implement truth "
"value testing or bool(). Please compare "
"with None instead: database is not None")
def dereference(self, dbref, session=None, **kwargs):
"""Dereference a :class:`~bson.dbref.DBRef`, getting the
document it points to.

View File

@ -2265,6 +2265,10 @@ class TestCollection(IntegrationTest):
('$dumb', 2),
('filter', {'foo': 1})]).to_dict())
def test_bool(self):
with self.assertRaises(NotImplementedError):
bool(Collection(self.db, 'test'))
if __name__ == "__main__":
unittest.main()

View File

@ -687,6 +687,10 @@ class TestDatabaseAggregation(IntegrationTest):
with self.admin.aggregate(self.pipeline) as _:
pass
def test_bool(self):
with self.assertRaises(NotImplementedError):
bool(Database(self.client, "test"))
if __name__ == "__main__":
unittest.main()