
    6pjl6                        S SK r S SKrS SKrS SKrS SKJr  S SKJrJrJ	r	  S SK
JrJrJr  S SKJr  S SKJr  \" 5       rS rS rS	\4S
 jrS	\4S jrS	\4S jrS\S	\4S jrS\S	\4S jrS rSS\SS4S jrS\\\\\4   S	\4S jr   S S\\\\\4   S\\   S\\   S\\    S	\!4
S jjr"   S S\\\4   S\S\\   S\\    S	\!4
S jjr#    S!S\\\\\4   S\\   S\S\\   S\\    S	\!4S jjr$S\S	\ 4S jr%g)"    N)Path)Errorcopy2copystat)BinaryIOOptionalUnion)urlparse)
get_loggerc                 $   [         R                  " U 5      nUR                  nUR                  nUc  Ub  gUR                  (       d  / OUR                  nU(       a  US   S;   a  UR                  S5      OU  [        U5      S:X  a
  US   S;   a  gg)zto decide if a func could receive dict inputs or not

Args:
    func (class): the target function to be inspected

Returns:
    bool: if func only has one arg ``input`` or ``inputs``, return True, else return False
Fr   )selfcls   )inputinputsT)inspectgetfullargspecvarargsvarkwargspoplen)funcfull_args_specr   r   r   s        W/var/www/html/pdf-tiff/venv/lib/python3.13/site-packages/modelscope/utils/file_utils.pyfunc_receive_dict_inputsr      s     ++D1N$$G  EO#((2n.A.ADT!W7DHHQKd
4yA~$q'%88    c                      [         R                  R                  [        R                  " 5       R                  SSS5      5      n U $ )z)
default base dir: '~/.cache/modelscope'
z.cache
modelscopehub)ospath
expanduserr   homejoinpath)default_cache_dirs    r    get_default_modelscope_cache_dirr'   )   s9     **499;+?+?,,' (r   returnc                  z    [         R                  R                  [         R                  " S[	        5       5      5      $ )z}Get modelscope cache dir, default location or
   setting with MODELSCOPE_CACHE

Returns:
    str: the modelscope cache root.
MODELSCOPE_CACHE)r!   r"   r#   getenvr'    r   r   get_modelscope_cache_dirr-   2   s0     77
		$&F&HIK Kr   c                  R    [         R                  R                  [        5       S5      $ )zOGet model cache root path.

Returns:
    str: the modelscope model cache root.
modelsr!   r"   joinr-   r,   r   r   get_model_cache_rootr2   =   s     77<<02H==r   c                  R    [         R                  R                  [        5       S5      $ )zGet dataset raw file cache root path.
if `MODELSCOPE_CACHE` is set, return `MODELSCOPE_CACHE/datasets`,
else return `~/.cache/modelscope/hub/datasets`

Returns:
    str: the modelscope dataset raw file cache root.
datasetsr0   r,   r   r   get_dataset_cache_rootr5   F   s     77<<02J??r   
dataset_idc                 d    [        5       nU c  U$ [        R                  R                  XS-   5      $ )zGet the dataset_id's path.
   dataset_cache_root/dataset_id.

Args:
    dataset_id (str): The dataset id.

Returns:
    str: The dataset_id's cache root path.
/)r5   r!   r"   r1   )r6   dataset_roots     r   get_dataset_cache_dirr:   Q   s5     *+L%-< (277<<3&4( (r   model_idc                 d    [        5       nU c  U$ [        R                  R                  XS-   5      $ )zcache dir precedence:
    function parameter > environment > ~/.cache/modelscope/hub/model_id

Args:
    model_id (str, optional): The model id.

Returns:
    str: the model_id dir if model_id not None, otherwise cache root dir.
r8   )r2   r!   r"   r1   )r;   	root_paths     r   get_model_cache_dirr>   `   s4     %&I (9 #bggllc>/# #r   c                 t    [        U S5       nUR                  5       nS S S 5        U$ ! , (       d  f       W$ = f)Nr)openread)r"   ftexts      r   	read_filerE   o   s/    	dCAvvx 
K 
Ks   (
7Fc           
         [         R                  " U 5      nUb	  U" X5      nO
[        5       n[         R                  " XS9  / n	U GH\  n
X;   a  M  [         R                  R                  X
5      n[         R                  R                  X5      n [         R                  R                  U5      (       a  [         R                  " U5      nU(       a'  [         R                  " X5        [        XU(       + S9  M  [         R                  R                  U5      (       d	  U(       a  M  [         R                  R                  U5      (       a  [        UUUUUUS9  GM  U" X5        GM  [         R                  R                  U5      (       a  [        UUUUUUS9  GMT  U" X5        GM_      [        X5        U	(       a  [        U	5      eU$ ! [         a*  nU	R                  UR                  S   5         SnAGM  SnAf[          a(  nU	R#                  X[%        U5      45         SnAGM  SnAff = f! [          a4  n['        USS5      c  U	R#                  X[%        U5      45         SnANSnAff = f)z7copy from py37 shutil. add the parameter dirs_exist_ok.N)exist_ok)follow_symlinks)dirs_exist_okr   winerror)r!   listdirsetmakedirsr"   r1   islinkreadlinksymlinkr   existsisdircopytree_py37r   extendr   OSErrorappendstrgetattr)srcdstsymlinksignorecopy_functionignore_dangling_symlinksrI   namesignored_nameserrorsnamesrcnamedstnamelinktoerrwhys                   r   rS   rS   v   s    JJsOEs*KK,F '',,s)'',,s)(	8ww~~g&&W- JJv/W8|L 77>>&116N ww}}W--%##$")*79 &g7w''!"/1 g/O \0
 FmJ  	'MM#((1+&& 	8MM7SX677	8  03
D)1MM3SX./0s[   A&G7+G$2GG$2GG'H- 
H*G55H*H%%H*-
I+7*I&&I+file_path_or_objc                    [        U [        [        45      (       a%  [        U 5      nUR                  5       R                  $ [        U [
        5      (       a  [        U 5      $ [        U [        R                  5      (       aS  U R                  5       nU R                  S[        R                  5        U R                  5       nU R                  U5        U$ [        S5      e)Nr   zCUnsupported type: must be string, Path, bytes, or io.BufferedIOBase)
isinstancerW   r   statst_sizebytesr   ioBufferedIOBasetellseekr!   SEEK_END	TypeError)rh   	file_pathcurrent_positionsizes       r   get_file_sizerw      s    "S$K00)*	~~'''	$e	,	,#$$	$b&7&7	8	8+002a-$$&./Q
 	
r   buffer_size_mb	tqdm_descdisable_tqdmc           
         SSK Jn  [        U 5      nUS:  aS  SnSn[        U [        [
        45      (       a.  [        U [
        5      (       a  U O
[        U 5      nUR                  nSU S3nUS-  S-  n[        R                  " 5       n	U" USS	S	S
UUS9n
[        U [        [
        45      (       a  Sn[        U S5       nUR                  U5      =n(       aS  U	R                  U5        U[        U5      -  nU
R                  [        U5      5        UR                  U5      =n(       a  MS  SSS5        U	R                  5       n	X:w  a  [        R                  SU SU SU  35        UnGOz[        U [         5      (       aH  U	R                  U 5        U	R                  5       n	U
R                  [        U 5      5        [        U 5      nGO[        U ["        R$                  5      (       a  SnU R'                  S[(        R*                  5        U R                  U5      =n(       aS  U	R                  U5        U[        U5      -  nU
R                  [        U5      5        U R                  U5      =n(       a  MS  U	R                  5       n	U R'                  S[(        R*                  5        X:w  a  [        R                  SU SU SU  35        UnOU
R-                  5         [/        S5      eU
R-                  5         U U	US.$ ! , (       d  f       GN= f)aa  Compute SHA256 hash for a file path, bytes, or file-like object.

Args:
    file_path_or_obj: File path, bytes, or file-like object.
    buffer_size_mb: Read buffer size in MB. Default 16MB.
    tqdm_desc: Progress bar description.
    disable_tqdm: Whether to disable progress bar.

Returns:
    dict with keys: file_path_or_obj, file_hash, file_size.
r   tqdmi   @Fz
Large Filez[Validating Hash for ]   TB)totalinitial
unit_scaledynamic_ncolsunitdescdisablerbN4File size changed during hash computation: declared  bytes, actually hashed % bytes. File may have been modified: z5Input must be str, Path, bytes or a io.BufferedIOBaserh   	file_hash	file_size)	tqdm.autor}   rw   rj   rW   r   rb   hashlibsha256rA   rB   updater   	hexdigestloggerwarningrm   rn   ro   rq   r!   SEEK_SETclose
ValueError)rh   rx   ry   rz   r}   declared_sizerb   r"   buffer_sizer   progressbytes_hashedrC   
byte_chunkr   s                  r   get_file_hashr      s   " !"23M))&d44'1 $(( ((#-12B-C 99D+D63	 4'$.K IH "S$K00"D)Q !{ 33*3  ,J/J0 !"{ 33*3 *
 '')	(NN)?*B<. Q00@/ACD !		$e	,	,)*'')	,-.()		$b&7&7	8	8a-,11+>>j>Z(C
O+LOOC
O, -11+>>j> '')	a-(NN)?*B<. Q00@/ACD !	 	CE 	E NN - U *)s   =A*K88
Lrt   c           
        ^ ^^^ SSK nSSKnSSKJn  [	        T 5      m [
        R                  R                  T 5      nUS-  S-  mUR                  SS9mS/mUUU U4S jnUR                  USS	9n	U	R                  5         [        R                  " 5       n
SnU" UUUSS
SSS9n TR                  5       nUc  O;U
R                  U5        U[        U5      -  nUR                  [        U5      5        MO  U	R!                  5         UR#                  5         TS   b  TS   eX:w  a  [$        R'                  SU SU ST  35        T U
R)                  5       US.$ )a   Compute SHA256 with async I/O double-buffering for high-latency storage.

Uses a producer-consumer pattern: a background thread reads file chunks
into a bounded queue while the main thread computes the hash. This
overlaps I/O latency with CPU computation.
r   Nr|   r      )maxsizec                  4  >  [        TS5       n  U R                  T5      nU(       d  OTR                  U5        M,  S S S 5        TR                  S 5        g ! , (       d  f       N = f! [         a  nUTS'    S nAN7S nAff = f! TR                  S 5        f = f)Nr   r   )rA   rB   put	Exception)rC   chunker   chunk_queuert   
read_errors      r   	_producer'_get_file_hash_async.<locals>._producerF  s    
	"i&!FF;/E OOE*	  ' OOD! '&  	JqM	 OOD!sK   A( .AA( 
A%!A( $B %A( (
B2A<7B <BB BT)targetdaemonr   )r   r   r   r   r   r   unit_divisorr   r   r   r   )queue	threadingr   r}   rW   r!   r"   getsizeQueueThreadstartr   r   getr   r   r1   r   r   r   r   )rt   rx   ry   rz   r   r   r}   r   r   reader_threadr   r   r   r   r   r   r   s   `             @@@r   _get_file_hash_asyncr   .  ss    IIGGOOI.M 4'$.K++a+(KJ" " $$Id$CM ILH !=E
"E
#  NN!} m$%&>|n M,,5;8	9 &((*! r   async_threshold_mbc                     [        U [        [        45      (       a?  [        R                  R                  [        U 5      5      nXRS-  S-  :  a  [        U UUUS9$ [        U UUUS9$ )a  Compute SHA256 hash with automatic optimization for large files.

For file paths larger than async_threshold_mb, uses async double-buffered
I/O to overlap disk reads with hash computation. For smaller files or
non-path inputs (bytes, BinaryIO), falls back to synchronous hashing.

Args:
    file_path_or_obj: File path, bytes, or file-like object.
    buffer_size_mb: Read buffer size in MB. Default 16MB for NAS optimization.
    async_threshold_mb: File size threshold for async mode. Default 32MB.
    tqdm_desc: Progress bar description.
    disable_tqdm: Whether to disable progress bar.

Returns:
    dict with keys: file_path_or_obj, file_hash, file_size.
r   )rx   ry   rz   )rj   rW   r   r!   r"   r   r   r   )rh   rx   r   ry   rz   r   s         r   compute_file_hashr   }  sr    0 "S$K00GGOOC(8$9:	T1D88' -#)	  %!	 r   url_or_filenamec                     [        U 5      R                  S:H  =(       a$    [        R                  R	                  U 5      (       + $ )z-
Check if a given string is a relative path.
 )r
   schemer!   r"   isabs)r   s    r   is_relative_pathr     s:     2& M.0ggmmO.L*LMr   )   [Calculating]T)r       r   T)&r   r   rn   r!   pathlibr   shutilr   r   r   typingr   r   r	   urllib.parser
   modelscope.utils.loggerr   r   r   r'   rW   r-   r2   r5   r:   r>   rE   rS   rm   intrw   booldictr   r   r   r   r,   r   r   <module>r      s     	 	  ) ) , , ! .	0K# K>c >@ @(c (c (## ## # ! %+0 %FR
E#tUH*D$E 
# 
( %'.#'	ZCuh67ZSMZ }Z 4.	Z
 
Z~ .#'	LS$YLL }L 4.	L
 
Lb %' .#'(Cuh67(SM( ( }	(
 4.( 
(VMc Md Mr   