python-httpfile 0.0.4__py3-none-any.whl → 0.0.4.2__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.
- httpfile/__init__.py +68 -9
- {python_httpfile-0.0.4.dist-info → python_httpfile-0.0.4.2.dist-info}/METADATA +1 -1
- python_httpfile-0.0.4.2.dist-info/RECORD +7 -0
- python_httpfile-0.0.4.dist-info/RECORD +0 -7
- {python_httpfile-0.0.4.dist-info → python_httpfile-0.0.4.2.dist-info}/LICENSE +0 -0
- {python_httpfile-0.0.4.dist-info → python_httpfile-0.0.4.2.dist-info}/WHEEL +0 -0
httpfile/__init__.py
CHANGED
|
@@ -215,6 +215,8 @@ class HTTPFileReader(RawIOBase, BinaryIO):
|
|
|
215
215
|
return self.file.fileno()
|
|
216
216
|
|
|
217
217
|
def flush(self, /):
|
|
218
|
+
if self.closed:
|
|
219
|
+
raise ValueError("I/O operation on closed file.")
|
|
218
220
|
return self.file.flush()
|
|
219
221
|
|
|
220
222
|
def isatty(self, /) -> bool:
|
|
@@ -253,7 +255,16 @@ class HTTPFileReader(RawIOBase, BinaryIO):
|
|
|
253
255
|
return 0
|
|
254
256
|
if self.file_closed:
|
|
255
257
|
self.reconnect()
|
|
256
|
-
|
|
258
|
+
try:
|
|
259
|
+
readinto = self.file.readinto
|
|
260
|
+
except AttributeError:
|
|
261
|
+
read = self.file.read
|
|
262
|
+
def readinto(buffer, /):
|
|
263
|
+
data = read(len(buffer))
|
|
264
|
+
size = len(data)
|
|
265
|
+
buffer[:size] = data
|
|
266
|
+
return data
|
|
267
|
+
size = readinto(buffer)
|
|
257
268
|
if size:
|
|
258
269
|
self._add_start(size)
|
|
259
270
|
return size
|
|
@@ -265,6 +276,7 @@ class HTTPFileReader(RawIOBase, BinaryIO):
|
|
|
265
276
|
return b""
|
|
266
277
|
if self.file_closed:
|
|
267
278
|
self.reconnect()
|
|
279
|
+
# TODO: if no readline method, give a default impl
|
|
268
280
|
if size is None or size < 0:
|
|
269
281
|
data = self.file.readline()
|
|
270
282
|
else:
|
|
@@ -280,6 +292,7 @@ class HTTPFileReader(RawIOBase, BinaryIO):
|
|
|
280
292
|
return []
|
|
281
293
|
if self.file_closed:
|
|
282
294
|
self.reconnect()
|
|
295
|
+
# TODO: if no readlines method, give a default impl
|
|
283
296
|
ls = self.file.readlines(hint)
|
|
284
297
|
if ls:
|
|
285
298
|
self._add_start(sum(map(len, ls)))
|
|
@@ -520,9 +533,9 @@ class AsyncHTTPFileReader(HTTPFileReader):
|
|
|
520
533
|
headers: None | Mapping = None,
|
|
521
534
|
start: int = 0,
|
|
522
535
|
seek_threshold: int = 1 << 20,
|
|
523
|
-
urlopen =
|
|
536
|
+
urlopen = None,
|
|
524
537
|
):
|
|
525
|
-
run_async(self.__ainit__(
|
|
538
|
+
self.__dict__["_initing"] = run_async(self.__ainit__(
|
|
526
539
|
url=url,
|
|
527
540
|
headers=headers,
|
|
528
541
|
start=start,
|
|
@@ -531,6 +544,9 @@ class AsyncHTTPFileReader(HTTPFileReader):
|
|
|
531
544
|
))
|
|
532
545
|
|
|
533
546
|
async def __aenter__(self, /) -> Self:
|
|
547
|
+
if _initing := self.__dict__.get("_initing"):
|
|
548
|
+
await _initing
|
|
549
|
+
self.__dict__.pop("_initing", None)
|
|
534
550
|
return self
|
|
535
551
|
|
|
536
552
|
async def __aexit__(self, /, *exc_info):
|
|
@@ -597,6 +613,7 @@ class AsyncHTTPFileReader(HTTPFileReader):
|
|
|
597
613
|
seek_threshold = max(seek_threshold, 0),
|
|
598
614
|
_seekable = is_range_request(response),
|
|
599
615
|
)
|
|
616
|
+
self.__dict__.pop("_initing", None)
|
|
600
617
|
|
|
601
618
|
async def aclose(self, /):
|
|
602
619
|
if not self.closed:
|
|
@@ -609,7 +626,10 @@ class AsyncHTTPFileReader(HTTPFileReader):
|
|
|
609
626
|
try:
|
|
610
627
|
ret = self.response.aclose()
|
|
611
628
|
except (AttributeError, TypeError):
|
|
612
|
-
|
|
629
|
+
try:
|
|
630
|
+
ret = self.response.close()
|
|
631
|
+
except (AttributeError, TypeError):
|
|
632
|
+
return
|
|
613
633
|
if isawaitable(ret):
|
|
614
634
|
run_async(ret)
|
|
615
635
|
|
|
@@ -617,24 +637,36 @@ class AsyncHTTPFileReader(HTTPFileReader):
|
|
|
617
637
|
try:
|
|
618
638
|
ret = self.response.aclose()
|
|
619
639
|
except (AttributeError, TypeError):
|
|
620
|
-
|
|
640
|
+
try:
|
|
641
|
+
ret = self.response.close()
|
|
642
|
+
except (AttributeError, TypeError):
|
|
643
|
+
return
|
|
621
644
|
if isawaitable(ret):
|
|
622
645
|
await ret
|
|
623
646
|
|
|
624
647
|
async def flush(self, /):
|
|
648
|
+
if self.closed:
|
|
649
|
+
raise ValueError("I/O operation on closed file.")
|
|
650
|
+
if _initing := self.__dict__.get("_initing"):
|
|
651
|
+
await _initing
|
|
652
|
+
self.__dict__.pop("_initing", None)
|
|
625
653
|
return await ensure_async(self.file.flush, threaded=True)()
|
|
626
654
|
|
|
627
655
|
async def read(self, size: int = -1, /) -> bytes: # type: ignore
|
|
628
656
|
if self.closed:
|
|
629
657
|
raise ValueError("I/O operation on closed file.")
|
|
658
|
+
if _initing := self.__dict__.get("_initing"):
|
|
659
|
+
await _initing
|
|
660
|
+
self.__dict__.pop("_initing", None)
|
|
630
661
|
if size == 0 or not self.chunked and self.tell() >= self.length:
|
|
631
662
|
return b""
|
|
632
663
|
if self.file_closed:
|
|
633
664
|
await self.reconnect()
|
|
665
|
+
read = ensure_async(self.file.read, threaded=True)
|
|
634
666
|
if size is None or size < 0:
|
|
635
|
-
data = await
|
|
667
|
+
data = await read(-1)
|
|
636
668
|
else:
|
|
637
|
-
data = await
|
|
669
|
+
data = await read(size)
|
|
638
670
|
if data:
|
|
639
671
|
self._add_start(len(data))
|
|
640
672
|
return data
|
|
@@ -642,11 +674,23 @@ class AsyncHTTPFileReader(HTTPFileReader):
|
|
|
642
674
|
async def readinto(self, buffer, /) -> int: # type: ignore
|
|
643
675
|
if self.closed:
|
|
644
676
|
raise ValueError("I/O operation on closed file.")
|
|
677
|
+
if _initing := self.__dict__.get("_initing"):
|
|
678
|
+
await _initing
|
|
679
|
+
self.__dict__.pop("_initing", None)
|
|
645
680
|
if not buffer or not self.chunked and self.tell() >= self.length:
|
|
646
681
|
return 0
|
|
647
682
|
if self.file_closed:
|
|
648
683
|
await self.reconnect()
|
|
649
|
-
|
|
684
|
+
try:
|
|
685
|
+
readinto = ensure_async(self.file.readinto, threaded=True)
|
|
686
|
+
except AttributeError:
|
|
687
|
+
read = ensure_async(self.file.read, threaded=True)
|
|
688
|
+
async def readinto(buffer, /):
|
|
689
|
+
data = await read(len(buffer))
|
|
690
|
+
size = len(data)
|
|
691
|
+
buffer[:size] = data
|
|
692
|
+
return size
|
|
693
|
+
size = await readinto(buffer)
|
|
650
694
|
if size:
|
|
651
695
|
self._add_start(size)
|
|
652
696
|
return size
|
|
@@ -654,10 +698,14 @@ class AsyncHTTPFileReader(HTTPFileReader):
|
|
|
654
698
|
async def readline(self, size: None | int = -1, /) -> bytes: # type: ignore
|
|
655
699
|
if self.closed:
|
|
656
700
|
raise ValueError("I/O operation on closed file.")
|
|
701
|
+
if _initing := self.__dict__.get("_initing"):
|
|
702
|
+
await _initing
|
|
703
|
+
self.__dict__.pop("_initing", None)
|
|
657
704
|
if size == 0 or not self.chunked and self.tell() >= self.length:
|
|
658
705
|
return b""
|
|
659
706
|
if self.file_closed:
|
|
660
707
|
await self.reconnect()
|
|
708
|
+
# TODO: if no readline method, give a default impl
|
|
661
709
|
if size is None or size < 0:
|
|
662
710
|
data = await ensure_async(self.file.readline, threaded=True)()
|
|
663
711
|
else:
|
|
@@ -669,16 +717,23 @@ class AsyncHTTPFileReader(HTTPFileReader):
|
|
|
669
717
|
async def readlines(self, hint: int = -1, /) -> list[bytes]: # type: ignore
|
|
670
718
|
if self.closed:
|
|
671
719
|
raise ValueError("I/O operation on closed file.")
|
|
720
|
+
if _initing := self.__dict__.get("_initing"):
|
|
721
|
+
await _initing
|
|
722
|
+
self.__dict__.pop("_initing", None)
|
|
672
723
|
if not self.chunked and self.tell() >= self.length:
|
|
673
724
|
return []
|
|
674
725
|
if self.file_closed:
|
|
675
726
|
await self.reconnect()
|
|
727
|
+
# TODO: if no readlines method, give a default impl
|
|
676
728
|
ls = await ensure_async(self.file.readlines, threaded=True)(hint)
|
|
677
729
|
if ls:
|
|
678
730
|
self._add_start(sum(map(len, ls)))
|
|
679
731
|
return ls
|
|
680
732
|
|
|
681
733
|
async def reconnect(self, /, start: None | int = None) -> int: # type: ignore
|
|
734
|
+
if _initing := self.__dict__.get("_initing"):
|
|
735
|
+
await _initing
|
|
736
|
+
self.__dict__.pop("_initing", None)
|
|
682
737
|
if not self._seekable:
|
|
683
738
|
if start is None and self.tell() or start:
|
|
684
739
|
raise OSError(errno.EOPNOTSUPP, "Unsupport for reconnection of non-seekable streams.")
|
|
@@ -711,6 +766,9 @@ class AsyncHTTPFileReader(HTTPFileReader):
|
|
|
711
766
|
async def seek(self, pos: int, whence: int = 0, /) -> int: # type: ignore
|
|
712
767
|
if self.closed:
|
|
713
768
|
raise ValueError("I/O operation on closed file.")
|
|
769
|
+
if _initing := self.__dict__.get("_initing"):
|
|
770
|
+
await _initing
|
|
771
|
+
self.__dict__.pop("_initing", None)
|
|
714
772
|
if not self._seekable:
|
|
715
773
|
raise OSError(errno.EINVAL, "not a seekable stream")
|
|
716
774
|
if whence == 0:
|
|
@@ -1128,7 +1186,7 @@ if find_spec("httpx"):
|
|
|
1128
1186
|
elif urlopen is None:
|
|
1129
1187
|
if _httpx_urlopen_async is None:
|
|
1130
1188
|
if "__del__" not in AsyncClient.__dict__:
|
|
1131
|
-
|
|
1189
|
+
setattr(AsyncClient, "__del__", lambda self: run_async(self.aclose()))
|
|
1132
1190
|
def async_stream(
|
|
1133
1191
|
method,
|
|
1134
1192
|
url,
|
|
@@ -1197,4 +1255,5 @@ if find_spec("httpx"):
|
|
|
1197
1255
|
__all__.append("HttpxFileReader")
|
|
1198
1256
|
__all__.append("AsyncHttpxFileReader")
|
|
1199
1257
|
|
|
1258
|
+
# TODO: 增加 blacksheep 的 HTTPFileReader
|
|
1200
1259
|
# TODO: 设计实现一个 HTTPFileWriter,用于实现上传,关闭后视为上传完成
|
|
@@ -0,0 +1,7 @@
|
|
|
1
|
+
LICENSE,sha256=o5242_N2TgDsWwFhPn7yr8YJNF7XsJM5NxUMtcT97bc,1100
|
|
2
|
+
httpfile/__init__.py,sha256=aU9cp4nBpCxPT49UWb1VFukYJMlo38AESouioBk3uYk,41004
|
|
3
|
+
httpfile/py.typed,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
|
|
4
|
+
python_httpfile-0.0.4.2.dist-info/LICENSE,sha256=o5242_N2TgDsWwFhPn7yr8YJNF7XsJM5NxUMtcT97bc,1100
|
|
5
|
+
python_httpfile-0.0.4.2.dist-info/METADATA,sha256=St2htsaH5qwPmBF6EGhlnVfyIx1KsusYCkgeQ6DTq1Y,1522
|
|
6
|
+
python_httpfile-0.0.4.2.dist-info/WHEEL,sha256=FMvqSimYX_P7y0a7UY-_Mc83r5zkBZsCYPm7Lr0Bsq4,88
|
|
7
|
+
python_httpfile-0.0.4.2.dist-info/RECORD,,
|
|
@@ -1,7 +0,0 @@
|
|
|
1
|
-
LICENSE,sha256=o5242_N2TgDsWwFhPn7yr8YJNF7XsJM5NxUMtcT97bc,1100
|
|
2
|
-
httpfile/__init__.py,sha256=PAqvhrEAfTEzVSZ7wbLrPplYX-8G1epkW7MZt2sWWaw,38657
|
|
3
|
-
httpfile/py.typed,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
|
|
4
|
-
python_httpfile-0.0.4.dist-info/LICENSE,sha256=o5242_N2TgDsWwFhPn7yr8YJNF7XsJM5NxUMtcT97bc,1100
|
|
5
|
-
python_httpfile-0.0.4.dist-info/METADATA,sha256=1CtTQ_EoeIP9eVYlevzlEBdA9D26S9pHfZmdTOnXB0Q,1520
|
|
6
|
-
python_httpfile-0.0.4.dist-info/WHEEL,sha256=FMvqSimYX_P7y0a7UY-_Mc83r5zkBZsCYPm7Lr0Bsq4,88
|
|
7
|
-
python_httpfile-0.0.4.dist-info/RECORD,,
|
|
File without changes
|
|
File without changes
|