@@ -198,11 +198,13 @@ def download(
198
198
msg = 'No Stages object is associated with this object.' ,
199
199
)
200
200
201
- return self ._stages .download (
201
+ return self ._stages .download_file (
202
202
self .path , local_path = local_path ,
203
203
overwrite = overwrite , encoding = encoding ,
204
204
)
205
205
206
+ download_file = download
207
+
206
208
def remove (self ) -> None :
207
209
"""Delete the stage file."""
208
210
if self ._stages is None :
@@ -230,7 +232,7 @@ def removedirs(self) -> None:
230
232
231
233
self ._stages .removedirs (self .path )
232
234
233
- def rename (self , new_path : PathLike , * , overwrite : bool = False ) -> StagesObject :
235
+ def rename (self , new_path : PathLike , * , overwrite : bool = False ) -> None :
234
236
"""
235
237
Move the stage file to a new location.
236
238
@@ -246,7 +248,10 @@ def rename(self, new_path: PathLike, *, overwrite: bool = False) -> StagesObject
246
248
raise ManagementError (
247
249
msg = 'No Stages object is associated with this object.' ,
248
250
)
249
- return self ._stages .rename (self .path , new_path , overwrite = overwrite )
251
+ out = self ._stages .rename (self .path , new_path , overwrite = overwrite )
252
+ self .name = out .name
253
+ self .path = out .path
254
+ return None
250
255
251
256
def exists (self ) -> bool :
252
257
"""Does the file / folder exist?"""
@@ -384,7 +389,7 @@ def open(
384
389
return StagesObjectTextWriter ('' , self , stage_path )
385
390
386
391
if 'r' in mode :
387
- content = self .download (stage_path )
392
+ content = self .download_file (stage_path )
388
393
if isinstance (content , bytes ):
389
394
if 'b' in mode :
390
395
return StagesObjectBytesReader (content )
@@ -400,7 +405,7 @@ def open(
400
405
401
406
def upload_file (
402
407
self ,
403
- local_path : PathLike ,
408
+ local_path : Union [ PathLike , TextIO , BinaryIO ] ,
404
409
stage_path : PathLike ,
405
410
* ,
406
411
overwrite : bool = False ,
@@ -410,15 +415,17 @@ def upload_file(
410
415
411
416
Parameters
412
417
----------
413
- local_path : Path or str
414
- Path to the local file
418
+ local_path : Path or str or file-like
419
+ Path to the local file or an open file object
415
420
stage_path : Path or str
416
421
Path to the stage file
417
422
overwrite : bool, optional
418
423
Should the ``stage_path`` be overwritten if it exists already?
419
424
420
425
"""
421
- if not os .path .isfile (local_path ):
426
+ if isinstance (local_path , (TextIO , BinaryIO )):
427
+ pass
428
+ elif not os .path .isfile (local_path ):
422
429
raise IsADirectoryError (f'local path is not a file: { local_path } ' )
423
430
424
431
if self .exists (stage_path ):
@@ -427,6 +434,8 @@ def upload_file(
427
434
428
435
self .remove (stage_path )
429
436
437
+ if isinstance (local_path , (TextIO , BinaryIO )):
438
+ return self ._upload (local_path , stage_path , overwrite = overwrite )
430
439
return self ._upload (open (local_path , 'rb' ), stage_path , overwrite = overwrite )
431
440
432
441
def upload_folder (
@@ -727,7 +736,7 @@ def listdir(
727
736
728
737
raise NotADirectoryError (f'stage path is not a directory: { stage_path } ' )
729
738
730
- def download (
739
+ def download_file (
731
740
self ,
732
741
stage_path : PathLike ,
733
742
local_path : Optional [PathLike ] = None ,
@@ -774,6 +783,41 @@ def download(
774
783
775
784
return out
776
785
786
+ def download_folder (
787
+ self ,
788
+ stage_path : PathLike ,
789
+ local_path : PathLike = '.' ,
790
+ * ,
791
+ overwrite : bool = False ,
792
+ ) -> None :
793
+ """
794
+ Download a Stages folder to a local directory.
795
+
796
+ Parameters
797
+ ----------
798
+ stage_path : Path or str
799
+ Path to the stage file
800
+ local_path : Path or str
801
+ Path to local directory target location
802
+ overwrite : bool, optional
803
+ Should an existing directory / files be overwritten if they exist?
804
+
805
+ """
806
+ if local_path is not None and not overwrite and os .path .exists (local_path ):
807
+ raise OSError (
808
+ 'target directory already exists; '
809
+ 'use overwrite=True to replace' ,
810
+ )
811
+ if not self .is_dir (stage_path ):
812
+ raise NotADirectoryError (f'stage path is not a directory: { stage_path } ' )
813
+
814
+ for f in self .listdir (stage_path , recursive = True ):
815
+ if self .is_dir (f ):
816
+ continue
817
+ target = os .path .normpath (os .path .join (local_path , f ))
818
+ os .makedirs (os .path .dirname (target ), exist_ok = True )
819
+ self .download_file (f , target , overwrite = overwrite )
820
+
777
821
def remove (self , stage_path : PathLike ) -> None :
778
822
"""
779
823
Delete a stage location.
0 commit comments