Skip to content

Commit eddaf51

Browse files
committed
feat: handle geohaystack removal
1 parent edbf721 commit eddaf51

File tree

4 files changed

+39
-26
lines changed

4 files changed

+39
-26
lines changed

mongoengine/base/document.py

Lines changed: 13 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -28,6 +28,11 @@
2828

2929
NON_FIELD_ERRORS = "__all__"
3030

31+
try:
32+
GEOHAYSTACK = pymongo.GEOHAYSTACK
33+
except AttributeError:
34+
GEOHAYSTACK = None
35+
3136

3237
class BaseDocument:
3338
# TODO simplify how `_changed_fields` is used.
@@ -898,7 +903,10 @@ def _build_index_spec(cls, spec):
898903
elif key.startswith("("):
899904
direction = pymongo.GEOSPHERE
900905
elif key.startswith(")"):
901-
direction = pymongo.GEOHAYSTACK
906+
try:
907+
direction = pymongo.GEOHAYSTACK
908+
except AttributeError:
909+
raise NotImplementedError
902910
elif key.startswith("*"):
903911
direction = pymongo.GEO2D
904912
if key.startswith(("+", "-", "*", "$", "#", "(", ")")):
@@ -923,10 +931,10 @@ def _build_index_spec(cls, spec):
923931
index_list.append((key, direction))
924932

925933
# Don't add cls to a geo index
926-
if include_cls and direction not in (
927-
pymongo.GEO2D,
928-
pymongo.GEOHAYSTACK,
929-
pymongo.GEOSPHERE,
934+
if (
935+
include_cls
936+
and direction not in (pymongo.GEO2D, pymongo.GEOSPHERE)
937+
and (GEOHAYSTACK is None or direction != GEOHAYSTACK)
930938
):
931939
index_list.insert(0, ("_cls", 1))
932940

mongoengine/pymongo_support.py

Lines changed: 2 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -4,12 +4,8 @@
44
import pymongo
55
from pymongo.errors import OperationFailure
66

7-
_PYMONGO_37 = (3, 7)
8-
97
PYMONGO_VERSION = tuple(pymongo.version_tuple[:2])
108

11-
IS_PYMONGO_GTE_37 = PYMONGO_VERSION >= _PYMONGO_37
12-
139

1410
def count_documents(
1511
collection, filter, skip=None, limit=None, hint=None, collation=None
@@ -29,7 +25,7 @@ def count_documents(
2925
kwargs["collation"] = collation
3026

3127
# count_documents appeared in pymongo 3.7
32-
if IS_PYMONGO_GTE_37:
28+
if PYMONGO_VERSION >= (3, 7):
3329
try:
3430
return collection.count_documents(filter=filter, **kwargs)
3531
except OperationFailure:
@@ -49,7 +45,7 @@ def count_documents(
4945

5046
def list_collection_names(db, include_system_collections=False):
5147
"""Pymongo>3.7 deprecates collection_names in favour of list_collection_names"""
52-
if IS_PYMONGO_GTE_37:
48+
if PYMONGO_VERSION >= (3, 7):
5349
collections = db.list_collection_names()
5450
else:
5551
collections = db.collection_names()

tests/document/test_indexes.py

Lines changed: 23 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -11,6 +11,7 @@
1111
MONGODB_42,
1212
get_mongodb_version,
1313
)
14+
from mongoengine.pymongo_support import PYMONGO_VERSION
1415

1516

1617
class TestIndexes(unittest.TestCase):
@@ -247,11 +248,9 @@ class Place(Document):
247248

248249
def test_explicit_geohaystack_index(self):
249250
"""Ensure that geohaystack indexes work when created via meta[indexes]"""
250-
pytest.skip(
251-
"GeoHaystack index creation is not supported for now"
252-
"from meta, as it requires a bucketSize parameter."
253-
)
254-
251+
# This test can be removed when pymongo 3.x is no longer supported
252+
if PYMONGO_VERSION >= (4,):
253+
pytest.skip('GEOHAYSTACK has been removed in pymongo 4.0')
255254
class Place(Document):
256255
location = DictField()
257256
name = StringField()
@@ -261,22 +260,32 @@ class Place(Document):
261260
{"fields": [("location.point", "geoHaystack"), ("name", 1)]}
262261
] == Place._meta["index_specs"]
263262

264-
Place.ensure_indexes()
265-
info = Place._get_collection().index_information()
266-
info = [value["key"] for key, value in info.items()]
267-
assert [("location.point", "geoHaystack")] in info
263+
# GeoHaystack index creation is not supported for now from meta, as it
264+
# requires a bucketSize parameter.
265+
if False:
266+
Place.ensure_indexes()
267+
info = Place._get_collection().index_information()
268+
info = [value["key"] for key, value in info.items()]
269+
assert [("location.point", "geoHaystack")] in info
268270

269271
def test_create_geohaystack_index(self):
270272
"""Ensure that geohaystack indexes can be created"""
271-
272273
class Place(Document):
273274
location = DictField()
274275
name = StringField()
275276

276-
Place.create_index({"fields": (")location.point", "name")}, bucketSize=10)
277-
info = Place._get_collection().index_information()
278-
info = [value["key"] for key, value in info.items()]
279-
assert [("location.point", "geoHaystack"), ("name", 1)] in info
277+
# This test can be removed when pymongo 3.x is no longer supported
278+
if PYMONGO_VERSION >= (4,):
279+
with pytest.raises(NotImplementedError):
280+
Place.create_index(
281+
{"fields": (")location.point", "name")},
282+
bucketSize=10,
283+
)
284+
else:
285+
Place.create_index({"fields": (")location.point", "name")}, bucketSize=10)
286+
info = Place._get_collection().index_information()
287+
info = [value["key"] for key, value in info.items()]
288+
assert [("location.point", "geoHaystack"), ("name", 1)] in info
280289

281290
def test_dictionary_indexes(self):
282291
"""Ensure that indexes are used when meta[indexes] contains

tox.ini

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
[tox]
2-
envlist = pypy3-{mg34,mg36,mg39,mg311,mg312}
2+
envlist = pypy3-{mg34,mg36,mg39,mg311,mg312,mg4}
33

44
[testenv]
55
commands =

0 commit comments

Comments
 (0)