@@ -172,33 +172,51 @@ def get_jinja_version():
172
172
return _jinja_version
173
173
174
174
175
- _are_symlinks_supported : Optional [ bool ] = None
175
+ _are_symlinks_supported_in_dir : Dict [ str , bool ] = {}
176
176
177
177
178
- def are_symlinks_supported () -> bool :
179
- # Check symlink compatibility only once at first time use
180
- global _are_symlinks_supported
178
+ def are_symlinks_supported (cache_dir : Union [str , Path , None ] = None ) -> bool :
179
+ """Return whether the symlinks are supported on the machine.
181
180
182
- if _are_symlinks_supported is None :
183
- _are_symlinks_supported = True
181
+ Since symlinks support can change depending on the mounted disk, we need to check
182
+ on the precise cache folder. By default, the default HF cache directory is checked.
184
183
185
- with tempfile .TemporaryDirectory () as tmpdir :
184
+ Args:
185
+ cache_dir (`str`, `Path`, *optional*):
186
+ Path to the folder where cached files are stored.
187
+
188
+ Returns: [bool] Whether symlinks are supported in the directory.
189
+ """
190
+ # Defaults to HF cache
191
+ if cache_dir is None :
192
+ cache_dir = HUGGINGFACE_HUB_CACHE
193
+ cache_dir = str (Path (cache_dir ).expanduser ().resolve ()) # make it unique
194
+
195
+ # Check symlink compatibility only once (per cache directory) at first time use
196
+ if cache_dir not in _are_symlinks_supported_in_dir :
197
+ _are_symlinks_supported_in_dir [cache_dir ] = True
198
+
199
+ os .makedirs (cache_dir , exist_ok = True )
200
+ with tempfile .TemporaryDirectory (dir = cache_dir ) as tmpdir :
186
201
src_path = Path (tmpdir ) / "dummy_file_src"
187
202
src_path .touch ()
188
203
dst_path = Path (tmpdir ) / "dummy_file_dst"
204
+
205
+ # Relative source path as in `_create_relative_symlink``
206
+ relative_src = os .path .relpath (src_path , start = os .path .dirname (dst_path ))
189
207
try :
190
- os .symlink (src_path , dst_path )
208
+ os .symlink (relative_src , dst_path )
191
209
except OSError :
192
210
# Likely running on Windows
193
- _are_symlinks_supported = False
211
+ _are_symlinks_supported_in_dir [ cache_dir ] = False
194
212
195
213
if not os .environ .get ("DISABLE_SYMLINKS_WARNING" ):
196
214
message = (
197
215
"`huggingface_hub` cache-system uses symlinks by default to"
198
- " efficiently store duplicated files but your machine doesn't "
199
- " support them. Caching files will still work but in a degraded "
200
- " version that might require more space on your disk. This "
201
- " warning can be disabled by setting the"
216
+ " efficiently store duplicated files but your machine does not "
217
+ f " support them in { cache_dir } . Caching files will still work"
218
+ " but in a degraded version that might require more space on"
219
+ " your disk. This warning can be disabled by setting the"
202
220
" `DISABLE_SYMLINKS_WARNING` environment variable. For more"
203
221
" details, see"
204
222
" https://huggingface.co/docs/huggingface_hub/how-to-cache#limitations."
@@ -213,7 +231,7 @@ def are_symlinks_supported() -> bool:
213
231
)
214
232
warnings .warn (message )
215
233
216
- return _are_symlinks_supported
234
+ return _are_symlinks_supported_in_dir [ cache_dir ]
217
235
218
236
219
237
# Return value when trying to load a file from cache but the file does not exist in the distant repo.
@@ -920,7 +938,8 @@ def _create_relative_symlink(src: str, dst: str, new_blob: bool = False) -> None
920
938
except OSError :
921
939
pass
922
940
923
- if are_symlinks_supported ():
941
+ cache_dir = os .path .dirname (os .path .commonpath ([src , dst ]))
942
+ if are_symlinks_supported (cache_dir = cache_dir ):
924
943
os .symlink (relative_src , dst )
925
944
elif new_blob :
926
945
os .replace (src , dst )
0 commit comments