Skip to content

Commit ad64f8f

Browse files
loryrutagreenrobot
authored andcommitted
test: close store after tests (add test_store fixture) #59
1 parent 661bfbe commit ad64f8f

File tree

11 files changed

+96
-130
lines changed

11 files changed

+96
-130
lines changed

tests/conftest.py

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -12,3 +12,10 @@ def cleanup_db():
1212
# Not needed: every test clears the DB on start, without deleting it on exit (not necessary)
1313
# Also, here we have no information regarding the DB path being used (although usually is "testdata")
1414
pass
15+
16+
17+
@pytest.fixture
18+
def test_store():
19+
store = create_test_store()
20+
yield store
21+
store.close()

tests/test_basics.py

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -30,4 +30,5 @@ def test_version():
3030

3131

3232
def test_open():
33-
create_test_store()
33+
store = create_test_store()
34+
store.close()

tests/test_box.py

Lines changed: 12 additions & 27 deletions
Original file line numberDiff line numberDiff line change
@@ -8,9 +8,8 @@
88
from math import floor
99

1010

11-
def test_box_basics():
12-
store = create_test_store()
13-
box = store.box(TestEntity)
11+
def test_box_basics(test_store):
12+
box = test_store.box(TestEntity)
1413

1514
assert box.is_empty()
1615
assert box.count() == 0
@@ -94,12 +93,9 @@ def test_box_basics():
9493
assert box.get(object.id) is None
9594
assert box.get(1) is None
9695

97-
store.close()
9896

99-
100-
def test_box_bulk():
101-
store = create_test_store()
102-
box = store.box(TestEntity)
97+
def test_box_bulk(test_store):
98+
box = test_store.box(TestEntity)
10399

104100
box.put(TestEntity(str="first"))
105101

@@ -130,12 +126,9 @@ def test_box_bulk():
130126
assert removed == 4
131127
assert box.count() == 0
132128

133-
store.close()
134-
135129

136-
def test_datetime():
137-
store = create_test_store()
138-
box = store.box(TestEntityDatetime)
130+
def test_datetime(test_store):
131+
box = test_store.box(TestEntityDatetime)
139132

140133
assert box.is_empty()
141134
assert box.count() == 0
@@ -185,12 +178,9 @@ def test_datetime():
185178
assert box.get(object.id) is None
186179
assert box.get(1) is None
187180

188-
store.close()
189-
190181

191-
def test_datetime_special_values():
192-
store = create_test_store()
193-
box = store.box(TestEntityDatetime)
182+
def test_datetime_special_values(test_store):
183+
box = test_store.box(TestEntityDatetime)
194184
assert box.is_empty()
195185

196186
object = TestEntityDatetime()
@@ -216,16 +206,15 @@ def test_datetime_special_values():
216206
assert read.date_nano == datetime.fromtimestamp(1.0, timezone.utc)
217207

218208

219-
def test_flex():
209+
def test_flex(test_store):
220210
def test_put_get(object: TestEntity, box: objectbox.Box, property):
221211
object.flex = property
222212
id = box.put(object)
223213
assert id == object.id
224214
read = box.get(object.id)
225215
assert read.flex == object.flex
226216

227-
store = create_test_store()
228-
box = store.box(TestEntity)
217+
box = test_store.box(TestEntity)
229218
object = TestEntity()
230219

231220
# Put an empty object
@@ -262,13 +251,9 @@ def test_put_get(object: TestEntity, box: objectbox.Box, property):
262251
# Update to list inside dict
263252
test_put_get(object, box, {"a": 1, "b": [1, 2, 3]})
264253

265-
store.close()
266-
267-
268-
def test_flex_values():
269-
store = create_test_store()
270254

271-
box = store.box(TestEntityFlex)
255+
def test_flex_values(test_store):
256+
box = test_store.box(TestEntityFlex)
272257

273258
# Test empty object
274259
obj_id = box.put(TestEntityFlex())

tests/test_deprecated.py

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -20,6 +20,7 @@ def test_deprecated_ObjectBox():
2020
ob = ObjectBox(c_store)
2121
box = objectbox.Box(ob, TestEntity)
2222
assert box.count() == 0
23+
ob.close() # TODO The store shall be closed even if the test fails
2324

2425

2526
def test_deprecated_Builder():
@@ -29,3 +30,4 @@ def test_deprecated_Builder():
2930
model = tests.common.create_default_model()
3031
with pytest.deprecated_call():
3132
ob = objectbox.Builder().model(model).directory("testdata").build()
33+
ob.close()

tests/test_hnsw.py

Lines changed: 8 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -34,10 +34,10 @@ def _test_random_points(
3434

3535
points = np.random.rand(num_points, 2).astype(np.float32)
3636

37-
store = create_test_store()
37+
test_store = create_test_store()
3838

3939
# Init and seed DB
40-
box = store.box(VectorEntity)
40+
box = test_store.box(VectorEntity)
4141

4242
print(f"Seeding DB with {num_points} points...")
4343
objects = []
@@ -77,6 +77,8 @@ def _test_random_points(
7777

7878
print(f"Done!")
7979

80+
test_store.close()
81+
8082

8183
def test_random_points():
8284

@@ -89,14 +91,8 @@ def test_random_points():
8991
_test_random_points(num_points=100, num_query_points=10, seed=14, distance_type=distance_type, min_score=min_score)
9092
_test_random_points(num_points=100, num_query_points=10, seed=15, distance_type=distance_type, min_score=min_score)
9193

92-
# TODO: Cosine and Dot Product may result in 0 score
93-
94-
95-
def _test_combined_nn_search(distance_type: VectorDistanceType = VectorDistanceType.EUCLIDEAN):
96-
97-
store = create_test_store()
98-
99-
box = store.box(VectorEntity)
94+
def _test_combined_nn_search(test_store: Store, distance_type: VectorDistanceType = VectorDistanceType.EUCLIDEAN):
95+
box = test_store.box(VectorEntity)
10096

10197
vector_field_name = "vector_"+distance_type.name.lower()
10298

@@ -203,8 +199,8 @@ def _test_combined_nn_search(distance_type: VectorDistanceType = VectorDistanceT
203199
assert len(numpy_result) == 0
204200

205201

206-
def test_combined_nn_search():
202+
def test_combined_nn_search(test_store):
207203
""" Tests NN search combined with regular query conditions, offset and limit. """
208204
distance_type = VectorDistanceType.EUCLIDEAN
209-
_test_combined_nn_search(distance_type)
205+
_test_combined_nn_search(test_store, distance_type)
210206
# TODO: Cosine, DotProduct diverges see below

tests/test_idsync.py

Lines changed: 31 additions & 36 deletions
Original file line numberDiff line numberDiff line change
@@ -21,21 +21,29 @@ def __init__(self):
2121
self.model_path = 'test.json'
2222
if path.exists(self.model_path):
2323
os.remove(self.model_path)
24-
self.model = None
24+
self._model = None
2525
self.db_path = 'testdb'
2626
Store.remove_db_files(self.db_path)
27+
self._store = None # Last created store
2728

2829
def sync(self, model: Model) -> bool:
2930
""" Returns True if changes were made and the model JSON was written. """
30-
self.model = model
31-
return sync_model(self.model, self.model_path)
31+
self._model = model
32+
return sync_model(self._model, self.model_path)
3233

3334
def json(self):
3435
return json.load(open(self.model_path))
3536

36-
def store(self):
37-
assert self.model is not None
38-
return Store(model=self.model, directory=self.db_path)
37+
def create_store(self):
38+
assert self._model is not None, "Model must be set before creating store"
39+
if self._store is not None:
40+
self._store.close()
41+
self._store = Store(model=self._model, directory=self.db_path)
42+
return self._store
43+
44+
def close(self):
45+
if self._store is not None:
46+
self._store.close()
3947

4048

4149
def reset_ids(entity: _Entity):
@@ -48,7 +56,9 @@ def reset_ids(entity: _Entity):
4856

4957
@pytest.fixture
5058
def env():
51-
return _TestEnv()
59+
env_ = _TestEnv()
60+
yield env_
61+
env_.close()
5262

5363

5464
def test_empty_model(env):
@@ -136,13 +146,11 @@ class MyEntity:
136146
entity_ids = str(MyEntity._iduid)
137147

138148
# create new database and populate with two objects
139-
store = env.store()
149+
store = env.create_store()
140150
entityBox = store.box(MyEntity)
141151
entityBox.put(MyEntity(name="foo"),MyEntity(name="bar"))
142152
assert entityBox.count() == 2
143153
del entityBox
144-
store.close()
145-
del store
146154

147155
# recreate model using existing model json and open existing database
148156
model = Model()
@@ -156,7 +164,7 @@ class MyEntity:
156164
assert str(model.entities[0]._iduid) == entity_ids
157165

158166
# open existing database
159-
store = env.store()
167+
store = env.create_store()
160168
entityBox = store.box(MyEntity)
161169
assert entityBox.count() == 2
162170

@@ -169,12 +177,10 @@ class MyEntity1:
169177
model.entity(MyEntity1)
170178
env.sync(model)
171179
e0_iduid = IdUid(MyEntity1._id, MyEntity1._uid)
172-
store = env.store()
180+
store = env.create_store()
173181
box = store.box(MyEntity1)
174182
box.put( MyEntity1(name="foo"), MyEntity1(name="bar"))
175183
assert box.count() == 2
176-
store.close()
177-
del store
178184

179185
@Entity()
180186
class MyEntity2:
@@ -188,7 +194,7 @@ class MyEntity2:
188194
assert str(model.entities[0]._iduid) == "0:0"
189195
env.sync(model)
190196
assert model.entities[0]._iduid == e0_iduid
191-
store = env.store()
197+
store = env.create_store()
192198
box1 = store.box(MyEntity1)
193199
assert box1.count() == 2
194200
box2 = store.box(MyEntity2)
@@ -209,24 +215,21 @@ class MyEntity2:
209215
model.entity(MyEntity1)
210216
model.entity(MyEntity2)
211217
env.sync(model)
212-
store = env.store()
218+
store = env.create_store()
213219
box1 = store.box(MyEntity1)
214220
box1.put( MyEntity1(name="foo"), MyEntity1(name="bar"))
215221
box2 = store.box(MyEntity2)
216222
box2.put( MyEntity2(name="foo"), MyEntity2(name="bar"))
217223
assert box1.count() == 2
218224
assert box2.count() == 2
219225

220-
store.close()
221-
del store
222-
223226
# Re-create a model without MyEntity2
224227

225228
model = Model()
226229
reset_ids(MyEntity1)
227230
model.entity(MyEntity1)
228231
env.sync(model)
229-
store = env.store()
232+
store = env.create_store()
230233
box1 = store.box(MyEntity1)
231234
assert box1.count() == 2
232235

@@ -248,13 +251,11 @@ class MyEntity:
248251
assert uid != 0
249252
# Debug: print("UID: "+ str(uid))
250253

251-
store = env.store()
254+
store = env.create_store()
252255
box = store.box(MyEntity)
253256
box.put(MyEntity(name="foo"),MyEntity(name="bar"))
254257
assert box.count() == 2
255258
del box
256-
store.close()
257-
del store
258259

259260
@Entity(uid=uid)
260261
class MyRenamedEntity:
@@ -264,7 +265,7 @@ class MyRenamedEntity:
264265
model = Model()
265266
model.entity(MyRenamedEntity)
266267
env.sync(model)
267-
store = env.store()
268+
store = env.create_store()
268269
box = store.box(MyRenamedEntity)
269270
assert box.count() == 2
270271

@@ -316,12 +317,10 @@ class MyEntity:
316317
model = Model()
317318
model.entity(MyEntity)
318319
env.sync(model)
319-
store = env.store()
320+
store = env.create_store()
320321
box = store.box(MyEntity)
321322
box.put( MyEntity(name="foo"), MyEntity(name="bar"))
322323
del box
323-
store.close()
324-
del store
325324

326325
@Entity()
327326
class MyEntity:
@@ -332,7 +331,7 @@ class MyEntity:
332331
model = Model()
333332
model.entity(MyEntity)
334333
env.sync(model)
335-
store = env.store()
334+
store = env.create_store()
336335
box = store.box(MyEntity)
337336

338337
assert box.count() == 2
@@ -348,12 +347,10 @@ class MyEntity:
348347
model = Model()
349348
model.entity(MyEntity)
350349
env.sync(model)
351-
store = env.store()
350+
store = env.create_store()
352351
box = store.box(MyEntity)
353352
box.put( MyEntity(name="foo"), MyEntity(name="bar"))
354353
del box
355-
store.close()
356-
del store
357354

358355
@Entity()
359356
class MyEntity:
@@ -363,7 +360,7 @@ class MyEntity:
363360
model = Model()
364361
model.entity(MyEntity)
365362
env.sync(model)
366-
store = env.store()
363+
store = env.create_store()
367364
box = store.box(MyEntity)
368365
assert box.count() == 2
369366

@@ -377,7 +374,7 @@ class EntityA:
377374
model = Model()
378375
model.entity(EntityA)
379376
env.sync(model)
380-
store = env.store()
377+
store = env.create_store()
381378
box = store.box(EntityA)
382379
box.put(EntityA(name="Luca"))
383380
assert box.count() == 1
@@ -390,8 +387,6 @@ class EntityA:
390387
print(f"Entity.name ID/UID: {name.iduid}")
391388

392389
del box # Close store
393-
store.close()
394-
del store
395390

396391
# *** Rename ***
397392

@@ -403,7 +398,7 @@ class EntityA:
403398
model = Model()
404399
model.entity(EntityA)
405400
env.sync(model)
406-
store = env.store()
401+
store = env.create_store()
407402

408403
# Check ID/UID(s) are preserved after renaming
409404
entity2_iduid = EntityA._iduid

0 commit comments

Comments
 (0)