gowalk-cicd 1.0.83 → 1.0.84
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/action/.daemux-version
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
1.0.
|
|
1
|
+
1.0.84
|
|
@@ -1 +1 @@
|
|
|
1
|
-
1.0.
|
|
1
|
+
1.0.84
|
|
@@ -39,11 +39,14 @@ class Relay:
|
|
|
39
39
|
self.ready.set()
|
|
40
40
|
if self.server:
|
|
41
41
|
self.server.close()
|
|
42
|
-
|
|
42
|
+
# Python 3.12+ waits for active clients in Server.wait_closed().
|
|
43
|
+
# Their handlers own the connections, so cancel and drain them first.
|
|
43
44
|
tasks = asyncio.all_tasks(self.loop)
|
|
44
45
|
for task in tasks:
|
|
45
46
|
task.cancel()
|
|
46
47
|
self.loop.run_until_complete(asyncio.gather(*tasks, return_exceptions=True))
|
|
48
|
+
if self.server:
|
|
49
|
+
self.loop.run_until_complete(self.server.wait_closed())
|
|
47
50
|
self.loop.close()
|
|
48
51
|
|
|
49
52
|
async def _upstream(self, request: bytes):
|
|
@@ -0,0 +1,44 @@
|
|
|
1
|
+
"""Open client sockets must not keep the command's owned relay alive on Python 3.12+."""
|
|
2
|
+
import asyncio
|
|
3
|
+
import socket
|
|
4
|
+
import unittest
|
|
5
|
+
|
|
6
|
+
import jvm_proxy_relay as relay
|
|
7
|
+
from test_jvm_proxy_relay import upstream
|
|
8
|
+
|
|
9
|
+
|
|
10
|
+
async def accepted():
|
|
11
|
+
while not any(task.get_coro().__name__ == "_handle" for task in asyncio.all_tasks()):
|
|
12
|
+
await asyncio.sleep(0.001)
|
|
13
|
+
|
|
14
|
+
|
|
15
|
+
class RelayCleanupTests(unittest.TestCase):
|
|
16
|
+
def test_shutdown_cancels_open_clients_before_waiting_for_server_connections(self):
|
|
17
|
+
with upstream() as (proxy, _seen):
|
|
18
|
+
for connected in (False, True):
|
|
19
|
+
with self.subTest(established_tunnel=connected):
|
|
20
|
+
owned = relay.Relay(proxy)
|
|
21
|
+
owned.thread.start()
|
|
22
|
+
self.assertTrue(owned.ready.wait(5))
|
|
23
|
+
client = socket.create_connection(("127.0.0.1", owned.port), timeout=5)
|
|
24
|
+
try:
|
|
25
|
+
if connected:
|
|
26
|
+
client.sendall(b"CONNECT unresolvable.invalid:443 HTTP/1.1\r\nHost: ignored\r\n\r\n")
|
|
27
|
+
self.assertIn(b"200", client.recv(4096))
|
|
28
|
+
else:
|
|
29
|
+
# Synchronize on acceptance while deliberately leaving the request unfinished.
|
|
30
|
+
asyncio.run_coroutine_threadsafe(accepted(), owned.loop).result(timeout=5)
|
|
31
|
+
owned.loop.call_soon_threadsafe(owned.loop.stop)
|
|
32
|
+
owned.thread.join(timeout=2)
|
|
33
|
+
self.assertFalse(owned.thread.is_alive(), "relay cleanup waits on a client it must close")
|
|
34
|
+
self.assertTrue(owned.loop.is_closed())
|
|
35
|
+
self.assertEqual(client.recv(4096), b"")
|
|
36
|
+
with self.assertRaises(OSError):
|
|
37
|
+
socket.create_connection(("127.0.0.1", owned.port), timeout=0.2)
|
|
38
|
+
finally:
|
|
39
|
+
client.close()
|
|
40
|
+
owned.thread.join(timeout=5)
|
|
41
|
+
|
|
42
|
+
|
|
43
|
+
if __name__ == "__main__":
|
|
44
|
+
unittest.main()
|
|
@@ -1 +1 @@
|
|
|
1
|
-
1.0.
|
|
1
|
+
1.0.84
|