summaryrefslogtreecommitdiff
path: root/tests/integration/test_expiry.py
diff options
context:
space:
mode:
Diffstat (limited to 'tests/integration/test_expiry.py')
-rw-r--r--tests/integration/test_expiry.py42
1 files changed, 42 insertions, 0 deletions
diff --git a/tests/integration/test_expiry.py b/tests/integration/test_expiry.py
new file mode 100644
index 0000000..4466724
--- /dev/null
+++ b/tests/integration/test_expiry.py
@@ -0,0 +1,42 @@
1"""What the expiry sweep finds after a connection has already gone.
2
3A plain request is answered and the connection closed by http_senddata, not
4by the sweep. If that path leaves the descriptor's slot behind, the sweep
5walks into it once the client timeout has passed and frees a cookie that is
6already gone. Under the sanitizer build that is reported, and teardown turns
7it into a failure.
8
9The two numbers below mirror OT_CLIENT_TIMEOUT and
10OT_CLIENT_TIMEOUT_CHECKINTERVAL in FEATURES_integration.
11"""
12
13import time
14import unittest
15
16from harness import TrackerTestCase
17
18CLIENT_TIMEOUT = 5
19CHECK_INTERVAL = 1
20
21
22class ExpirySweep(TrackerTestCase):
23 def test_an_answered_request_leaves_nothing_behind(self):
24 info_hash = self.hash_for("expiry-sweep")
25 self.assertEqual(self.tracker.announce(info_hash)[b"complete"], 1)
26
27 # Long enough for the slot to expire and for a sweep to visit it
28 time.sleep(CLIENT_TIMEOUT + 3 * CHECK_INTERVAL)
29
30 self.assertEqual(self.tracker.torrent_count(), 1, "the tracker stopped serving while sweeping")
31
32 def test_a_connection_that_never_speaks_is_swept(self):
33 """The other side of it: a slot that really is live must still go."""
34 import socket
35
36 idle = socket.create_connection(("127.0.0.1", self.tracker.port), timeout=5)
37 try:
38 time.sleep(CLIENT_TIMEOUT + 3 * CHECK_INTERVAL)
39 idle.settimeout(5)
40 self.assertEqual(idle.recv(64), b"", "the tracker held a connection that never sent a request")
41 finally:
42 idle.close()