1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
|
import pytest
from szurubooru import db
from szurubooru.func import similar
@pytest.fixture
def verify_posts():
def verify(actual_posts, expected_posts):
actual_post_ids = list([p.post_id for p in actual_posts])
expected_post_ids = list([p.post_id for p in expected_posts])
assert actual_post_ids == expected_post_ids
return verify
# I'd like my behavior to be like this
def test_find_similar_posts(post_factory, tag_factory, verify_posts):
tagA = tag_factory(names=["a"])
tagB = tag_factory(names=["b"])
tagC = tag_factory(names=["c"])
postA = post_factory(id=1, tags=[tagA])
postAB = post_factory(id=2, tags=[tagA, tagB])
postAC = post_factory(id=3, tags=[tagA, tagC])
postABC = post_factory(id=4, tags=[tagA, tagB, tagC])
postBC = post_factory(id=5, tags=[tagB, tagC])
db.session.add_all([tagA, tagB, tagC, postA, postAB, postAC, postABC, postBC])
db.session.flush()
results = similar.find_similar_posts(postBC, 10)
verify_posts(results, [postABC, postAC, postAB])
results = similar.find_similar_posts(postBC, 2)
verify_posts(results, [postABC, postAC])
results = similar.find_similar_posts(postABC, 10)
verify_posts(results, [postBC, postAC, postAB, postA])
results = similar.find_similar_posts(postA, 10)
verify_posts(results, [postABC, postAC, postAB]) # sorted by id
results = similar.find_similar_posts(postAB, 10)
verify_posts(results, [postABC, postBC, postAC, postA])
results = similar.find_similar_posts(postAC, 10)
verify_posts(results, [postABC, postBC, postAB, postA])
# but it's actually like this for performance reasons
def test_find_similar_posts_naive(post_factory, tag_factory, verify_posts):
tagA = tag_factory(names=["a"]) # count=4
tagB = tag_factory(names=["b"]) # count=3
tagC = tag_factory(names=["c"]) # count=3
postA = post_factory(id=1, tags=[tagA])
postAB = post_factory(id=2, tags=[tagA, tagB])
postAC = post_factory(id=3, tags=[tagA, tagC])
postABC = post_factory(id=4, tags=[tagA, tagB, tagC])
postBC = post_factory(id=5, tags=[tagB, tagC])
db.session.add_all([tagA, tagB, tagC, postA, postAB, postAC, postABC, postBC])
db.session.flush()
results = similar.find_similar_posts(postBC, 10)
verify_posts(results, [postABC, postAC])
results = similar.find_similar_posts(postBC, 2)
verify_posts(results, [postABC, postAC])
results = similar.find_similar_posts(postABC, 10)
verify_posts(results, [postAC, postAB, postA])
results = similar.find_similar_posts(postA, 10)
verify_posts(results, [postABC, postAC, postAB]) # sorted by id
results = similar.find_similar_posts(postAB, 10)
verify_posts(results, [postABC, postAC, postA])
results = similar.find_similar_posts(postAC, 10)
verify_posts(results, [postABC, postAB, postA])
def test_find_similar_posts_with_limit(post_factory, tag_factory, verify_posts):
tagA = tag_factory(names=["a"])
tagB = tag_factory(names=["b"])
tagC = tag_factory(names=["c"])
tagD = tag_factory(names=["d"])
tagE = tag_factory(names=["e"])
postA = post_factory(id=111, tags=[tagA])
postAB = post_factory(id=112, tags=[tagA, tagB])
postABCDE = post_factory(id=113, tags=[tagA, tagB, tagC, tagD, tagE])
db.session.add_all([tagA, tagB, tagC, tagD, tagE, postA, postAB, postABCDE])
db.session.flush()
results = similar.find_similar_posts(postABCDE, 10)
# I'd like it to be like this:
# verify_posts(results, [postAB])
# but it's like this for performance reasons:
verify_posts(results, [postAB, postA])
|