python-socks 2.8.2__py3-none-any.whl → 3.0.0__py3-none-any.whl

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.
Files changed (76) hide show
  1. python_socks/__init__.py +11 -13
  2. python_socks/_abc.py +35 -22
  3. python_socks/_connectors/abc.py +5 -3
  4. python_socks/_connectors/factory_async.py +8 -8
  5. python_socks/_connectors/factory_sync.py +8 -8
  6. python_socks/_connectors/http_async.py +7 -7
  7. python_socks/_connectors/http_sync.py +7 -7
  8. python_socks/_connectors/socks4_async.py +10 -10
  9. python_socks/_connectors/socks4_sync.py +10 -10
  10. python_socks/_connectors/socks5_async.py +29 -26
  11. python_socks/_connectors/socks5_sync.py +36 -28
  12. python_socks/_errors.py +15 -2
  13. python_socks/_helpers.py +35 -32
  14. python_socks/_protocols/errors.py +10 -1
  15. python_socks/_protocols/http.py +55 -60
  16. python_socks/_protocols/socks4.py +22 -26
  17. python_socks/_protocols/socks5.py +77 -70
  18. python_socks/_types.py +4 -0
  19. python_socks/_version.py +2 -2
  20. python_socks/async_/__init__.py +0 -3
  21. python_socks/async_/anyio/__init__.py +1 -2
  22. python_socks/async_/anyio/_connect.py +6 -4
  23. python_socks/async_/anyio/_proxy.py +85 -92
  24. python_socks/async_/anyio/_resolver.py +10 -3
  25. python_socks/async_/anyio/_stream.py +11 -26
  26. python_socks/async_/anyio/v2/__init__.py +1 -5
  27. python_socks/async_/anyio/v2/_connect.py +7 -4
  28. python_socks/async_/anyio/v2/_proxy.py +36 -26
  29. python_socks/async_/anyio/v2/_stream.py +11 -11
  30. python_socks/async_/asyncio/__init__.py +1 -2
  31. python_socks/async_/asyncio/_connect.py +12 -7
  32. python_socks/async_/asyncio/_proxy.py +48 -49
  33. python_socks/async_/asyncio/_resolver.py +11 -4
  34. python_socks/async_/asyncio/_stream.py +9 -13
  35. python_socks/async_/asyncio/v2/__init__.py +1 -2
  36. python_socks/async_/asyncio/v2/_connect.py +8 -5
  37. python_socks/async_/asyncio/v2/_proxy.py +38 -28
  38. python_socks/async_/asyncio/v2/_stream.py +16 -18
  39. python_socks/async_/trio/__init__.py +1 -1
  40. python_socks/async_/trio/_connect.py +5 -4
  41. python_socks/async_/trio/_proxy.py +46 -48
  42. python_socks/async_/trio/_resolver.py +11 -3
  43. python_socks/async_/trio/_stream.py +9 -9
  44. python_socks/async_/trio/v2/__init__.py +1 -5
  45. python_socks/async_/trio/v2/_connect.py +3 -2
  46. python_socks/async_/trio/v2/_proxy.py +34 -24
  47. python_socks/async_/trio/v2/_stream.py +13 -13
  48. python_socks/sync/__init__.py +1 -3
  49. python_socks/sync/_connect.py +4 -3
  50. python_socks/sync/_proxy.py +42 -43
  51. python_socks/sync/_resolver.py +17 -5
  52. python_socks/sync/_stream.py +9 -9
  53. python_socks/sync/v2/__init__.py +1 -5
  54. python_socks/sync/v2/_connect.py +5 -3
  55. python_socks/sync/v2/_proxy.py +35 -26
  56. python_socks/sync/v2/_ssl_transport.py +3 -0
  57. python_socks/sync/v2/_stream.py +19 -14
  58. python_socks-3.0.0.dist-info/METADATA +346 -0
  59. python_socks-3.0.0.dist-info/RECORD +65 -0
  60. {python_socks-2.8.2.dist-info → python_socks-3.0.0.dist-info}/WHEEL +1 -1
  61. python_socks/async_/_proxy_chain.py +0 -34
  62. python_socks/async_/anyio/_chain.py +0 -42
  63. python_socks/async_/anyio/v2/_chain.py +0 -32
  64. python_socks/async_/asyncio/v2/_chain.py +0 -32
  65. python_socks/async_/curio/__init__.py +0 -4
  66. python_socks/async_/curio/_connect.py +0 -17
  67. python_socks/async_/curio/_proxy.py +0 -132
  68. python_socks/async_/curio/_resolver.py +0 -25
  69. python_socks/async_/curio/_stream.py +0 -32
  70. python_socks/async_/trio/v2/_chain.py +0 -32
  71. python_socks/sync/_chain.py +0 -32
  72. python_socks/sync/v2/_chain.py +0 -26
  73. python_socks-2.8.2.dist-info/METADATA +0 -295
  74. python_socks-2.8.2.dist-info/RECORD +0 -77
  75. {python_socks-2.8.2.dist-info → python_socks-3.0.0.dist-info}/licenses/LICENSE.txt +0 -0
  76. {python_socks-2.8.2.dist-info → python_socks-3.0.0.dist-info}/top_level.txt +0 -0
python_socks/__init__.py CHANGED
@@ -1,20 +1,18 @@
1
- from ._version import __version__, __title__
2
-
3
- from ._types import ProxyType
4
- from ._helpers import parse_proxy_url
5
-
6
1
  from ._errors import (
2
+ ProxyConnectionError,
7
3
  ProxyError,
8
4
  ProxyTimeoutError,
9
- ProxyConnectionError,
10
5
  )
6
+ from ._helpers import parse_proxy_url
7
+ from ._types import ProxyType
8
+ from ._version import __title__, __version__
11
9
 
12
10
  __all__ = (
13
- '__title__',
14
- '__version__',
15
- 'ProxyError',
16
- 'ProxyTimeoutError',
17
- 'ProxyConnectionError',
18
- 'ProxyType',
19
- 'parse_proxy_url',
11
+ "ProxyConnectionError",
12
+ "ProxyError",
13
+ "ProxyTimeoutError",
14
+ "ProxyType",
15
+ "__title__",
16
+ "__version__",
17
+ "parse_proxy_url",
20
18
  )
python_socks/_abc.py CHANGED
@@ -1,40 +1,53 @@
1
- from typing import Optional
1
+ from __future__ import annotations
2
+
3
+ import socket
4
+
5
+ from ._types import ResolvedAddress
2
6
 
3
7
 
4
8
  class SyncResolver:
5
- def resolve(self, host, port=0, family=0):
6
- raise NotImplementedError()
9
+ def resolve(
10
+ self,
11
+ host: str,
12
+ port: int = 0,
13
+ family: socket.AddressFamily = socket.AF_UNSPEC,
14
+ ) -> ResolvedAddress:
15
+ raise NotImplementedError
7
16
 
8
17
 
9
18
  class AsyncResolver:
10
- async def resolve(self, host, port=0, family=0):
11
- raise NotImplementedError()
19
+ async def resolve(
20
+ self,
21
+ host: str,
22
+ port: int = 0,
23
+ family: socket.AddressFamily = socket.AF_UNSPEC,
24
+ ) -> ResolvedAddress:
25
+ raise NotImplementedError
12
26
 
13
27
 
14
28
  class SyncSocketStream:
29
+ def write(self, data: bytes) -> None:
30
+ raise NotImplementedError
15
31
 
16
- def write_all(self, data: bytes):
17
- raise NotImplementedError()
18
-
19
- def read(self, max_bytes: Optional[int] = None):
20
- raise NotImplementedError()
32
+ def read(self, max_bytes: int = ...) -> bytes:
33
+ raise NotImplementedError
21
34
 
22
- def read_exact(self, n: int):
23
- raise NotImplementedError()
35
+ def read_exactly(self, n: int) -> bytes:
36
+ raise NotImplementedError
24
37
 
25
- def close(self):
26
- raise NotImplementedError()
38
+ def close(self) -> None:
39
+ raise NotImplementedError
27
40
 
28
41
 
29
42
  class AsyncSocketStream:
30
- async def write_all(self, data: bytes):
31
- raise NotImplementedError()
43
+ async def write(self, data: bytes) -> None:
44
+ raise NotImplementedError
32
45
 
33
- async def read(self, max_bytes: Optional[int] = None):
34
- raise NotImplementedError()
46
+ async def read(self, max_bytes: int = ...) -> bytes:
47
+ raise NotImplementedError
35
48
 
36
- async def read_exact(self, n: int):
37
- raise NotImplementedError()
49
+ async def read_exactly(self, n: int) -> bytes:
50
+ raise NotImplementedError
38
51
 
39
- async def close(self):
40
- raise NotImplementedError()
52
+ async def close(self) -> None:
53
+ raise NotImplementedError
@@ -1,4 +1,6 @@
1
- from .._abc import SyncSocketStream, AsyncSocketStream
1
+ from typing import Any
2
+
3
+ from .._abc import AsyncSocketStream, SyncSocketStream
2
4
 
3
5
 
4
6
  class SyncConnector:
@@ -7,7 +9,7 @@ class SyncConnector:
7
9
  stream: SyncSocketStream,
8
10
  host: str,
9
11
  port: int,
10
- ):
12
+ ) -> Any:
11
13
  raise NotImplementedError
12
14
 
13
15
 
@@ -17,5 +19,5 @@ class AsyncConnector:
17
19
  stream: AsyncSocketStream,
18
20
  host: str,
19
21
  port: int,
20
- ):
22
+ ) -> Any:
21
23
  raise NotImplementedError
@@ -1,18 +1,18 @@
1
- from typing import Optional
1
+ from __future__ import annotations
2
+
2
3
  from .._abc import AsyncResolver
3
4
  from .._types import ProxyType
4
-
5
5
  from .abc import AsyncConnector
6
- from .socks5_async import Socks5AsyncConnector
7
- from .socks4_async import Socks4AsyncConnector
8
6
  from .http_async import HttpAsyncConnector
7
+ from .socks4_async import Socks4AsyncConnector
8
+ from .socks5_async import Socks5AsyncConnector
9
9
 
10
10
 
11
11
  def create_connector(
12
12
  proxy_type: ProxyType,
13
- username: Optional[str],
14
- password: Optional[str],
15
- rdns: Optional[bool],
13
+ username: str | None,
14
+ password: str | None,
15
+ rdns: bool | None, # noqa: FBT001
16
16
  resolver: AsyncResolver,
17
17
  ) -> AsyncConnector:
18
18
  if proxy_type == ProxyType.SOCKS4:
@@ -37,4 +37,4 @@ def create_connector(
37
37
  resolver=resolver,
38
38
  )
39
39
 
40
- raise ValueError(f'Invalid proxy type: {proxy_type}')
40
+ raise ValueError(f"Invalid proxy type: {proxy_type}")
@@ -1,18 +1,18 @@
1
- from typing import Optional
1
+ from __future__ import annotations
2
+
2
3
  from .._abc import SyncResolver
3
4
  from .._types import ProxyType
4
-
5
5
  from .abc import SyncConnector
6
- from .socks5_sync import Socks5SyncConnector
7
- from .socks4_sync import Socks4SyncConnector
8
6
  from .http_sync import HttpSyncConnector
7
+ from .socks4_sync import Socks4SyncConnector
8
+ from .socks5_sync import Socks5SyncConnector
9
9
 
10
10
 
11
11
  def create_connector(
12
12
  proxy_type: ProxyType,
13
- username: Optional[str],
14
- password: Optional[str],
15
- rdns: Optional[bool],
13
+ username: str | None,
14
+ password: str | None,
15
+ rdns: bool | None, # noqa: FBT001
16
16
  resolver: SyncResolver,
17
17
  ) -> SyncConnector:
18
18
  if proxy_type == ProxyType.SOCKS4:
@@ -37,4 +37,4 @@ def create_connector(
37
37
  resolver=resolver,
38
38
  )
39
39
 
40
- raise ValueError(f'Invalid proxy type: {proxy_type}')
40
+ raise ValueError(f"Invalid proxy type: {proxy_type}")
@@ -1,17 +1,17 @@
1
- from typing import Optional
2
- from .._abc import AsyncSocketStream, AsyncResolver
3
- from .abc import AsyncConnector
1
+ from __future__ import annotations
4
2
 
3
+ from .._abc import AsyncResolver, AsyncSocketStream
5
4
  from .._protocols import http
5
+ from .abc import AsyncConnector
6
6
 
7
7
 
8
8
  class HttpAsyncConnector(AsyncConnector):
9
9
  def __init__(
10
10
  self,
11
- username: Optional[str],
12
- password: Optional[str],
11
+ username: str | None,
12
+ password: str | None,
13
13
  resolver: AsyncResolver,
14
- ):
14
+ ) -> None:
15
15
  self._username = username
16
16
  self._password = password
17
17
  self._resolver = resolver
@@ -31,7 +31,7 @@ class HttpAsyncConnector(AsyncConnector):
31
31
  password=self._password,
32
32
  )
33
33
  data = conn.send(request)
34
- await stream.write_all(data)
34
+ await stream.write(data)
35
35
 
36
36
  data = await stream.read()
37
37
  reply: http.ConnectReply = conn.receive(data)
@@ -1,17 +1,17 @@
1
- from typing import Optional
2
- from .._abc import SyncSocketStream, SyncResolver
3
- from .abc import SyncConnector
1
+ from __future__ import annotations
4
2
 
3
+ from .._abc import SyncResolver, SyncSocketStream
5
4
  from .._protocols import http
5
+ from .abc import SyncConnector
6
6
 
7
7
 
8
8
  class HttpSyncConnector(SyncConnector):
9
9
  def __init__(
10
10
  self,
11
- username: Optional[str],
12
- password: Optional[str],
11
+ username: str | None,
12
+ password: str | None,
13
13
  resolver: SyncResolver,
14
- ):
14
+ ) -> None:
15
15
  self._username = username
16
16
  self._password = password
17
17
  self._resolver = resolver
@@ -31,7 +31,7 @@ class HttpSyncConnector(SyncConnector):
31
31
  password=self._password,
32
32
  )
33
33
  data = conn.send(request)
34
- stream.write_all(data)
34
+ stream.write(data)
35
35
 
36
36
  data = stream.read()
37
37
  reply: http.ConnectReply = conn.receive(data)
@@ -1,20 +1,20 @@
1
- import socket
2
- from typing import Optional
1
+ from __future__ import annotations
3
2
 
4
- from .._abc import AsyncSocketStream, AsyncResolver
5
- from .abc import AsyncConnector
3
+ import socket
6
4
 
7
- from .._protocols import socks4
5
+ from .._abc import AsyncResolver, AsyncSocketStream
8
6
  from .._helpers import is_ip_address
7
+ from .._protocols import socks4
8
+ from .abc import AsyncConnector
9
9
 
10
10
 
11
11
  class Socks4AsyncConnector(AsyncConnector):
12
12
  def __init__(
13
13
  self,
14
- user_id: Optional[str],
15
- rdns: Optional[bool],
14
+ user_id: str | None,
15
+ rdns: bool | None, # noqa: FBT001
16
16
  resolver: AsyncResolver,
17
- ):
17
+ ) -> None:
18
18
  if rdns is None:
19
19
  rdns = False
20
20
 
@@ -38,8 +38,8 @@ class Socks4AsyncConnector(AsyncConnector):
38
38
 
39
39
  request = socks4.ConnectRequest(host=host, port=port, user_id=self._user_id)
40
40
  data = conn.send(request)
41
- await stream.write_all(data)
41
+ await stream.write(data)
42
42
 
43
- data = await stream.read_exact(socks4.ConnectReply.SIZE)
43
+ data = await stream.read_exactly(socks4.ConnectReply.SIZE)
44
44
  reply: socks4.ConnectReply = conn.receive(data)
45
45
  return reply
@@ -1,20 +1,20 @@
1
- import socket
2
- from typing import Optional
1
+ from __future__ import annotations
3
2
 
4
- from .._abc import SyncSocketStream, SyncResolver
5
- from .abc import SyncConnector
3
+ import socket
6
4
 
7
- from .._protocols import socks4
5
+ from .._abc import SyncResolver, SyncSocketStream
8
6
  from .._helpers import is_ip_address
7
+ from .._protocols import socks4
8
+ from .abc import SyncConnector
9
9
 
10
10
 
11
11
  class Socks4SyncConnector(SyncConnector):
12
12
  def __init__(
13
13
  self,
14
- user_id: Optional[str],
15
- rdns: Optional[bool],
14
+ user_id: str | None,
15
+ rdns: bool | None, # noqa: FBT001
16
16
  resolver: SyncResolver,
17
- ):
17
+ ) -> None:
18
18
  if rdns is None:
19
19
  rdns = False
20
20
 
@@ -38,8 +38,8 @@ class Socks4SyncConnector(SyncConnector):
38
38
 
39
39
  request = socks4.ConnectRequest(host=host, port=port, user_id=self._user_id)
40
40
  data = conn.send(request)
41
- stream.write_all(data)
41
+ stream.write(data)
42
42
 
43
- data = stream.read_exact(socks4.ConnectReply.SIZE)
43
+ data = stream.read_exactly(socks4.ConnectReply.SIZE)
44
44
  reply: socks4.ConnectReply = conn.receive(data)
45
45
  return reply
@@ -1,21 +1,21 @@
1
- import socket
2
- from typing import Optional
1
+ from __future__ import annotations
3
2
 
4
- from .._abc import AsyncSocketStream, AsyncResolver
5
- from .abc import AsyncConnector
3
+ import socket
6
4
 
7
- from .._protocols import socks5
5
+ from .._abc import AsyncResolver, AsyncSocketStream
8
6
  from .._helpers import is_ip_address
7
+ from .._protocols import socks5
8
+ from .abc import AsyncConnector
9
9
 
10
10
 
11
11
  class Socks5AsyncConnector(AsyncConnector):
12
12
  def __init__(
13
13
  self,
14
- username: Optional[str],
15
- password: Optional[str],
16
- rdns: Optional[bool],
14
+ username: str | None,
15
+ password: str | None,
16
+ rdns: bool | None, # noqa: FBT001
17
17
  resolver: AsyncResolver,
18
- ):
18
+ ) -> None:
19
19
  if rdns is None:
20
20
  rdns = True
21
21
 
@@ -38,41 +38,44 @@ class Socks5AsyncConnector(AsyncConnector):
38
38
  password=self._password,
39
39
  )
40
40
  data = conn.send(request)
41
- await stream.write_all(data)
41
+ await stream.write(data)
42
42
 
43
- data = await stream.read_exact(socks5.AuthMethodReply.SIZE)
44
- reply: socks5.AuthMethodReply = conn.receive(data)
43
+ data = await stream.read_exactly(socks5.AuthMethodReply.SIZE)
44
+ reply: socks5.AuthMethodReply = conn.receive(data) # type:ignore[assignment]
45
45
 
46
46
  # Authenticate
47
47
  if reply.method == socks5.AuthMethod.USERNAME_PASSWORD:
48
- request = socks5.AuthRequest(
48
+ assert self._username is not None
49
+ assert self._password is not None
50
+
51
+ request = socks5.AuthRequest( # type:ignore[assignment]
49
52
  username=self._username,
50
53
  password=self._password,
51
54
  )
52
55
  data = conn.send(request)
53
- await stream.write_all(data)
56
+ await stream.write(data)
54
57
 
55
- data = await stream.read_exact(socks5.AuthReply.SIZE)
56
- _: socks5.AuthReply = conn.receive(data)
58
+ data = await stream.read_exactly(socks5.AuthReply.SIZE)
59
+ _: socks5.AuthReply = conn.receive(data) # type:ignore[assignment]
57
60
 
58
61
  # Connect
59
62
  if not is_ip_address(host) and not self._rdns:
60
- _, host = await self._resolver.resolve(
63
+ _family, host = await self._resolver.resolve(
61
64
  host,
62
65
  family=socket.AF_UNSPEC,
63
66
  )
64
67
 
65
68
  request = socks5.ConnectRequest(host=host, port=port)
66
69
  data = conn.send(request)
67
- await stream.write_all(data)
70
+ await stream.write(data)
68
71
 
69
72
  data = await self._read_reply(stream)
70
- reply: socks5.ConnectReply = conn.receive(data)
71
- return reply
73
+ reply: socks5.ConnectReply = conn.receive(data) # type:ignore[assignment]
74
+ return reply # type:ignore[return-value]
72
75
 
73
76
  # noinspection PyMethodMayBeStatic
74
77
  async def _read_reply(self, stream: AsyncSocketStream) -> bytes:
75
- data = await stream.read_exact(3)
78
+ data = await stream.read_exactly(3)
76
79
  if data[0] != socks5.SOCKS_VER:
77
80
  return data
78
81
  if data[1] != socks5.ReplyCode.SUCCEEDED:
@@ -80,16 +83,16 @@ class Socks5AsyncConnector(AsyncConnector):
80
83
  if data[2] != socks5.RSV:
81
84
  return data
82
85
 
83
- data += await stream.read_exact(1)
86
+ data += await stream.read_exactly(1)
84
87
  addr_type = data[3]
85
88
 
86
89
  if addr_type == socks5.AddressType.IPV4:
87
- data += await stream.read_exact(6)
90
+ data += await stream.read_exactly(6)
88
91
  elif addr_type == socks5.AddressType.IPV6:
89
- data += await stream.read_exact(18)
92
+ data += await stream.read_exactly(18)
90
93
  elif addr_type == socks5.AddressType.DOMAIN:
91
- data += await stream.read_exact(1)
94
+ data += await stream.read_exactly(1)
92
95
  host_len = data[-1]
93
- data += await stream.read_exact(host_len + 2)
96
+ data += await stream.read_exactly(host_len + 2)
94
97
 
95
98
  return data
@@ -1,21 +1,21 @@
1
- import socket
2
- from typing import Optional
1
+ from __future__ import annotations
3
2
 
4
- from .._abc import SyncSocketStream, SyncResolver
5
- from .abc import SyncConnector
3
+ import socket
6
4
 
7
- from .._protocols import socks5
5
+ from .._abc import SyncResolver, SyncSocketStream
8
6
  from .._helpers import is_ip_address
7
+ from .._protocols import socks5
8
+ from .abc import SyncConnector
9
9
 
10
10
 
11
11
  class Socks5SyncConnector(SyncConnector):
12
12
  def __init__(
13
13
  self,
14
- username: Optional[str],
15
- password: Optional[str],
16
- rdns: Optional[bool],
14
+ username: str | None,
15
+ password: str | None,
16
+ rdns: bool | None, # noqa: FBT001
17
17
  resolver: SyncResolver,
18
- ):
18
+ ) -> None:
19
19
  if rdns is None:
20
20
  rdns = True
21
21
 
@@ -33,37 +33,45 @@ class Socks5SyncConnector(SyncConnector):
33
33
  conn = socks5.Connection()
34
34
 
35
35
  # Auth methods
36
- request = socks5.AuthMethodsRequest(username=self._username, password=self._password)
36
+ request = socks5.AuthMethodsRequest(
37
+ username=self._username,
38
+ password=self._password,
39
+ )
37
40
  data = conn.send(request)
38
- stream.write_all(data)
41
+ stream.write(data)
39
42
 
40
- data = stream.read_exact(socks5.AuthMethodReply.SIZE)
41
- reply: socks5.AuthMethodReply = conn.receive(data)
43
+ data = stream.read_exactly(socks5.AuthMethodReply.SIZE)
44
+ reply: socks5.AuthMethodReply = conn.receive(data) # type:ignore[assignment]
42
45
 
43
46
  # Authenticate
44
47
  if reply.method == socks5.AuthMethod.USERNAME_PASSWORD:
45
- request = socks5.AuthRequest(username=self._username, password=self._password)
48
+ assert self._username is not None
49
+ assert self._password is not None
50
+
51
+ request = socks5.AuthRequest( # type:ignore[assignment]
52
+ username=self._username,
53
+ password=self._password,
54
+ )
46
55
  data = conn.send(request)
47
- stream.write_all(data)
56
+ stream.write(data)
48
57
 
49
- data = stream.read_exact(socks5.AuthReply.SIZE)
50
- _: socks5.AuthReply = conn.receive(data)
58
+ data = stream.read_exactly(socks5.AuthReply.SIZE)
59
+ _: socks5.AuthReply = conn.receive(data) # type:ignore[assignment]
51
60
 
52
61
  # Connect
53
62
  if not is_ip_address(host) and not self._rdns:
54
- _, host = self._resolver.resolve(host, family=socket.AF_UNSPEC)
63
+ _family, host = self._resolver.resolve(host, family=socket.AF_UNSPEC)
55
64
 
56
65
  request = socks5.ConnectRequest(host=host, port=port)
57
66
  data = conn.send(request)
58
- stream.write_all(data)
67
+ stream.write(data)
59
68
 
60
69
  data = self._read_reply(stream)
61
- reply: socks5.ConnectReply = conn.receive(data)
62
- return reply
70
+ reply: socks5.ConnectReply = conn.receive(data) # type:ignore[assignment]
71
+ return reply # type:ignore[return-value]
63
72
 
64
- # noinspection PyMethodMayBeStatic
65
73
  def _read_reply(self, stream: SyncSocketStream) -> bytes:
66
- data = stream.read_exact(3)
74
+ data = stream.read_exactly(3)
67
75
  if data[0] != socks5.SOCKS_VER:
68
76
  return data
69
77
  if data[1] != socks5.ReplyCode.SUCCEEDED:
@@ -71,16 +79,16 @@ class Socks5SyncConnector(SyncConnector):
71
79
  if data[2] != socks5.RSV:
72
80
  return data
73
81
 
74
- data += stream.read_exact(1)
82
+ data += stream.read_exactly(1)
75
83
  addr_type = data[3]
76
84
 
77
85
  if addr_type == socks5.AddressType.IPV4:
78
- data += stream.read_exact(6)
86
+ data += stream.read_exactly(6)
79
87
  elif addr_type == socks5.AddressType.IPV6:
80
- data += stream.read_exact(18)
88
+ data += stream.read_exactly(18)
81
89
  elif addr_type == socks5.AddressType.DOMAIN:
82
- data += stream.read_exact(1)
90
+ data += stream.read_exactly(1)
83
91
  host_len = data[-1]
84
- data += stream.read_exact(host_len + 2)
92
+ data += stream.read_exactly(host_len + 2)
85
93
 
86
94
  return data
python_socks/_errors.py CHANGED
@@ -1,4 +1,13 @@
1
- class ProxyException(Exception):
1
+ from __future__ import annotations
2
+
3
+ from typing import Any
4
+
5
+
6
+ class IncompleteReadError(Exception):
7
+ pass
8
+
9
+
10
+ class ProxyException(Exception): # noqa: N818
2
11
  pass
3
12
 
4
13
 
@@ -11,6 +20,10 @@ class ProxyConnectionError(ProxyException, OSError):
11
20
 
12
21
 
13
22
  class ProxyError(ProxyException):
14
- def __init__(self, message, error_code=None):
23
+ def __init__(
24
+ self,
25
+ message: Any,
26
+ error_code: int | None = None,
27
+ ) -> None:
15
28
  super().__init__(message)
16
29
  self.error_code = error_code