python-http_request 0.0.1__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.
LICENSE ADDED
@@ -0,0 +1,21 @@
1
+ MIT License
2
+
3
+ Copyright (c) 2024 ChenyangGao <https://github.com/ChenyangGao>
4
+
5
+ Permission is hereby granted, free of charge, to any person obtaining a copy
6
+ of this software and associated documentation files (the "Software"), to deal
7
+ in the Software without restriction, including without limitation the rights
8
+ to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9
+ copies of the Software, and to permit persons to whom the Software is
10
+ furnished to do so, subject to the following conditions:
11
+
12
+ The above copyright notice and this permission notice shall be included in all
13
+ copies or substantial portions of the Software.
14
+
15
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16
+ IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17
+ FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18
+ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19
+ LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20
+ OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21
+ SOFTWARE.
@@ -0,0 +1,104 @@
1
+ #!/usr/bin/env python3
2
+ # encoding: utf-8
3
+
4
+ __author__ = "ChenyangGao <https://chenyanggao.github.io>"
5
+ __version__ = (0, 0, 1)
6
+ __all__ = ["encode_multipart_data", "encode_multipart_data_async"]
7
+
8
+ from itertools import chain
9
+ from collections.abc import AsyncIterable, AsyncIterator, ItemsView, Iterable, Iterator, Mapping
10
+ from typing import Any
11
+ from urllib.parse import quote
12
+ from uuid import uuid4
13
+
14
+ from asynctools import ensure_aiter, async_chain
15
+ from filewrap import bio_chunk_iter, bio_chunk_async_iter, SupportsRead
16
+ from integer_tool import int_to_bytes
17
+
18
+
19
+ def ensure_bytes(s, /) -> bytes | bytearray | memoryview:
20
+ if isinstance(s, (bytes, bytearray, memoryview)):
21
+ return s
22
+ if isinstance(s, int):
23
+ return int_to_bytes(s)
24
+ elif isinstance(s, str):
25
+ return bytes(s, "utf-8")
26
+ try:
27
+ return bytes(s)
28
+ except TypeError:
29
+ return bytes(str(s), "utf-8")
30
+
31
+
32
+ def encode_multipart_data(
33
+ data: Mapping[str, Any],
34
+ files: Mapping[str, bytes | bytearray | memoryview | SupportsRead[bytes] | Iterable[bytes]],
35
+ boundary: None | str = None,
36
+ ) -> tuple[dict, Iterator[bytes]]:
37
+ if not boundary:
38
+ boundary = uuid4().bytes.hex()
39
+ headers = {"Content-Type": f"multipart/form-data; boundary={boundary}"}
40
+
41
+ def encode_data(data) -> Iterator[bytes]:
42
+ if isinstance(data, Mapping):
43
+ data = ItemsView(data)
44
+ for name, value in data:
45
+ yield boundary_line
46
+ yield b'Content-Disposition: form-data; name="%s"\r\n\r\n' % bytes(quote(name), "ascii")
47
+ yield ensure_bytes(value)
48
+ yield b"\r\n"
49
+
50
+ def encode_files(files) -> Iterator[bytes]:
51
+ if isinstance(files, Mapping):
52
+ files = ItemsView(files)
53
+ for name, file in files:
54
+ yield boundary_line
55
+ yield b'Content-Disposition: form-data; name="%s"\r\nContent-Type: application/octet-stream\r\n\r\n' % bytes(quote(name), "ascii")
56
+ if isinstance(file, (bytes, bytearray, memoryview)):
57
+ yield file
58
+ elif hasattr(file, "read"):
59
+ yield from bio_chunk_iter(file)
60
+ else:
61
+ yield from file
62
+ yield b"\r\n"
63
+
64
+ boundary_line = b"--%s\r\n" % boundary.encode("utf-8")
65
+ return headers, chain(encode_data(data), encode_files(files), (b'--%s--\r\n' % boundary.encode("ascii"),))
66
+
67
+
68
+ def encode_multipart_data_async(
69
+ data: Mapping[str, Any],
70
+ files: Mapping[str, bytes | bytearray | memoryview | SupportsRead[bytes] | Iterable[bytes] | AsyncIterable[bytes]],
71
+ boundary: None | str = None,
72
+ ) -> tuple[dict, AsyncIterator[bytes]]:
73
+ if not boundary:
74
+ boundary = uuid4().bytes.hex()
75
+ headers = {"Content-Type": f"multipart/form-data; boundary={boundary}"}
76
+
77
+ async def encode_data(data) -> AsyncIterator[bytes]:
78
+ if isinstance(data, Mapping):
79
+ data = ItemsView(data)
80
+ for name, value in data:
81
+ yield boundary_line
82
+ yield b'Content-Disposition: form-data; name="%s"\r\n\r\n' % bytes(quote(name), "ascii")
83
+ yield ensure_bytes(value)
84
+ yield b"\r\n"
85
+
86
+ async def encode_files(files) -> AsyncIterator[bytes]:
87
+ if isinstance(files, Mapping):
88
+ files = ItemsView(files)
89
+ for name, file in files:
90
+ yield boundary_line
91
+ yield b'Content-Disposition: form-data; name="%s"\r\nContent-Type: application/octet-stream\r\n\r\n' % bytes(quote(name), "ascii")
92
+ if isinstance(file, (bytes, bytearray, memoryview)):
93
+ yield file
94
+ elif hasattr(file, "read"):
95
+ async for b in bio_chunk_async_iter(file):
96
+ yield b
97
+ else:
98
+ async for b in ensure_aiter(file):
99
+ yield b
100
+ yield b"\r\n"
101
+
102
+ boundary_line = b"--%s\r\n" % boundary.encode("utf-8")
103
+ return headers, async_chain(encode_data(data), encode_files(files), (b'--%s--\r\n' % boundary.encode("ascii"),))
104
+
http_request/py.typed ADDED
File without changes
@@ -0,0 +1,21 @@
1
+ MIT License
2
+
3
+ Copyright (c) 2024 ChenyangGao <https://github.com/ChenyangGao>
4
+
5
+ Permission is hereby granted, free of charge, to any person obtaining a copy
6
+ of this software and associated documentation files (the "Software"), to deal
7
+ in the Software without restriction, including without limitation the rights
8
+ to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9
+ copies of the Software, and to permit persons to whom the Software is
10
+ furnished to do so, subject to the following conditions:
11
+
12
+ The above copyright notice and this permission notice shall be included in all
13
+ copies or substantial portions of the Software.
14
+
15
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16
+ IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17
+ FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18
+ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19
+ LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20
+ OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21
+ SOFTWARE.
@@ -0,0 +1,45 @@
1
+ Metadata-Version: 2.1
2
+ Name: python-http_request
3
+ Version: 0.0.1
4
+ Summary: Python http response utils.
5
+ Home-page: https://github.com/ChenyangGao/web-mount-packs/tree/main/python-module/python-http_request
6
+ License: MIT
7
+ Keywords: http,request
8
+ Author: ChenyangGao
9
+ Author-email: wosiwujm@gmail.com
10
+ Requires-Python: >=3.10,<4.0
11
+ Classifier: Development Status :: 5 - Production/Stable
12
+ Classifier: Intended Audience :: Developers
13
+ Classifier: License :: OSI Approved :: MIT License
14
+ Classifier: Operating System :: OS Independent
15
+ Classifier: Programming Language :: Python
16
+ Classifier: Programming Language :: Python :: 3
17
+ Classifier: Programming Language :: Python :: 3.10
18
+ Classifier: Programming Language :: Python :: 3.11
19
+ Classifier: Programming Language :: Python :: 3.12
20
+ Classifier: Programming Language :: Python :: 3 :: Only
21
+ Classifier: Topic :: Software Development
22
+ Classifier: Topic :: Software Development :: Libraries
23
+ Classifier: Topic :: Software Development :: Libraries :: Python Modules
24
+ Requires-Dist: integer_tool
25
+ Requires-Dist: python-asynctools
26
+ Requires-Dist: python-filewrap
27
+ Project-URL: Repository, https://github.com/ChenyangGao/web-mount-packs/tree/main/python-module/python-http_request
28
+ Description-Content-Type: text/markdown
29
+
30
+ # Python http response utils.
31
+
32
+ ## Installation
33
+
34
+ You can install from [pypi](https://pypi.org/project/python-http_request/)
35
+
36
+ ```console
37
+ pip install -U python-http_request
38
+ ```
39
+
40
+ ## Usage
41
+
42
+ ```python
43
+ import http_request
44
+ ```
45
+
@@ -0,0 +1,7 @@
1
+ LICENSE,sha256=o5242_N2TgDsWwFhPn7yr8YJNF7XsJM5NxUMtcT97bc,1100
2
+ http_request/__init__.py,sha256=XFn8Ooa6VTEf90lYj2sijGgv1tywDxQ8bJoVH24Gv_M,3992
3
+ http_request/py.typed,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
4
+ python_http_request-0.0.1.dist-info/LICENSE,sha256=o5242_N2TgDsWwFhPn7yr8YJNF7XsJM5NxUMtcT97bc,1100
5
+ python_http_request-0.0.1.dist-info/METADATA,sha256=l8J6UAwNpZ26OQraM82s0uHpCJc15piOxne5dLjvXz8,1457
6
+ python_http_request-0.0.1.dist-info/WHEEL,sha256=FMvqSimYX_P7y0a7UY-_Mc83r5zkBZsCYPm7Lr0Bsq4,88
7
+ python_http_request-0.0.1.dist-info/RECORD,,
@@ -0,0 +1,4 @@
1
+ Wheel-Version: 1.0
2
+ Generator: poetry-core 1.8.1
3
+ Root-Is-Purelib: true
4
+ Tag: py3-none-any