Ë
    Z²jÿ€  ã                   óê  — d Z ddlZddlZddlmZ ddlmZ ddlmZ ddl	m
Z
 ddlmZmZ dd	lmZ d
dlmZ d
dlmZ d
dlmZ  ej,                  e«      Ze
d   ZdgZ ed¬«       G d„ d«      «       Z ed¬«       G d„ d«      «       Z ed¬«       G d„ d«      «       Z ed¬«       G d„ d«      «       Z ed¬«       G d„ d«      «       Zd&de ez  dz  defd„Z!dedefd „Z"d!e#de fd"„Z$d#ed$e ddfd%„Z%y)'z4Contains utilities to manage the HF cache directory.é    N)Údefaultdict)Ú	dataclass)ÚPath)ÚLiteral)ÚCacheNotFoundÚCorruptedCacheExceptioné   )ÚHF_HUB_CACHEé   )Úlogging)Úformat_timesince)Útabulate)ÚmodelÚdatasetÚspacez	.DS_StoreT)Úfrozenc                   ó�   — e Zd ZU dZeed<   eed<   eed<   eed<   eed<   eed<   e	defd	„«       Z
e	defd
„«       Ze	defd„«       Zy)ÚCachedFileInfoaò  Frozen data structure holding information about a single cached file.

    Args:
        file_name (`str`):
            Name of the file. Example: `config.json`.
        file_path (`Path`):
            Path of the file in the `snapshots` directory. The file path is a symlink
            referring to a blob in the `blobs` folder.
        blob_path (`Path`):
            Path of the blob file. This is equivalent to `file_path.resolve()`.
        size_on_disk (`int`):
            Size of the blob file in bytes.
        blob_last_accessed (`float`):
            Timestamp of the last time the blob file has been accessed (from any
            revision).
        blob_last_modified (`float`):
            Timestamp of the last time the blob file has been modified/created.

    > [!WARNING]
    > `blob_last_accessed` and `blob_last_modified` reliability can depend on the OS you
    > are using. See [python documentation](https://docs.python.org/3/library/os.html#os.stat_result)
    > for more details.
    Ú	file_nameÚ	file_pathÚ	blob_pathÚsize_on_diskÚblob_last_accessedÚblob_last_modifiedÚreturnc                 ó,   — t        | j                  «      S )zº
        (property) Timestamp of the last time the blob file has been accessed (from any
        revision), returned as a human-readable string.

        Example: "2 weeks ago".
        )r   r   ©Úselfs    úc/var/www/html/ia-enhanced/venv/lib/python3.12/site-packages/huggingface_hub/utils/_cache_manager.pyÚblob_last_accessed_strz%CachedFileInfo.blob_last_accessed_strI   ó   € ô   × 7Ñ 7Ó8Ð8ó    c                 ó,   — t        | j                  «      S )z¦
        (property) Timestamp of the last time the blob file has been modified, returned
        as a human-readable string.

        Example: "2 weeks ago".
        )r   r   r   s    r   Úblob_last_modified_strz%CachedFileInfo.blob_last_modified_strS   r!   r"   c                 ó,   — t        | j                  «      S )zi
        (property) Size of the blob file as a human-readable string.

        Example: "42.2K".
        ©Ú_format_sizer   r   s    r   Úsize_on_disk_strzCachedFileInfo.size_on_disk_str]   ó   € ô ˜D×-Ñ-Ó.Ð.r"   N)Ú__name__Ú
__module__Ú__qualname__Ú__doc__ÚstrÚ__annotations__r   ÚintÚfloatÚpropertyr    r$   r(   © r"   r   r   r   '   sy   … ñð0 ƒNØƒOØƒOØÓàÓØÓàð9¨ò 9ó ð9ð ð9¨ò 9ó ð9ð ð/ #ò /ó ñ/r"   r   c                   óœ   — e Zd ZU dZeed<   eed<   eed<   ee	   ed<   ee   ed<   e
ed<   edefd	„«       Zedefd
„«       Zedefd„«       Zy)ÚCachedRevisionInfoa.  Frozen data structure holding information about a revision.

    A revision correspond to a folder in the `snapshots` folder and is populated with
    the exact tree structure as the repo on the Hub but contains only symlinks. A
    revision can be either referenced by 1 or more `refs` or be "detached" (no refs).

    Args:
        commit_hash (`str`):
            Hash of the revision (unique).
            Example: `"9338f7b671827df886678df2bdd7cc7b4f36dffd"`.
        snapshot_path (`Path`):
            Path to the revision directory in the `snapshots` folder. It contains the
            exact tree structure as the repo on the Hub.
        files: (`frozenset[CachedFileInfo]`):
            Set of [`~CachedFileInfo`] describing all files contained in the snapshot.
        refs (`frozenset[str]`):
            Set of `refs` pointing to this revision. If the revision has no `refs`, it
            is considered detached.
            Example: `{"main", "2.4.0"}` or `{"refs/pr/1"}`.
        size_on_disk (`int`):
            Sum of the blob file sizes that are symlink-ed by the revision.
        last_modified (`float`):
            Timestamp of the last time the revision has been created/modified.

    > [!WARNING]
    > `last_accessed` cannot be determined correctly on a single revision as blob files
    > are shared across revisions.

    > [!WARNING]
    > `size_on_disk` is not necessarily the sum of all file sizes because of possible
    > duplicated files. Besides, only blobs are taken into account, not the (negligible)
    > size of folders and symlinks.
    Úcommit_hashÚsnapshot_pathr   ÚfilesÚrefsÚlast_modifiedr   c                 ó,   — t        | j                  «      S )z¥
        (property) Timestamp of the last time the revision has been modified, returned
        as a human-readable string.

        Example: "2 weeks ago".
        ©r   r:   r   s    r   Úlast_modified_strz$CachedRevisionInfo.last_modified_str“   ó   € ô   × 2Ñ 2Ó3Ð3r"   c                 ó,   — t        | j                  «      S ©zn
        (property) Sum of the blob file sizes as a human-readable string.

        Example: "42.2K".
        r&   r   s    r   r(   z#CachedRevisionInfo.size_on_disk_str�   r)   r"   c                 ó,   — t        | j                  «      S )zC
        (property) Total number of files in the revision.
        )Úlenr8   r   s    r   Únb_fileszCachedRevisionInfo.nb_files¦   s   € ô
 �4—:‘:‹Ðr"   N)r*   r+   r,   r-   r.   r/   r   r0   Ú	frozensetr   r1   r2   r=   r(   rC   r3   r"   r   r5   r5   g   s†   … ñ ðD ÓØÓØÓØ�^Ñ$Ó$Ø
�C‰.ÓàÓàð4 3ò 4ó ð4ð ð/ #ò /ó ð/ð ð˜#ò ó ñr"   r5   c                   óà   — e Zd ZU dZeed<   eed<   eed<   eed<   eed<   e	e
   ed<   eed<   eed	<   ed
efd„«       Zed
efd„«       Zed
efd„«       Zed
efd„«       Zed
eee
f   fd„«       Zy)ÚCachedRepoInfoaF  Frozen data structure holding information about a cached repository.

    Args:
        repo_id (`str`):
            Repo id of the repo on the Hub. Example: `"google/fleurs"`.
        repo_type (`Literal["dataset", "model", "space"]`):
            Type of the cached repo.
        repo_path (`Path`):
            Local path to the cached repo.
        size_on_disk (`int`):
            Sum of the blob file sizes in the cached repo.
        nb_files (`int`):
            Total number of blob files in the cached repo.
        revisions (`frozenset[CachedRevisionInfo]`):
            Set of [`~CachedRevisionInfo`] describing all revisions cached in the repo.
        last_accessed (`float`):
            Timestamp of the last time a blob file of the repo has been accessed.
        last_modified (`float`):
            Timestamp of the last time a blob file of the repo has been modified/created.

    > [!WARNING]
    > `size_on_disk` is not necessarily the sum of all revisions sizes because of
    > duplicated files. Besides, only blobs are taken into account, not the (negligible)
    > size of folders and symlinks.

    > [!WARNING]
    > `last_accessed` and `last_modified` reliability can depend on the OS you are using.
    > See [python documentation](https://docs.python.org/3/library/os.html#os.stat_result)
    > for more details.
    Úrepo_idÚ	repo_typeÚ	repo_pathr   rC   Ú	revisionsÚlast_accessedr:   r   c                 ó,   — t        | j                  «      S )zŸ
        (property) Last time a blob file of the repo has been accessed, returned as a
        human-readable string.

        Example: "2 weeks ago".
        )r   rK   r   s    r   Úlast_accessed_strz CachedRepoInfo.last_accessed_strÙ   r>   r"   c                 ó,   — t        | j                  «      S )zŸ
        (property) Last time a blob file of the repo has been modified, returned as a
        human-readable string.

        Example: "2 weeks ago".
        r<   r   s    r   r=   z CachedRepoInfo.last_modified_strã   r>   r"   c                 ó,   — t        | j                  «      S r@   r&   r   s    r   r(   zCachedRepoInfo.size_on_disk_strí   r)   r"   c                 ó8   — | j                   › d| j                  › �S )z9Canonical `type/id` identifier used across cache tooling.ú/)rH   rG   r   s    r   Úcache_idzCachedRepoInfo.cache_idö   s   € ð —.‘.Ð!  4§<¡< .Ð1Ð1r"   c                 ój   — | j                   D ��ci c]  }|j                  D ]  }||“Œ Œ c}}S c c}}w )zQ
        (property) Mapping between `refs` and revision data structures.
        )rJ   r9   )r   ÚrevisionÚrefs      r   r9   zCachedRepoInfo.refsû   s0   € ð
 /3¯n©n×V (ÈÏÉÒVÀ��X‘ÐV�ÓVÐVùÓVs   �/N)r*   r+   r,   r-   r.   r/   ÚREPO_TYPE_Tr   r0   rD   r5   r1   r2   rM   r=   r(   rR   Údictr9   r3   r"   r   rF   rF   ®   sÏ   … ñð> ƒLØÓØƒOØÓØƒMØÐ+Ñ,Ó,àÓØÓàð4 3ò 4ó ð4ð ð4 3ò 4ó ð4ð ð/ #ò /ó ð/ð ð2˜#ò 2ó ð2ð ðW�d˜3Ð 2Ð2Ñ3ò Wó ñWr"   rF   c                   óz   — e Zd ZU dZeed<   ee   ed<   ee   ed<   ee   ed<   ee   ed<   ede	fd„«       Z
dd
„Zy	)ÚDeleteCacheStrategyaÒ  Frozen data structure holding the strategy to delete cached revisions.

    This object is not meant to be instantiated programmatically but to be returned by
    [`~utils.HFCacheInfo.delete_revisions`]. See documentation for usage example.

    Args:
        expected_freed_size (`float`):
            Expected freed size once strategy is executed.
        blobs (`frozenset[Path]`):
            Set of blob file paths to be deleted.
        refs (`frozenset[Path]`):
            Set of reference file paths to be deleted.
        repos (`frozenset[Path]`):
            Set of entire repo paths to be deleted.
        snapshots (`frozenset[Path]`):
            Set of snapshots to be deleted (directory of symlinks).
    Úexpected_freed_sizeÚblobsr9   ÚreposÚ	snapshotsr   c                 ó,   — t        | j                  «      S )zt
        (property) Expected size that will be freed as a human-readable string.

        Example: "42.2K".
        )r'   rZ   r   s    r   Úexpected_freed_size_strz+DeleteCacheStrategy.expected_freed_size_str  s   € ô ˜D×4Ñ4Ó5Ð5r"   Nc                 ó:  — | j                   D ]  }t        |d¬«       Œ | j                  D ]  }t        |d¬«       Œ | j                  D ]  }t        |d¬«       Œ | j                  D ]  }t        |d¬«       Œ t
        j                  d| j                  › d�«       y)	aŠ  Execute the defined strategy.

        > [!WARNING]
        > If this method is interrupted, the cache might get corrupted. Deletion order is
        > implemented so that references and symlinks are deleted before the actual blob
        > files.

        > [!WARNING]
        > This method is irreversible. If executed, cached files are erased and must be
        > downloaded again.
        Úrepo)Ú	path_typeÚsnapshotrU   ÚblobzCache deletion done. Saved ú.N)r\   Ú_try_delete_pathr]   r9   r[   ÚloggerÚinfor_   )r   Úpaths     r   ÚexecutezDeleteCacheStrategy.execute&  s�   € ð" —J‘Jò 	5ˆDÜ˜T¨VÖ4ð	5ð —N‘Nò 	9ˆDÜ˜T¨ZÖ8ð	9ð —I‘Iò 	4ˆDÜ˜T¨UÖ3ð	4ð —J‘Jò 	5ˆDÜ˜T¨VÖ4ð	5ô 	�‰Ð1°$×2NÑ2NÐ1OÈqÐQÕRr"   )r   N)r*   r+   r,   r-   r0   r/   rD   r   r2   r.   r_   rj   r3   r"   r   rY   rY     sV   … ñð$ ÓØ�T‰?ÓØ
�D‰/ÓØ�T‰?ÓØ˜‰Óàð6¨ò 6ó ð6ô Sr"   rY   c                   óx   — e Zd ZU dZeed<   ee   ed<   ee	   ed<   e
defd„«       Zdedefd„Zd	d
œdedefd„Zy)ÚHFCacheInfoas  Frozen data structure holding information about the entire cache-system.

    This data structure is returned by [`scan_cache_dir`] and is immutable.

    Args:
        size_on_disk (`int`):
            Sum of all valid repo sizes in the cache-system.
        repos (`frozenset[CachedRepoInfo]`):
            Set of [`~CachedRepoInfo`] describing all valid cached repos found on the
            cache-system while scanning.
        warnings (`list[CorruptedCacheException]`):
            List of [`~CorruptedCacheException`] that occurred while scanning the cache.
            Those exceptions are captured so that the scan can continue. Corrupted repos
            are skipped from the scan.

    > [!WARNING]
    > Here `size_on_disk` is equal to the sum of all repo sizes (only blobs). However if
    > some cached repos are corrupted, their sizes are not taken into account.
    r   r\   Úwarningsr   c                 ó,   — t        | j                  «      S )z‹
        (property) Sum of all valid repo sizes in the cache-system as a human-readable
        string.

        Example: "42.2K".
        r&   r   s    r   r(   zHFCacheInfo.size_on_disk_strc  s   € ô ˜D×-Ñ-Ó.Ð.r"   rJ   c                 ó˜  — t        |«      }t        t         «      }| j                  D ]Q  }|j                  D ]@  }|j                  |v sŒ||   j                  |«       |j                  |j                  «       ŒB ŒS t        |«      dkD  r't        j                  ddj                  |«      › �«       t        «       }t        «       }t        «       }t        «       }	d}
|j                  «       D �]*  \  }}|j                  |z
  }t        |«      dk(  r+|j                  |j                  «       |
|j                  z  }
ŒO|D ]×  }|	j                  |j                  «       |j                  D ]#  }|j                  |j                  dz  |z  «       Œ% |j                   D ]y  }|j"                  |vsŒd}|D ]4  }|j                   D ]  }|j"                  |j"                  k(  sŒd} n |rŒ4 n |sŒP|j                  |j"                  «       |
|j                  z  }
Œ{ ŒÙ �Œ- t%        t'        |«      t'        |«      t'        |«      t'        |	«      |
¬«      S )a’  Prepare the strategy to delete one or more revisions cached locally.

        Input revisions can be any revision hash. If a revision hash is not found in the
        local cache, a warning is thrown but no error is raised. Revisions can be from
        different cached repos since hashes are unique across repos,

        Examples:
        ```py
        >>> from huggingface_hub import scan_cache_dir
        >>> cache_info = scan_cache_dir()
        >>> delete_strategy = cache_info.delete_revisions(
        ...     "81fd1d6e7847c99f5862c9fb81387956d99ec7aa"
        ... )
        >>> print(f"Will free {delete_strategy.expected_freed_size_str}.")
        Will free 7.9K.
        >>> delete_strategy.execute()
        Cache deletion done. Saved 7.9K.
        ```

        ```py
        >>> from huggingface_hub import scan_cache_dir
        >>> scan_cache_dir().delete_revisions(
        ...     "81fd1d6e7847c99f5862c9fb81387956d99ec7aa",
        ...     "e2983b237dccf3ab4937c97fa717319a9ca1a96d",
        ...     "6c0e6080953db56375760c0471a8c5f2929baf11",
        ... ).execute()
        Cache deletion done. Saved 8.6G.
        ```

        > [!WARNING]
        > `delete_revisions` returns a [`~utils.DeleteCacheStrategy`] object that needs to
        > be executed. The [`~utils.DeleteCacheStrategy`] is not meant to be modified but
        > allows having a dry run before actually executing the deletion.
        r   z,Revision(s) not found - cannot delete them: ú, r9   TF)r[   r9   r\   r]   rZ   )Úsetr   r\   rJ   r6   ÚaddÚremoverB   rg   ÚwarningÚjoinÚitemsrI   r   r7   r9   r8   r   rY   rD   )r   rJ   Úhashes_to_deleteÚrepos_with_revisionsra   rT   Údelete_strategy_blobsÚdelete_strategy_refsÚdelete_strategy_reposÚdelete_strategy_snapshotsÚ#delete_strategy_expected_freed_sizeÚaffected_repoÚrevisions_to_deleteÚother_revisionsÚrevision_to_deleterU   ÚfileÚis_file_aloneÚrev_files                      r   Údelete_revisionszHFCacheInfo.delete_revisionsm  sg  € ôF &)¨£^ÐäNYÔZ]ÓN^Ðà—J‘Jò 	BˆDØ ŸN™Nò B�Ø×'Ñ'Ð+;Ò;Ø(¨Ñ.×2Ñ2°8Ô<Ø$×+Ñ+¨H×,@Ñ,@ÕAñBð	Bô ÐÓ  1Ò$Ü�N‰NÐIÈ$Ï)É)ÐTdÓJeÐIfÐgÔhä+.«5ÐÜ*-«%ÐÜ+.«5ÐÜ/2«uÐ!Ø./Ð+à2F×2LÑ2LÓ2Nó #	UÑ.ˆMÐ.Ø+×5Ñ5Ð8KÑKˆOô �?Ó# qÒ(Ø%×)Ñ)¨-×*AÑ*AÔBØ3°}×7QÑ7QÑQÐ3Øð ':ò UÐ"à)×-Ñ-Ð.@×.NÑ.NÔOð .×2Ñ2ò U�CØ(×,Ñ,¨]×-DÑ-DÀvÑ-MÐPSÑ-SÕTðUð /×4Ñ4ò U�DØ—~‘~Ð-BÒBØ(,˜Ø(7ò &˜HØ,4¯N©Nò * Ø#'§>¡>°X×5GÑ5GÓ#GØ49 MÙ$)ð*ò $1Ù %ð&ò )Ø1×5Ñ5°d·n±nÔEØ?À4×CTÑCTÑTÑ?ñUòUð#	UôL #ÜÐ1Ó2ÜÐ/Ó0ÜÐ1Ó2ÜÐ 9Ó:Ø Cô
ð 	
r"   r   )Ú	verbosityr†   c                ó  — |dk(  r®t        t        | j                  d„ ¬«      D �cg c]  }|j                  |j                  |j
                  d›|j                  |j                  |j                  dj                  t        |j                  «      «      t        |j                  «      g‘Œ� c}g d¢¬«      S t        t        | j                  d„ ¬«      D ��cg c]œ  }t        |j                  d	„ ¬«      D ]  }|j                  |j                  |j                  |j
                  d›|j                  |j                  dj                  t        |j                  «      «      t        |j                  «      g‘Œ� Œž c}}g d
¢¬«      S c c}w c c}}w )a}  Generate a table from the [`HFCacheInfo`] object.

        Pass `verbosity=0` to get a table with a single row per repo, with columns
        "repo_id", "repo_type", "size_on_disk", "nb_files", "last_accessed", "last_modified", "refs", "local_path".

        Pass `verbosity=1` to get a table with a row per repo and revision (thus multiple rows can appear for a single repo), with columns
        "repo_id", "repo_type", "revision", "size_on_disk", "nb_files", "last_modified", "refs", "local_path".

        Example:
        ```py
        >>> from huggingface_hub.utils import scan_cache_dir

        >>> hf_cache_info = scan_cache_dir()
        HFCacheInfo(...)

        >>> print(hf_cache_info.export_as_table())
        REPO ID                                             REPO TYPE SIZE ON DISK NB FILES LAST_ACCESSED LAST_MODIFIED REFS LOCAL PATH
        --------------------------------------------------- --------- ------------ -------- ------------- ------------- ---- --------------------------------------------------------------------------------------------------
        roberta-base                                        model             2.7M        5 1 day ago     1 week ago    main ~/.cache/huggingface/hub/models--roberta-base
        suno/bark                                           model             8.8K        1 1 week ago    1 week ago    main ~/.cache/huggingface/hub/models--suno--bark
        t5-base                                             model           893.8M        4 4 days ago    7 months ago  main ~/.cache/huggingface/hub/models--t5-base
        t5-large                                            model             3.0G        4 5 weeks ago   5 months ago  main ~/.cache/huggingface/hub/models--t5-large

        >>> print(hf_cache_info.export_as_table(verbosity=1))
        REPO ID                                             REPO TYPE REVISION                                 SIZE ON DISK NB FILES LAST_MODIFIED REFS LOCAL PATH
        --------------------------------------------------- --------- ---------------------------------------- ------------ -------- ------------- ---- -----------------------------------------------------------------------------------------------------------------------------------------------------
        roberta-base                                        model     e2da8e2f811d1448a5b465c236feacd80ffbac7b         2.7M        5 1 week ago    main ~/.cache/huggingface/hub/models--roberta-base/snapshots/e2da8e2f811d1448a5b465c236feacd80ffbac7b
        suno/bark                                           model     70a8a7d34168586dc5d028fa9666aceade177992         8.8K        1 1 week ago    main ~/.cache/huggingface/hub/models--suno--bark/snapshots/70a8a7d34168586dc5d028fa9666aceade177992
        t5-base                                             model     a9723ea7f1b39c1eae772870f3b547bf6ef7e6c1       893.8M        4 7 months ago  main ~/.cache/huggingface/hub/models--t5-base/snapshots/a9723ea7f1b39c1eae772870f3b547bf6ef7e6c1
        t5-large                                            model     150ebc2c4b72291e770f58e6057481c8d2ed331a         3.0G        4 5 months ago  main ~/.cache/huggingface/hub/models--t5-large/snapshots/150ebc2c4b72291e770f58e6057481c8d2ed331a
        ```

        Args:
            verbosity (`int`, *optional*):
                The verbosity level. Defaults to 0.

        Returns:
            `str`: The table as a string.
        r   c                 ó   — | j                   S ©N©rI   ©ra   s    r   ú<lambda>z-HFCacheInfo.export_as_table.<locals>.<lambda>  ó
   € ÀDÇNÁN€ r"   )Úkeyz>12rp   )úREPO IDú	REPO TYPEúSIZE ON DISKúNB FILESÚLAST_ACCESSEDÚLAST_MODIFIEDÚREFSú
LOCAL PATH)ÚrowsÚheadersc                 ó   — | j                   S r‰   rŠ   r‹   s    r   rŒ   z-HFCacheInfo.export_as_table.<locals>.<lambda>   r�   r"   c                 ó   — | j                   S r‰   )r6   )rT   s    r   rŒ   z-HFCacheInfo.export_as_table.<locals>.<lambda>!  s   € ÐPX×PdÑPd€ r"   )r�   r�   ÚREVISIONr‘   r’   r”   r•   r–   )r   Úsortedr\   rG   rH   r(   rC   rM   r=   ru   r9   r.   rI   rJ   r6   r7   )r   r†   ra   rT   s       r   Úexport_as_tablezHFCacheInfo.export_as_tableÑ  s_  € ðP ˜Š>Üô !' t§z¡zÑ7RÔ Söð ð Ÿ™ØŸ™Ø×0Ñ0°Ð5ØŸ™Ø×.Ñ.Ø×.Ñ.ØŸ	™	¤&¨¯©Ó"3Ó4Ü˜DŸN™NÓ+ò	òò	ôð ô4 ô !' t§z¡zÑ7RÔ S÷ð Ü$*¨4¯>©>Ñ?dÔ$eòð !ð Ÿ™ØŸ™Ø ×,Ñ,Ø#×4Ñ4°SÐ9Ø ×)Ñ)Ø ×2Ñ2ØŸ	™	¤&¨¯©Ó"7Ó8Ü˜H×2Ñ2Ó3ò	ðð	óò	ôð ùò3ùó4s   ¥BFÃB!F
N)r*   r+   r,   r-   r0   r/   rD   rF   Úlistr   r2   r.   r(   rY   r…   r�   r3   r"   r   rl   rl   I  sr   … ñð( ÓØ�^Ñ$Ó$ØÐ*Ñ+Ó+àð/ #ò /ó ð/ðb
¨3ð b
Ð3Fó b
ðH 34ò \¨Cð \¸ô \r"   rl   Ú	cache_dirr   c                 ó4  — | €t         } t        | «      j                  «       j                  «       } | j	                  «       st        d| › d�| ¬«      ‚| j                  «       rt        d| › d�«      ‚t        «       }g }| j                  «       D ]=  }|j                  dk(  rŒ|j                  dk(  rŒ#	 |j                  t        |«      «       Œ? t        t!        |«      t#        d„ |D «       «      |¬	«      S # t        $ r}|j                  |«       Y d}~Œ†d}~ww xY w)
a‹  Scan the entire HF cache-system and return a [`~HFCacheInfo`] structure.

    Use `scan_cache_dir` in order to programmatically scan your cache-system. The cache
    will be scanned repo by repo. If a repo is corrupted, a [`~CorruptedCacheException`]
    will be thrown internally but captured and returned in the [`~HFCacheInfo`]
    structure. Only valid repos get a proper report.

    ```py
    >>> from huggingface_hub import scan_cache_dir

    >>> hf_cache_info = scan_cache_dir()
    HFCacheInfo(
        size_on_disk=3398085269,
        repos=frozenset({
            CachedRepoInfo(
                repo_id='t5-small',
                repo_type='model',
                repo_path=PosixPath(...),
                size_on_disk=970726914,
                nb_files=11,
                revisions=frozenset({
                    CachedRevisionInfo(
                        commit_hash='d78aea13fa7ecd06c29e3e46195d6341255065d5',
                        size_on_disk=970726339,
                        snapshot_path=PosixPath(...),
                        files=frozenset({
                            CachedFileInfo(
                                file_name='config.json',
                                size_on_disk=1197
                                file_path=PosixPath(...),
                                blob_path=PosixPath(...),
                            ),
                            CachedFileInfo(...),
                            ...
                        }),
                    ),
                    CachedRevisionInfo(...),
                    ...
                }),
            ),
            CachedRepoInfo(...),
            ...
        }),
        warnings=[
            CorruptedCacheException("Snapshots dir doesn't exist in cached repo: ..."),
            CorruptedCacheException(...),
            ...
        ],
    )
    ```

    You can also print a detailed report directly from the `hf` command line using:
    ```text
    > hf cache ls
    ID                          SIZE     LAST_ACCESSED LAST_MODIFIED REFS
    --------------------------- -------- ------------- ------------- -----------
    dataset/nyu-mll/glue          157.4M 2 days ago    2 days ago    main script
    model/LiquidAI/LFM2-VL-1.6B     3.2G 4 days ago    4 days ago    main
    model/microsoft/UserLM-8b      32.1G 4 days ago    4 days ago    main

    Done in 0.0s. Scanned 6 repo(s) for a total of 3.4G.
    Got 1 warning(s) while scanning. Use -vvv to print details.
    ```

    Args:
        cache_dir (`str` or `Path`, `optional`):
            Cache directory to cache. Defaults to the default HF cache directory.

    > [!WARNING]
    > Raises:
    >
    >     `CacheNotFound`
    >       If the cache directory does not exist.
    >
    >     [`ValueError`](https://docs.python.org/3/library/exceptions.html#ValueError)
    >       If the cache directory is a file, instead of a directory.

    Returns: a [`~HFCacheInfo`] object.
    NzCache directory not found: zM. Please use `cache_dir` argument or set `HF_HUB_CACHE` environment variable.)rŸ   z1Scan cache expects a directory but found a file: z.lockszCACHEDIR.TAGc              3   ó4   K  — | ]  }|j                   –— Œ y ­wr‰   )r   )Ú.0ra   s     r   ú	<genexpr>z!scan_cache_dir.<locals>.<genexpr>�  s   è ø€ Ò=¨t˜×*Õ*Ñ=ùó   ‚)r\   r   rm   )r
   r   Ú
expanduserÚresolveÚexistsr   Úis_fileÚ
ValueErrorrq   ÚiterdirÚnamerr   Ú_scan_cached_repor   Úappendrl   rD   Úsum)rŸ   r\   rm   rI   Úes        r   Úscan_cache_dirr°   0  s-  € ð` ÐÜ ˆ	ä�Y“×*Ñ*Ó,×4Ñ4Ó6€IØ×ÑÔÜØ)¨)¨ð  5Bð  CØô
ð 	
ð
 ×ÑÔÜØ?À	¸{ð  KXð  Yó
ð 	
ô "%£€EØ.0€HØ×&Ñ&Ó(ò ˆ	Ø�>‰>˜XÒ%ØØ�>‰>˜^Ò+Øð	Ø�I‰IÔ'¨	Ó2Õ3ðô Ü˜ÓÜÑ=°uÔ=Ó=Øôð øô 'ò 	Ø�O‰O˜A×Ñûð	ús   Â0C3Ã3	DÃ<DÄDrI   c                 óØ  ‡— | j                  «       st        d| › �«      ‚d| j                  vrt        d| › �«      ‚| j                  j                  dd¬«      \  }}|dd }|j	                  dd«      }|d	vrt        d
|› d| › d�«      ‚i Š| dz  }| dz  }|j                  «       r|j                  «       st        d|› �«      ‚t        t        «      }|j                  «       r®|j                  «       rt        d|› �«      ‚|j                  d«      D ]|  }|j                  «       s|j                  t        v rŒ&t        |j                  |«      «      }|j                  «       5 }|j                  «       }	ddd«       |	   j                  |«       Œ~ t        «       }
|j!                  «       D �]É  }|j                  t        v rŒ|j                  «       rt        d|› �«      ‚t        «       }|j                  d«      D ]²  }|j                  «       rŒt#        |«      j%                  «       }|j                  «       st        d|› �«      ‚|‰vr|j'                  «       ‰|<   |j                  t)        |j                  |‰|   j*                  |‰|   j,                  ‰|   j.                  ¬«      «       Œ´ t1        |«      dkD  rt3        ˆfd„|D «       «      }n|j'                  «       j.                  }|
j                  t5        |j                  t7        |«      t7        |j9                  |j                  t        «       «      «      t;        ˆfd„|D �ch c]  }|j<                  ’Œ c}D «       «      ||¬«      «       �ŒÌ t1        |«      dkD  rt        dt?        |«      › d| › d�«      ‚t1        ‰«      dkD  rAt3        d„ ‰jA                  «       D «       «      }t3        d„ ‰jA                  «       D «       «      }n(| j'                  «       }|j,                  }|j.                  }tC        t1        ‰«      || |t7        |
«      t;        d„ ‰jA                  «       D «       «      ||¬«      S # 1 sw Y   �ŒêxY wc c}w )z†Scan a single cache repo and return information about it.

    Any unexpected behavior will raise a [`~CorruptedCacheException`].
    zRepo path is not a directory: z--z6Repo path is not a valid HuggingFace cache directory: r   )ÚmaxsplitNéÿÿÿÿrQ   >   r   r   r   z8Repo type must be `dataset`, `model` or `space`, found `z` (z).r]   r9   z,Snapshots dir doesn't exist in cached repo: z!Refs directory cannot be a file: z**/*z*Snapshots folder corrupted. Found a file: zBlob missing (broken symlink): )r   r   r   r   r   r   r   c              3   óP   •K  — | ]  }‰|j                      j                  –— Œ y ­wr‰   )r   Úst_mtime)r¢   r‚   Ú
blob_statss     €r   r£   z$_scan_cached_repo.<locals>.<genexpr>û  s!   øè ø€ Ò(fÐQU¨°D·N±NÑ)C×)LÕ)LÑ(fùs   ƒ#&c              3   ó<   •K  — | ]  }‰|   j                   –— Œ y ­wr‰   ©Úst_size)r¢   r   r¶   s     €r   r£   z$_scan_cached_repo.<locals>.<genexpr>  s!   øè ø€ ò !Ø6?�J˜yÑ)×1Õ1ñ!ùs   ƒ)r6   r8   r9   r   r7   r:   z-Reference(s) refer to missing commit hashes: z (c              3   ó4   K  — | ]  }|j                   –— Œ y ­wr‰   )Úst_atime©r¢   Ústats     r   r£   z$_scan_cached_repo.<locals>.<genexpr>  ó   è ø€ Ò O°4 §¥Ñ Oùr¤   c              3   ó4   K  — | ]  }|j                   –— Œ y ­wr‰   )rµ   r¼   s     r   r£   z$_scan_cached_repo.<locals>.<genexpr>  r¾   r¤   c              3   ó4   K  — | ]  }|j                   –— Œ y ­wr‰   r¸   r¼   s     r   r£   z$_scan_cached_repo.<locals>.<genexpr>#  s   è ø€ ÒF¨$˜Ÿ�ÑFùr¤   )rC   rG   rI   rH   rJ   r   rK   r:   )"Úis_dirr   r«   ÚsplitÚreplacer§   r   rq   r¨   ÚglobÚFILES_TO_IGNOREr.   Úrelative_toÚopenÚreadrr   rª   r   r¦   r½   r   r¹   r»   rµ   rB   Úmaxr5   rD   Úpopr®   r   rW   ÚvaluesrF   )rI   rH   rG   Úsnapshots_pathÚ	refs_pathÚrefs_by_hashÚref_pathÚref_nameÚfr6   Úcached_revisionsÚrevision_pathÚcached_filesr   r   Úrevision_last_modifiedr‚   Úrepo_last_accessedÚrepo_last_modifiedÚ
repo_statsr¶   s                       @r   r¬   r¬   ¢  s^  ø€ ð
 ×ÑÔÜ%Ð(FÀyÀkÐ&RÓSÐSà�9—>‘>Ñ!Ü%Ð(^Ð_hÐ^iÐ&jÓkÐkà"Ÿ™×-Ñ-¨d¸QÐ-Ó?Ñ€IˆwØ˜#˜2�€IØ�o‰o˜d CÓ(€GàÐ5Ñ5Ü%ØFÀyÀkÐQTÐU^ÐT_Ð_aÐbó
ð 	
ð .0€Jà Ñ,€NØ˜FÑ"€Ià× Ñ Ô"¨.×*?Ñ*?Ô*AÜ%Ð(TÐUcÐTdÐ&eÓfÐfô
 )4´CÓ(8€LØ×ÑÔð ×ÑÔÜ)Ð,MÈiÈ[Ð*YÓZÐZà!Ÿ™ vÓ.ò 		4ˆHà�‰Ô  H§M¡M´_Ñ$DØä˜8×/Ñ/°	Ó:Ó;ˆHØ—‘“ð ' AØŸf™f›h�÷'ð ˜Ñ%×)Ñ)¨(Õ3ð		4ô 14³ÐØ'×/Ñ/Ó1ó 1
ˆà×Ñ¤Ñ0ØØ× Ñ Ô"Ü)Ð,VÐWdÐVeÐ*fÓgÐgä“uˆØ&×+Ñ+¨FÓ3ò 	ˆIà×ÑÔ!Øä˜Y›×/Ñ/Ó1ˆIØ×#Ñ#Ô%Ü-Ð0OÐPYÈ{Ð.[Ó\Ð\à 
Ñ*Ø(1¯©Ó(8�
˜9Ñ%à×ÑÜØ'Ÿn™nØ'Ø!+¨IÑ!6×!>Ñ!>Ø'Ø'1°)Ñ'<×'EÑ'EØ'1°)Ñ'<×'EÑ'Eôõ	ð	ô2 ˆ|Ó˜qÒ Ü%(Ó(fÐYeÔ(fÓ%fÑ"à%2×%7Ñ%7Ó%9×%BÑ%BÐ"à×ÑÜØ)×.Ñ.Ü Ó-Ü˜|×/Ñ/°×0BÑ0BÄCÃEÓJÓKÜ ó !Ø_kÖClÐW[ÀDÇNÃNÒClô!ó ð ,Ø4ô	ö	
ðM1
ôh ˆ<Ó˜1ÒÜ%Ø;¼DÀÓ<NÐ;OÈrÐR[ÐQ\Ð\^Ð_ó
ð 	
ô ˆ:ƒ˜ÒÜ Ñ O¸:×;LÑ;LÓ;NÔ OÓOÐÜ Ñ O¸:×;LÑ;LÓ;NÔ OÓOÑà—^‘^Ó%ˆ
Ø'×0Ñ0ÐØ'×0Ñ0Ðô Ü�Z“ØØØÜÐ,Ó-ÜÑF°*×2CÑ2CÓ2EÔFÓFØ(Ø(ô	ð 	÷W'ñ 'üòf Dms   Å!QÍ
Q'ÑQ$	Únumc                 ój   — t        | «      }dD ]  }t        |«      dk  r	|d›|› �c S |dz  }Œ  |d›d�S )zkFormat size in bytes into a human-readable string.

    Taken from https://stackoverflow.com/a/1094933
    )Ú ÚKÚMÚGÚTÚPÚEÚZg     @�@z3.1fz.1fÚY)r1   Úabs)rÙ   Únum_fÚunits      r   r'   r'   )  sR   € ô
 �#‹J€EØ7ò ˆÜˆu‹:˜ÒØ˜D�\ $ Ð(Ò(Ø�‰‰ðð �Cˆ[˜ˆ?Ðr"   ri   rb   c                 ó\  — t         j                  d|› d| › �«       	 | j                  «       rt        j                  | «       y	t        j                  | «       y	# t        $ r! t         j                  d|› d| › d�d¬«       Y y	t        $ r! t         j                  d|› d| › d�d¬«       Y y	w xY w)
aD  Try to delete a local file or folder.

    If the path does not exist, error is logged as a warning and then ignored.

    Args:
        path (`Path`)
            Path to delete. Can be a file or a folder.
        path_type (`str`)
            What path are we deleting ? Only for logging purposes. Example: "snapshot".
    zDelete z: zCouldn't delete z: file not found (ú)T)Úexc_infoz: permission denied (N)
rg   rh   r¨   Úosrs   ÚshutilÚrmtreeÚFileNotFoundErrorrt   ÚPermissionError)ri   rb   s     r   rf   rf   6  s¡   € ô ‡K�K�'˜)˜ B t fÐ-Ô.ðbØ�<‰<Œ>Ü�I‰I�d�Oä�M‰M˜$ÕøÜò _Ü�‰Ð)¨)¨Ð4FÀtÀfÈAÐNÐY]ˆÖ^Üò bÜ�‰Ð)¨)¨Ð4IÈ$ÈÈqÐQÐ\`ˆÖaðbús   �%A ÁA Á'B+Â&B+Â*B+r‰   )&r-   rê   rë   Úcollectionsr   Údataclassesr   Úpathlibr   Útypingr   Úhuggingface_hub.errorsr   r   Ú	constantsr
   rÛ   r   Ú_parsingr   Ú	_terminalr   Ú
get_loggerr*   rg   rV   rÅ   r   r5   rF   rY   rl   r.   r°   r¬   r0   r'   rf   r3   r"   r   ú<module>rø      sh  ðñ ;ã 	Û Ý #Ý !Ý Ý ç Iå $Ý Ý &Ý ð 
ˆ×	Ñ	˜HÓ	%€àÐ1Ñ2€ð �-€ñ �$Ô÷</ð </ó ð</ñ~ �$Ô÷Cð Có ðCñL �$Ô÷QWð QWó ðQWñh �$Ô÷BSð BSó ðBSñJ �$Ô÷cð có ðcñLo˜c D™j¨4Ñ/ð o¸;ó oðdD ð D¨.ó DðN
�cð 
˜có 
ðb˜4ð b¨Cð b°Dô br"   