huggingface-hub 0.22.2__py3-none-any.whl → 0.23.1__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.
Potentially problematic release.
This version of huggingface-hub might be problematic. Click here for more details.
- huggingface_hub/__init__.py +51 -19
- huggingface_hub/_commit_api.py +9 -8
- huggingface_hub/_commit_scheduler.py +2 -2
- huggingface_hub/_inference_endpoints.py +10 -17
- huggingface_hub/_local_folder.py +229 -0
- huggingface_hub/_login.py +4 -3
- huggingface_hub/_multi_commits.py +1 -1
- huggingface_hub/_snapshot_download.py +16 -38
- huggingface_hub/_tensorboard_logger.py +16 -6
- huggingface_hub/_webhooks_payload.py +22 -1
- huggingface_hub/_webhooks_server.py +24 -20
- huggingface_hub/commands/download.py +11 -34
- huggingface_hub/commands/huggingface_cli.py +2 -0
- huggingface_hub/commands/tag.py +159 -0
- huggingface_hub/constants.py +3 -5
- huggingface_hub/errors.py +58 -0
- huggingface_hub/file_download.py +545 -376
- huggingface_hub/hf_api.py +756 -622
- huggingface_hub/hf_file_system.py +20 -5
- huggingface_hub/hub_mixin.py +127 -43
- huggingface_hub/inference/_client.py +402 -183
- huggingface_hub/inference/_common.py +19 -29
- huggingface_hub/inference/_generated/_async_client.py +402 -184
- huggingface_hub/inference/_generated/types/__init__.py +23 -6
- huggingface_hub/inference/_generated/types/chat_completion.py +197 -43
- huggingface_hub/inference/_generated/types/text_generation.py +57 -79
- huggingface_hub/inference/_templating.py +2 -4
- huggingface_hub/keras_mixin.py +0 -3
- huggingface_hub/lfs.py +9 -1
- huggingface_hub/repository.py +1 -0
- huggingface_hub/utils/__init__.py +12 -6
- huggingface_hub/utils/_fixes.py +1 -0
- huggingface_hub/utils/_headers.py +2 -4
- huggingface_hub/utils/_http.py +2 -4
- huggingface_hub/utils/_paths.py +13 -1
- huggingface_hub/utils/_runtime.py +10 -0
- huggingface_hub/utils/_safetensors.py +0 -13
- huggingface_hub/utils/_validators.py +2 -7
- huggingface_hub/utils/tqdm.py +124 -46
- {huggingface_hub-0.22.2.dist-info → huggingface_hub-0.23.1.dist-info}/METADATA +5 -1
- {huggingface_hub-0.22.2.dist-info → huggingface_hub-0.23.1.dist-info}/RECORD +45 -43
- {huggingface_hub-0.22.2.dist-info → huggingface_hub-0.23.1.dist-info}/LICENSE +0 -0
- {huggingface_hub-0.22.2.dist-info → huggingface_hub-0.23.1.dist-info}/WHEEL +0 -0
- {huggingface_hub-0.22.2.dist-info → huggingface_hub-0.23.1.dist-info}/entry_points.txt +0 -0
- {huggingface_hub-0.22.2.dist-info → huggingface_hub-0.23.1.dist-info}/top_level.txt +0 -0
|
@@ -16,7 +16,21 @@
|
|
|
16
16
|
|
|
17
17
|
from typing import List, Literal, Optional
|
|
18
18
|
|
|
19
|
-
from
|
|
19
|
+
from .utils import is_pydantic_available
|
|
20
|
+
|
|
21
|
+
|
|
22
|
+
if is_pydantic_available():
|
|
23
|
+
from pydantic import BaseModel
|
|
24
|
+
else:
|
|
25
|
+
# Define a dummy BaseModel to avoid import errors when pydantic is not installed
|
|
26
|
+
# Import error will be raised when trying to use the class
|
|
27
|
+
|
|
28
|
+
class BaseModel: # type: ignore [no-redef]
|
|
29
|
+
def __init__(self, *args, **kwargs) -> None:
|
|
30
|
+
raise ImportError(
|
|
31
|
+
"You must have `pydantic` installed to use `WebhookPayload`. This is an optional dependency that"
|
|
32
|
+
" should be installed separately. Please run `pip install --upgrade pydantic` and retry."
|
|
33
|
+
)
|
|
20
34
|
|
|
21
35
|
|
|
22
36
|
# This is an adaptation of the ReportV3 interface implemented in moon-landing. V0, V1 and V2 have been ignored as they
|
|
@@ -107,6 +121,12 @@ class WebhookPayloadRepo(ObjectId):
|
|
|
107
121
|
url: WebhookPayloadUrl
|
|
108
122
|
|
|
109
123
|
|
|
124
|
+
class WebhookPayloadUpdatedRef(BaseModel):
|
|
125
|
+
ref: str
|
|
126
|
+
oldSha: Optional[str] = None
|
|
127
|
+
newSha: Optional[str] = None
|
|
128
|
+
|
|
129
|
+
|
|
110
130
|
class WebhookPayload(BaseModel):
|
|
111
131
|
event: WebhookPayloadEvent
|
|
112
132
|
repo: WebhookPayloadRepo
|
|
@@ -114,3 +134,4 @@ class WebhookPayload(BaseModel):
|
|
|
114
134
|
comment: Optional[WebhookPayloadComment] = None
|
|
115
135
|
webhook: WebhookPayloadWebhook
|
|
116
136
|
movedTo: Optional[WebhookPayloadMovedTo] = None
|
|
137
|
+
updatedRefs: Optional[List[WebhookPayloadUpdatedRef]] = None
|
|
@@ -20,16 +20,19 @@ import os
|
|
|
20
20
|
from functools import wraps
|
|
21
21
|
from typing import TYPE_CHECKING, Any, Callable, Dict, Optional
|
|
22
22
|
|
|
23
|
-
from .utils import experimental, is_gradio_available
|
|
24
|
-
from .utils._deprecation import _deprecate_method
|
|
23
|
+
from .utils import experimental, is_fastapi_available, is_gradio_available
|
|
25
24
|
|
|
26
25
|
|
|
27
26
|
if TYPE_CHECKING:
|
|
28
27
|
import gradio as gr
|
|
28
|
+
from fastapi import Request
|
|
29
29
|
|
|
30
|
-
|
|
31
|
-
from fastapi import FastAPI, Request
|
|
32
|
-
from fastapi.responses import JSONResponse
|
|
30
|
+
if is_fastapi_available():
|
|
31
|
+
from fastapi import FastAPI, Request
|
|
32
|
+
from fastapi.responses import JSONResponse
|
|
33
|
+
else:
|
|
34
|
+
# Will fail at runtime if FastAPI is not available
|
|
35
|
+
FastAPI = Request = JSONResponse = None # type: ignore [misc, assignment]
|
|
33
36
|
|
|
34
37
|
|
|
35
38
|
_global_app: Optional["WebhooksServer"] = None
|
|
@@ -41,7 +44,7 @@ class WebhooksServer:
|
|
|
41
44
|
"""
|
|
42
45
|
The [`WebhooksServer`] class lets you create an instance of a Gradio app that can receive Huggingface webhooks.
|
|
43
46
|
These webhooks can be registered using the [`~WebhooksServer.add_webhook`] decorator. Webhook endpoints are added to
|
|
44
|
-
the app as a POST endpoint to the FastAPI router. Once all the webhooks are registered, the `
|
|
47
|
+
the app as a POST endpoint to the FastAPI router. Once all the webhooks are registered, the `launch` method has to be
|
|
45
48
|
called to start the app.
|
|
46
49
|
|
|
47
50
|
It is recommended to accept [`WebhookPayload`] as the first argument of the webhook function. It is a Pydantic
|
|
@@ -87,7 +90,7 @@ class WebhooksServer:
|
|
|
87
90
|
async def hello(payload: WebhookPayload):
|
|
88
91
|
return {"message": "hello"}
|
|
89
92
|
|
|
90
|
-
app.
|
|
93
|
+
app.launch()
|
|
91
94
|
```
|
|
92
95
|
"""
|
|
93
96
|
|
|
@@ -97,6 +100,11 @@ class WebhooksServer:
|
|
|
97
100
|
"You must have `gradio` installed to use `WebhooksServer`. Please run `pip install --upgrade gradio`"
|
|
98
101
|
" first."
|
|
99
102
|
)
|
|
103
|
+
if not is_fastapi_available():
|
|
104
|
+
raise ImportError(
|
|
105
|
+
"You must have `fastapi` installed to use `WebhooksServer`. Please run `pip install --upgrade fastapi`"
|
|
106
|
+
" first."
|
|
107
|
+
)
|
|
100
108
|
return super().__new__(cls)
|
|
101
109
|
|
|
102
110
|
def __init__(
|
|
@@ -134,7 +142,7 @@ class WebhooksServer:
|
|
|
134
142
|
# Trigger a training job if a dataset is updated
|
|
135
143
|
...
|
|
136
144
|
|
|
137
|
-
app.
|
|
145
|
+
app.launch()
|
|
138
146
|
```
|
|
139
147
|
"""
|
|
140
148
|
# Usage: directly as decorator. Example: `@app.add_webhook`
|
|
@@ -185,10 +193,6 @@ class WebhooksServer:
|
|
|
185
193
|
if not prevent_thread_lock:
|
|
186
194
|
ui.block_thread()
|
|
187
195
|
|
|
188
|
-
@_deprecate_method(version="0.23", message="Use `WebhooksServer.launch` instead.")
|
|
189
|
-
def run(self) -> None:
|
|
190
|
-
return self.launch()
|
|
191
|
-
|
|
192
196
|
def _get_default_ui(self) -> "gr.Blocks":
|
|
193
197
|
"""Default UI if not provided (lists webhooks and provides basic instructions)."""
|
|
194
198
|
import gradio as gr
|
|
@@ -278,7 +282,7 @@ def webhook_endpoint(path: Optional[str] = None) -> Callable:
|
|
|
278
282
|
...
|
|
279
283
|
|
|
280
284
|
# Start the server manually
|
|
281
|
-
trigger_training.
|
|
285
|
+
trigger_training.launch()
|
|
282
286
|
```
|
|
283
287
|
"""
|
|
284
288
|
if callable(path):
|
|
@@ -290,16 +294,16 @@ def webhook_endpoint(path: Optional[str] = None) -> Callable:
|
|
|
290
294
|
app = _get_global_app()
|
|
291
295
|
app.add_webhook(path)(func)
|
|
292
296
|
if len(app.registered_webhooks) == 1:
|
|
293
|
-
# Register `app.
|
|
294
|
-
atexit.register(app.
|
|
297
|
+
# Register `app.launch` to run at exit (only once)
|
|
298
|
+
atexit.register(app.launch)
|
|
295
299
|
|
|
296
|
-
@wraps(app.
|
|
297
|
-
def
|
|
300
|
+
@wraps(app.launch)
|
|
301
|
+
def _launch_now():
|
|
298
302
|
# Run the app directly (without waiting atexit)
|
|
299
|
-
atexit.unregister(app.
|
|
300
|
-
app.
|
|
303
|
+
atexit.unregister(app.launch)
|
|
304
|
+
app.launch()
|
|
301
305
|
|
|
302
|
-
func.
|
|
306
|
+
func.launch = _launch_now # type: ignore
|
|
303
307
|
return func
|
|
304
308
|
|
|
305
309
|
return _inner
|
|
@@ -38,12 +38,11 @@ Usage:
|
|
|
38
38
|
|
|
39
39
|
import warnings
|
|
40
40
|
from argparse import Namespace, _SubParsersAction
|
|
41
|
-
from typing import List,
|
|
41
|
+
from typing import List, Optional
|
|
42
42
|
|
|
43
43
|
from huggingface_hub import logging
|
|
44
44
|
from huggingface_hub._snapshot_download import snapshot_download
|
|
45
45
|
from huggingface_hub.commands import BaseHuggingfaceCLICommand
|
|
46
|
-
from huggingface_hub.constants import HF_HUB_ENABLE_HF_TRANSFER
|
|
47
46
|
from huggingface_hub.file_download import hf_hub_download
|
|
48
47
|
from huggingface_hub.utils import disable_progress_bars, enable_progress_bars
|
|
49
48
|
|
|
@@ -85,8 +84,7 @@ class DownloadCommand(BaseHuggingfaceCLICommand):
|
|
|
85
84
|
"--local-dir",
|
|
86
85
|
type=str,
|
|
87
86
|
help=(
|
|
88
|
-
"If set, the downloaded file will be placed under this directory
|
|
89
|
-
" regular file. Check out"
|
|
87
|
+
"If set, the downloaded file will be placed under this directory. Check out"
|
|
90
88
|
" https://huggingface.co/docs/huggingface_hub/guides/download#download-files-to-local-folder for more"
|
|
91
89
|
" details."
|
|
92
90
|
),
|
|
@@ -94,13 +92,7 @@ class DownloadCommand(BaseHuggingfaceCLICommand):
|
|
|
94
92
|
download_parser.add_argument(
|
|
95
93
|
"--local-dir-use-symlinks",
|
|
96
94
|
choices=["auto", "True", "False"],
|
|
97
|
-
|
|
98
|
-
help=(
|
|
99
|
-
"To be used with `local_dir`. If set to 'auto', the cache directory will be used and the file will be"
|
|
100
|
-
" either duplicated or symlinked to the local directory depending on its size. It set to `True`, a"
|
|
101
|
-
" symlink will be created, no matter the file size. If set to `False`, the file will either be"
|
|
102
|
-
" duplicated from cache (if already exists) or downloaded from the Hub and not cached."
|
|
103
|
-
),
|
|
95
|
+
help=("Deprecated and ignored. Downloading to a local directory does not use symlinks anymore."),
|
|
104
96
|
)
|
|
105
97
|
download_parser.add_argument(
|
|
106
98
|
"--force-download",
|
|
@@ -108,7 +100,9 @@ class DownloadCommand(BaseHuggingfaceCLICommand):
|
|
|
108
100
|
help="If True, the files will be downloaded even if they are already cached.",
|
|
109
101
|
)
|
|
110
102
|
download_parser.add_argument(
|
|
111
|
-
"--resume-download",
|
|
103
|
+
"--resume-download",
|
|
104
|
+
action="store_true",
|
|
105
|
+
help="Deprecated and ignored. Downloading a file to local dir always attempts to resume previously interrupted downloads (unless hf-transfer is enabled).",
|
|
112
106
|
)
|
|
113
107
|
download_parser.add_argument(
|
|
114
108
|
"--token", type=str, help="A User Access Token generated from https://huggingface.co/settings/tokens"
|
|
@@ -131,22 +125,13 @@ class DownloadCommand(BaseHuggingfaceCLICommand):
|
|
|
131
125
|
self.cache_dir: Optional[str] = args.cache_dir
|
|
132
126
|
self.local_dir: Optional[str] = args.local_dir
|
|
133
127
|
self.force_download: bool = args.force_download
|
|
134
|
-
self.resume_download: bool = args.resume_download
|
|
128
|
+
self.resume_download: Optional[bool] = args.resume_download or None
|
|
135
129
|
self.quiet: bool = args.quiet
|
|
136
130
|
|
|
137
|
-
|
|
138
|
-
|
|
139
|
-
|
|
140
|
-
|
|
141
|
-
self.local_dir_use_symlinks = True
|
|
142
|
-
elif use_symlinks_lowercase == "false":
|
|
143
|
-
self.local_dir_use_symlinks = False
|
|
144
|
-
elif use_symlinks_lowercase == "auto":
|
|
145
|
-
self.local_dir_use_symlinks = "auto"
|
|
146
|
-
else:
|
|
147
|
-
raise ValueError(
|
|
148
|
-
f"'{args.local_dir_use_symlinks}' is not a valid value for `local_dir_use_symlinks`. It must be either"
|
|
149
|
-
" 'auto', 'True' or 'False'."
|
|
131
|
+
if args.local_dir_use_symlinks is not None:
|
|
132
|
+
warnings.warn(
|
|
133
|
+
"Ignoring --local-dir-use-symlinks. Downloading to a local directory does not use symlinks anymore.",
|
|
134
|
+
FutureWarning,
|
|
150
135
|
)
|
|
151
136
|
|
|
152
137
|
def run(self) -> None:
|
|
@@ -169,12 +154,6 @@ class DownloadCommand(BaseHuggingfaceCLICommand):
|
|
|
169
154
|
if self.exclude is not None and len(self.exclude) > 0:
|
|
170
155
|
warnings.warn("Ignoring `--exclude` since filenames have being explicitly set.")
|
|
171
156
|
|
|
172
|
-
if not HF_HUB_ENABLE_HF_TRANSFER:
|
|
173
|
-
logger.info(
|
|
174
|
-
"Consider using `hf_transfer` for faster downloads. This solution comes with some limitations. See"
|
|
175
|
-
" https://huggingface.co/docs/huggingface_hub/hf_transfer for more details."
|
|
176
|
-
)
|
|
177
|
-
|
|
178
157
|
# Single file to download: use `hf_hub_download`
|
|
179
158
|
if len(self.filenames) == 1:
|
|
180
159
|
return hf_hub_download(
|
|
@@ -187,7 +166,6 @@ class DownloadCommand(BaseHuggingfaceCLICommand):
|
|
|
187
166
|
force_download=self.force_download,
|
|
188
167
|
token=self.token,
|
|
189
168
|
local_dir=self.local_dir,
|
|
190
|
-
local_dir_use_symlinks=self.local_dir_use_symlinks,
|
|
191
169
|
library_name="huggingface-cli",
|
|
192
170
|
)
|
|
193
171
|
|
|
@@ -210,6 +188,5 @@ class DownloadCommand(BaseHuggingfaceCLICommand):
|
|
|
210
188
|
cache_dir=self.cache_dir,
|
|
211
189
|
token=self.token,
|
|
212
190
|
local_dir=self.local_dir,
|
|
213
|
-
local_dir_use_symlinks=self.local_dir_use_symlinks,
|
|
214
191
|
library_name="huggingface-cli",
|
|
215
192
|
)
|
|
@@ -20,6 +20,7 @@ from huggingface_hub.commands.download import DownloadCommand
|
|
|
20
20
|
from huggingface_hub.commands.env import EnvironmentCommand
|
|
21
21
|
from huggingface_hub.commands.lfs import LfsCommands
|
|
22
22
|
from huggingface_hub.commands.scan_cache import ScanCacheCommand
|
|
23
|
+
from huggingface_hub.commands.tag import TagCommands
|
|
23
24
|
from huggingface_hub.commands.upload import UploadCommand
|
|
24
25
|
from huggingface_hub.commands.user import UserCommands
|
|
25
26
|
|
|
@@ -36,6 +37,7 @@ def main():
|
|
|
36
37
|
LfsCommands.register_subcommand(commands_parser)
|
|
37
38
|
ScanCacheCommand.register_subcommand(commands_parser)
|
|
38
39
|
DeleteCacheCommand.register_subcommand(commands_parser)
|
|
40
|
+
TagCommands.register_subcommand(commands_parser)
|
|
39
41
|
|
|
40
42
|
# Let's go
|
|
41
43
|
args = parser.parse_args()
|
|
@@ -0,0 +1,159 @@
|
|
|
1
|
+
# coding=utf-8
|
|
2
|
+
# Copyright 2024-present, the HuggingFace Inc. team.
|
|
3
|
+
#
|
|
4
|
+
# Licensed under the Apache License, Version 2.0 (the "License");
|
|
5
|
+
# you may not use this file except in compliance with the License.
|
|
6
|
+
# You may obtain a copy of the License at
|
|
7
|
+
#
|
|
8
|
+
# http://www.apache.org/licenses/LICENSE-2.0
|
|
9
|
+
#
|
|
10
|
+
# Unless required by applicable law or agreed to in writing, software
|
|
11
|
+
# distributed under the License is distributed on an "AS IS" BASIS,
|
|
12
|
+
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
13
|
+
# See the License for the specific language governing permissions and
|
|
14
|
+
# limitations under the License.
|
|
15
|
+
|
|
16
|
+
"""Contains commands to perform tag management with the CLI.
|
|
17
|
+
|
|
18
|
+
Usage Examples:
|
|
19
|
+
- Create a tag:
|
|
20
|
+
$ huggingface-cli tag user/my-model 1.0 --message "First release"
|
|
21
|
+
$ huggingface-cli tag user/my-model 1.0 -m "First release" --revision develop
|
|
22
|
+
$ huggingface-cli tag user/my-dataset 1.0 -m "First release" --repo-type dataset
|
|
23
|
+
$ huggingface-cli tag user/my-space 1.0
|
|
24
|
+
- List all tags:
|
|
25
|
+
$ huggingface-cli tag -l user/my-model
|
|
26
|
+
$ huggingface-cli tag --list user/my-dataset --repo-type dataset
|
|
27
|
+
- Delete a tag:
|
|
28
|
+
$ huggingface-cli tag -d user/my-model 1.0
|
|
29
|
+
$ huggingface-cli tag --delete user/my-dataset 1.0 --repo-type dataset
|
|
30
|
+
$ huggingface-cli tag -d user/my-space 1.0 -y
|
|
31
|
+
"""
|
|
32
|
+
|
|
33
|
+
from argparse import Namespace, _SubParsersAction
|
|
34
|
+
|
|
35
|
+
from requests.exceptions import HTTPError
|
|
36
|
+
|
|
37
|
+
from huggingface_hub.commands import BaseHuggingfaceCLICommand
|
|
38
|
+
from huggingface_hub.constants import (
|
|
39
|
+
REPO_TYPES,
|
|
40
|
+
)
|
|
41
|
+
from huggingface_hub.hf_api import HfApi
|
|
42
|
+
|
|
43
|
+
from ..utils import HfHubHTTPError, RepositoryNotFoundError, RevisionNotFoundError
|
|
44
|
+
from ._cli_utils import ANSI
|
|
45
|
+
|
|
46
|
+
|
|
47
|
+
class TagCommands(BaseHuggingfaceCLICommand):
|
|
48
|
+
@staticmethod
|
|
49
|
+
def register_subcommand(parser: _SubParsersAction):
|
|
50
|
+
tag_parser = parser.add_parser("tag", help="(create, list, delete) tags for a repo in the hub")
|
|
51
|
+
|
|
52
|
+
tag_parser.add_argument("repo_id", type=str, help="The ID of the repo to tag (e.g. `username/repo-name`).")
|
|
53
|
+
tag_parser.add_argument("tag", nargs="?", type=str, help="The name of the tag for creation or deletion.")
|
|
54
|
+
tag_parser.add_argument("-m", "--message", type=str, help="The description of the tag to create.")
|
|
55
|
+
tag_parser.add_argument("--revision", type=str, help="The git revision to tag.")
|
|
56
|
+
tag_parser.add_argument(
|
|
57
|
+
"--token", type=str, help="A User Access Token generated from https://huggingface.co/settings/tokens."
|
|
58
|
+
)
|
|
59
|
+
tag_parser.add_argument(
|
|
60
|
+
"--repo-type",
|
|
61
|
+
choices=["model", "dataset", "space"],
|
|
62
|
+
default="model",
|
|
63
|
+
help="Set the type of repository (model, dataset, or space).",
|
|
64
|
+
)
|
|
65
|
+
tag_parser.add_argument("-y", "--yes", action="store_true", help="Answer Yes to prompts automatically.")
|
|
66
|
+
|
|
67
|
+
tag_parser.add_argument("-l", "--list", action="store_true", help="List tags for a repository.")
|
|
68
|
+
tag_parser.add_argument("-d", "--delete", action="store_true", help="Delete a tag for a repository.")
|
|
69
|
+
|
|
70
|
+
tag_parser.set_defaults(func=lambda args: handle_commands(args))
|
|
71
|
+
|
|
72
|
+
|
|
73
|
+
def handle_commands(args: Namespace):
|
|
74
|
+
if args.list:
|
|
75
|
+
return TagListCommand(args)
|
|
76
|
+
elif args.delete:
|
|
77
|
+
return TagDeleteCommand(args)
|
|
78
|
+
else:
|
|
79
|
+
return TagCreateCommand(args)
|
|
80
|
+
|
|
81
|
+
|
|
82
|
+
class TagCommand:
|
|
83
|
+
def __init__(self, args: Namespace):
|
|
84
|
+
self.args = args
|
|
85
|
+
self.api = HfApi(token=self.args.token)
|
|
86
|
+
self.repo_id = self.args.repo_id
|
|
87
|
+
self.repo_type = self.args.repo_type
|
|
88
|
+
if self.repo_type not in REPO_TYPES:
|
|
89
|
+
print("Invalid repo --repo-type")
|
|
90
|
+
exit(1)
|
|
91
|
+
|
|
92
|
+
|
|
93
|
+
class TagCreateCommand(TagCommand):
|
|
94
|
+
def run(self):
|
|
95
|
+
print(f"You are about to create tag {ANSI.bold(self.args.tag)} on {self.repo_type} {ANSI.bold(self.repo_id)}")
|
|
96
|
+
|
|
97
|
+
try:
|
|
98
|
+
self.api.create_tag(
|
|
99
|
+
repo_id=self.repo_id,
|
|
100
|
+
tag=self.args.tag,
|
|
101
|
+
tag_message=self.args.message,
|
|
102
|
+
revision=self.args.revision,
|
|
103
|
+
repo_type=self.repo_type,
|
|
104
|
+
)
|
|
105
|
+
except RepositoryNotFoundError:
|
|
106
|
+
print(f"{self.repo_type.capitalize()} {ANSI.bold(self.repo_id)} not found.")
|
|
107
|
+
exit(1)
|
|
108
|
+
except RevisionNotFoundError:
|
|
109
|
+
print(f"Revision {ANSI.bold(self.args.revision)} not found.")
|
|
110
|
+
exit(1)
|
|
111
|
+
except HfHubHTTPError as e:
|
|
112
|
+
if e.response.status_code == 409:
|
|
113
|
+
print(f"Tag {ANSI.bold(self.args.tag)} already exists on {ANSI.bold(self.repo_id)}")
|
|
114
|
+
exit(1)
|
|
115
|
+
raise e
|
|
116
|
+
|
|
117
|
+
print(f"Tag {ANSI.bold(self.args.tag)} created on {ANSI.bold(self.repo_id)}")
|
|
118
|
+
|
|
119
|
+
|
|
120
|
+
class TagListCommand(TagCommand):
|
|
121
|
+
def run(self):
|
|
122
|
+
try:
|
|
123
|
+
refs = self.api.list_repo_refs(
|
|
124
|
+
repo_id=self.repo_id,
|
|
125
|
+
repo_type=self.repo_type,
|
|
126
|
+
)
|
|
127
|
+
except RepositoryNotFoundError:
|
|
128
|
+
print(f"{self.repo_type.capitalize()} {ANSI.bold(self.repo_id)} not found.")
|
|
129
|
+
exit(1)
|
|
130
|
+
except HTTPError as e:
|
|
131
|
+
print(e)
|
|
132
|
+
print(ANSI.red(e.response.text))
|
|
133
|
+
exit(1)
|
|
134
|
+
if len(refs.tags) == 0:
|
|
135
|
+
print("No tags found")
|
|
136
|
+
exit(0)
|
|
137
|
+
print(f"Tags for {self.repo_type} {ANSI.bold(self.repo_id)}:")
|
|
138
|
+
for tag in refs.tags:
|
|
139
|
+
print(tag.name)
|
|
140
|
+
|
|
141
|
+
|
|
142
|
+
class TagDeleteCommand(TagCommand):
|
|
143
|
+
def run(self):
|
|
144
|
+
print(f"You are about to delete tag {ANSI.bold(self.args.tag)} on {self.repo_type} {ANSI.bold(self.repo_id)}")
|
|
145
|
+
|
|
146
|
+
if not self.args.yes:
|
|
147
|
+
choice = input("Proceed? [Y/n] ").lower()
|
|
148
|
+
if choice not in ("", "y", "yes"):
|
|
149
|
+
print("Abort")
|
|
150
|
+
exit()
|
|
151
|
+
try:
|
|
152
|
+
self.api.delete_tag(repo_id=self.repo_id, tag=self.args.tag, repo_type=self.repo_type)
|
|
153
|
+
except RepositoryNotFoundError:
|
|
154
|
+
print(f"{self.repo_type.capitalize()} {ANSI.bold(self.repo_id)} not found.")
|
|
155
|
+
exit(1)
|
|
156
|
+
except RevisionNotFoundError:
|
|
157
|
+
print(f"Tag {ANSI.bold(self.args.tag)} not found on {ANSI.bold(self.repo_id)}")
|
|
158
|
+
exit(1)
|
|
159
|
+
print(f"Tag {ANSI.bold(self.args.tag)} deleted on {ANSI.bold(self.repo_id)}")
|
huggingface_hub/constants.py
CHANGED
|
@@ -127,7 +127,7 @@ HF_HUB_DISABLE_TELEMETRY = (
|
|
|
127
127
|
# `_OLD_HF_TOKEN_PATH` is deprecated and will be removed "at some point".
|
|
128
128
|
# See https://github.com/huggingface/huggingface_hub/issues/1232
|
|
129
129
|
_OLD_HF_TOKEN_PATH = os.path.expanduser("~/.huggingface/token")
|
|
130
|
-
HF_TOKEN_PATH = os.path.join(HF_HOME, "token")
|
|
130
|
+
HF_TOKEN_PATH = os.environ.get("HF_TOKEN_PATH", os.path.join(HF_HOME, "token"))
|
|
131
131
|
|
|
132
132
|
|
|
133
133
|
if _staging_mode:
|
|
@@ -163,9 +163,8 @@ HF_HUB_DISABLE_IMPLICIT_TOKEN: bool = _is_true(os.environ.get("HF_HUB_DISABLE_IM
|
|
|
163
163
|
HF_HUB_ENABLE_HF_TRANSFER: bool = _is_true(os.environ.get("HF_HUB_ENABLE_HF_TRANSFER"))
|
|
164
164
|
|
|
165
165
|
|
|
166
|
-
#
|
|
167
|
-
#
|
|
168
|
-
# huge files (i.e. LFS files most of the time) while allowing small files to be manually edited in local folder.
|
|
166
|
+
# UNUSED
|
|
167
|
+
# We don't use symlinks in local dir anymore.
|
|
169
168
|
HF_HUB_LOCAL_DIR_AUTO_SYMLINK_THRESHOLD: int = (
|
|
170
169
|
_as_int(os.environ.get("HF_HUB_LOCAL_DIR_AUTO_SYMLINK_THRESHOLD")) or 5 * 1024 * 1024
|
|
171
170
|
)
|
|
@@ -197,7 +196,6 @@ ALL_INFERENCE_API_FRAMEWORKS = MAIN_INFERENCE_API_FRAMEWORKS + [
|
|
|
197
196
|
"fastai",
|
|
198
197
|
"fasttext",
|
|
199
198
|
"flair",
|
|
200
|
-
"generic",
|
|
201
199
|
"k2",
|
|
202
200
|
"keras",
|
|
203
201
|
"mindspore",
|
huggingface_hub/errors.py
CHANGED
|
@@ -3,6 +3,20 @@
|
|
|
3
3
|
from requests import HTTPError
|
|
4
4
|
|
|
5
5
|
|
|
6
|
+
# HEADERS ERRORS
|
|
7
|
+
|
|
8
|
+
|
|
9
|
+
class LocalTokenNotFoundError(EnvironmentError):
|
|
10
|
+
"""Raised if local token is required but not found."""
|
|
11
|
+
|
|
12
|
+
|
|
13
|
+
# HTTP ERRORS
|
|
14
|
+
|
|
15
|
+
|
|
16
|
+
class OfflineModeIsEnabled(ConnectionError):
|
|
17
|
+
"""Raised when a request is made but `HF_HUB_OFFLINE=1` is set as environment variable."""
|
|
18
|
+
|
|
19
|
+
|
|
6
20
|
# INFERENCE CLIENT ERRORS
|
|
7
21
|
|
|
8
22
|
|
|
@@ -10,6 +24,40 @@ class InferenceTimeoutError(HTTPError, TimeoutError):
|
|
|
10
24
|
"""Error raised when a model is unavailable or the request times out."""
|
|
11
25
|
|
|
12
26
|
|
|
27
|
+
# INFERENCE ENDPOINT ERRORS
|
|
28
|
+
|
|
29
|
+
|
|
30
|
+
class InferenceEndpointError(Exception):
|
|
31
|
+
"""Generic exception when dealing with Inference Endpoints."""
|
|
32
|
+
|
|
33
|
+
|
|
34
|
+
class InferenceEndpointTimeoutError(InferenceEndpointError, TimeoutError):
|
|
35
|
+
"""Exception for timeouts while waiting for Inference Endpoint."""
|
|
36
|
+
|
|
37
|
+
|
|
38
|
+
# SAFETENSORS ERRORS
|
|
39
|
+
|
|
40
|
+
|
|
41
|
+
class SafetensorsParsingError(Exception):
|
|
42
|
+
"""Raised when failing to parse a safetensors file metadata.
|
|
43
|
+
|
|
44
|
+
This can be the case if the file is not a safetensors file or does not respect the specification.
|
|
45
|
+
"""
|
|
46
|
+
|
|
47
|
+
|
|
48
|
+
class NotASafetensorsRepoError(Exception):
|
|
49
|
+
"""Raised when a repo is not a Safetensors repo i.e. doesn't have either a `model.safetensors` or a
|
|
50
|
+
`model.safetensors.index.json` file.
|
|
51
|
+
"""
|
|
52
|
+
|
|
53
|
+
|
|
54
|
+
# TEMPLATING ERRORS
|
|
55
|
+
|
|
56
|
+
|
|
57
|
+
class TemplateError(Exception):
|
|
58
|
+
"""Any error raised while trying to fetch or render a chat template."""
|
|
59
|
+
|
|
60
|
+
|
|
13
61
|
# TEXT GENERATION ERRORS
|
|
14
62
|
|
|
15
63
|
|
|
@@ -36,3 +84,13 @@ class IncompleteGenerationError(TextGenerationError):
|
|
|
36
84
|
|
|
37
85
|
class UnknownError(TextGenerationError):
|
|
38
86
|
pass
|
|
87
|
+
|
|
88
|
+
|
|
89
|
+
# VALIDATION ERRORS
|
|
90
|
+
|
|
91
|
+
|
|
92
|
+
class HFValidationError(ValueError):
|
|
93
|
+
"""Generic exception thrown by `huggingface_hub` validators.
|
|
94
|
+
|
|
95
|
+
Inherits from [`ValueError`](https://docs.python.org/3/library/exceptions.html#ValueError).
|
|
96
|
+
"""
|