Hub Python Library documentation
管理您的 Space
管理您的 Space
在本指南中,我们将了解如何使用 huggingface_hub 管理您的 Space 运行时(secrets、hardware 和卷)。
搜索 Spaces
您可以使用 search_spaces() 在 Hub 上通过语义搜索查找 Spaces。对于多词查询,它使用基于嵌入的搜索;对于单词查询,则使用全文搜索。
>>> from huggingface_hub import search_spaces
>>> results = list(search_spaces("generate image"))
>>> results[0]
SpaceSearchResult(id='mrfakename/Z-Image-Turbo', title='Z Image Turbo', sdk='gradio', likes=2867, ...)您可以按 SDK 或标签筛选结果:
>>> results = search_spaces("chatbot", sdk="gradio", filter="mcp-server")或通过 CLI:
>>> hf spaces search "generate image"
>>> hf spaces search "chatbot" --sdk gradio --limit 5一个简单的示例:配置密钥和硬件。
下面是一个端到端的示例,用于在 Hub 上创建并配置一个 Space。
在 Hub 上创建一个 Space
>>> from huggingface_hub import HfApi
>>> repo_id = "Wauplin/my-cool-training-space"
>>> api = HfApi()
# For example with a Gradio SDK
>>> api.create_repo(repo_id=repo_id, repo_type="space", space_sdk="gradio")静态 Spaces 对所有人免费。Gradio 和 Docker Spaces 在计算资源上运行:在免费的
cpu-basic硬件上,它们需要订阅(用户为 PRO,组织为 Team 或 Enterprise),而付费硬件仅需账单(一种支付方式和预付费额度)。如果没有订阅,在cpu-basic上创建、复制或移动 Gradio 或 Docker Space 会因支付错误(HTTP 402)而失败。有关更多详细信息,请参阅 定价。
从模板创建 Space
与其从空的 Space 开始,您可以使用 Hub 上提供的官方模板(例如 JupyterLab、Gradio 聊天机器人、Streamlit 应用等)来初始化一个新的 Space。使用 list_space_templates() 列出可用模板,然后将模板的 repo_id(或其简短的 name)作为 space_template 传递给 create_repo()。请注意,space_sdk 仍然是必需的:模板用于初始化文件,而 SDK 用于设置卡片元数据。
>>> from huggingface_hub import HfApi
>>> api = HfApi()
# List available templates
>>> for template in api.list_space_templates():
... print(f"{template.name} ({template.repo_id})")
Streamlit (streamlit/streamlit-template-space)
JupyterLab (SpacesExamples/jupyterlab)
chatbot (gradio-templates/chatbot)
...
# Create a Space from a template, by repo id or by short name
>>> api.create_repo(repo_id=repo_id, repo_type="space", space_template="SpacesExamples/jupyterlab")
>>> api.create_repo(repo_id=repo_id, repo_type="space", space_template="JupyterLab")某些模板建议设置为私有(例如 JupyterLab)。如果您未显式设置可见性,此类 Spaces 将自动创建为私有。
在 CLI 中,也可以通过 hf spaces templates 和 hf repos create --template 使用相同的功能:
# List available templates
>>> hf spaces templates
NAME REPO_ID SDK PREFERRED_PRIVATE
--------------- ---------------------------------------------- ------ -----------------
Streamlit streamlit/streamlit-template-space docker
JupyterLab SpacesExamples/jupyterlab docker ✔
Argilla argilla/argilla-template-space docker
Livebook livebook-dev/livebook docker
...
# Create a Space from a template
>>> hf repos create my-jupyterlab --type space --template jupyterlab复制一个 Space
如果您希望基于现有的 Space 进行构建,而不是从头开始,这会非常有用。 如果您希望控制公共 Space 的配置/设置,这也很有用。有关更多详细信息,请参阅 duplicate_repo()。
>>> api.duplicate_repo("multimodalart/dreambooth-training", repo_type="space")使用您首选的方案上传您的代码
以下是一个示例,用于将您机器上的本地文件夹 src/ 上传到您的 Space:
>>> api.upload_folder(repo_id=repo_id, repo_type="space", folder_path="src/")在此步骤中,您的应用应该已经在 Hub 上运行了!不过,您可能希望使用密钥和升级的硬件对其进行进一步配置。
配置密钥和变量
您的 Space 可能需要一些密钥、令牌或变量才能正常运行。 有关更多详细信息,请参阅 文档。 例如,一个 HF 令牌,用于将您的 Space 生成的图像数据集上传到 Hub。
>>> api.add_space_secret(repo_id=repo_id, key="HF_TOKEN", value="hf_api_***")
>>> api.add_space_variable(repo_id=repo_id, key="MODEL_REPO_ID", value="user/repo")您可以列出已有的密钥和变量。密钥的值是只写的,因此仅返回键、描述和更新时间戳:
>>> api.get_space_secrets(repo_id=repo_id)
{'HF_TOKEN': SpaceSecret(key='HF_TOKEN', description=None, updated_at=datetime.datetime(...))}
>>> api.get_space_variables(repo_id=repo_id)
{'MODEL_REPO_ID': SpaceVariable(key='MODEL_REPO_ID', value='user/repo', description=None, updated_at=...)}Secrets 和变量也可以被删除:
>>> api.delete_space_secret(repo_id=repo_id, key="HF_TOKEN")
>>> api.delete_space_variable(repo_id=repo_id, key="MODEL_REPO_ID")在您的 Space 内部,密钥可作为环境变量使用(如果使用 Streamlit,则通过 Streamlit Secrets Management 管理)。无需通过 API 获取它们!
对您的 Space 配置(密钥或硬件)的任何更改都会触发您的应用重启。
额外提示:在创建或复制 Space 时设置密钥和变量!
在创建或复制空间时,可以设置密钥和变量:
>>> api.create_repo(
... repo_id=repo_id,
... repo_type="space",
... space_sdk="gradio",
... space_secrets=[{"key": "HF_TOKEN", "value": "hf_api_***"}, ...],
... space_variables=[{"key": "MODEL_REPO_ID", "value": "user/repo"}, ...],
... )>>> api.duplicate_repo(
... from_id=repo_id,
... repo_type="space",
... space_secrets=[{"key": "HF_TOKEN", "value": "hf_api_***"}, ...],
... space_variables=[{"key": "MODEL_REPO_ID", "value": "user/repo"}, ...],
... )配置硬件
默认情况下,您的 Space 运行在免费的 cpu-basic 硬件上(Gradio 和 Docker Spaces 需要订阅,详见上文)。您可以升级硬件以在 GPU 上运行。升级 Space 需要支付方式以及预付费额度(或社区资助)。有关更多详细信息,请参阅 文档。
# Use `SpaceHardware` enum
>>> from huggingface_hub import SpaceHardware
>>> api.request_space_hardware(repo_id=repo_id, hardware=SpaceHardware.T4_MEDIUM)
# Or simply pass a string value
>>> api.request_space_hardware(repo_id=repo_id, hardware="t4-medium")硬件更新不会立即生效,因为您的 Space 需要在我们的服务器上重新加载。 您可以随时查看您的 Space 正在运行的硬件,以确认您的请求是否已得到满足。
>>> runtime = api.get_space_runtime(repo_id=repo_id)
>>> runtime.stage
"RUNNING_BUILDING"
>>> runtime.hardware
"cpu-basic"
>>> runtime.requested_hardware
"t4-medium"您现在已经拥有一个完全配置好的 Space。使用完毕后,请务必将您的 Space 降级回 cpu-basic。
额外提示:在创建或复制 Space 时请求硬件!
硬件升级后,您的 Space 构建完成时会自动分配。
>>> api.create_repo(
... repo_id=repo_id,
... repo_type="space",
... space_sdk="gradio",
... space_hardware="cpu-upgrade",
... space_sleep_time="7200", # 2 hours in secs
... )>>> api.duplicate_repo(
... from_id=repo_id,
... repo_type="space",
... space_hardware="cpu-upgrade",
... space_sleep_time="7200", # 2 hours in secs
... )跟踪您的 ZeroGPU 配额
ZeroGPU Spaces 运行在按需分配的共享 GPU 上。每次您使用 ZeroGPU Space(通过 UI 或其 API)时,都会从您的个人配额中扣除一定的 GPU 时间,该配额会定期重置。如果您正在基于 ZeroGPU Spaces 构建应用、智能体或 MCP 服务器,可以使用 get_zero_gpu_quota() 来跟踪您的使用情况。数值以 GPU 秒为单位表示。
>>> quota = api.get_zero_gpu_quota()
>>> quota
ZeroGpuQuota(base=2400, remaining=1810, resets_at=datetime.datetime(2026, 9, 30, 9, 12, 3, tzinfo=datetime.timezone.utc), overquota_used=0)
>>> if quota.remaining < 60:
... print(f"Less than 1 minute of ZeroGPU left. Quota resets at {quota.resets_at}.")resets_at 在自上次重置以来未使用过 ZeroGPU 时为 None。如果使用细粒度令牌,该令牌必须具有“Billing > Read billing usage and payment method status”权限。相同的信息也可以通过 CLI 命令 hf spaces zero-gpu quota 获取。
配额用尽后,PRO、Team 和 Enterprise 用户可以通过消耗预付费额度继续使用 ZeroGPU Spaces。您可以从账单设置中购买额度。有关更多详细信息,请参阅使用额度扩展配额。
暂停并重启您的 Space
默认情况下,如果您的 Space 运行在升级后的硬件上,它将永远不会停止。但为了避免产生费用,您可能希望在未使用时将其暂停。这可以通过 pause_space() 实现。已暂停的 Space 将处于非活动状态,直到 Space 的所有者通过 UI 或使用 restart_space() 通过 API 将其重新启动。有关暂停模式的更多详细信息,请参阅 此部分
# Pause your Space to avoid getting billed
>>> api.pause_space(repo_id=repo_id)
# (...)
# Restart it when you need it
>>> api.restart_space(repo_id=repo_id)另一种方法是为您的 Space 设置超时时间。如果您的 Space 在超过超时时长后处于非活动状态,它将进入休眠。任何访问您 Space 的用户都会将其重新唤醒。您可以使用 set_space_sleep_time() 来设置超时时间。有关休眠模式的更多详细信息,请参阅 此部分。
# Put your Space to sleep after 1h of inactivity
>>> api.set_space_sleep_time(repo_id=repo_id, sleep_time=3600)注意:如果您使用的是‘cpu-basic’硬件,则无法配置自定义休眠时间。您的 Space 将在 48 小时无活动后自动暂停。
附加功能:在请求硬件时设置睡眠时间
硬件升级后,您的 Space 构建完成时会自动分配。
>>> api.request_space_hardware(repo_id=repo_id, hardware=SpaceHardware.T4_MEDIUM, sleep_time=3600)额外提示:在创建或复制 Space 时设置休眠时间!
>>> api.create_repo(
... repo_id=repo_id,
... repo_type="space",
... space_sdk="gradio",
... space_hardware="t4-medium",
... space_sleep_time="3600",
... )>>> api.duplicate_repo(
... from_id=repo_id,
... repo_type="space",
... space_hardware="t4-medium",
... space_sleep_time="3600",
... )通过读取日志来调试失败的 Space
当 Space 构建失败或在运行时崩溃时,您通常在浏览器中查看的日志也可以通过 fetch_space_logs() 以编程方式获取。这在无法打开浏览器的脚本或智能体工作流中尤为有用。
# Drain the currently available run logs and return immediately (like `docker logs`)
>>> for line in api.fetch_space_logs(repo_id=repo_id):
... print(line, end="")
# Read the container build logs instead (useful when the Space is stuck in BUILD_ERROR)
>>> for line in api.fetch_space_logs(repo_id=repo_id, build=True):
... print(line, end="")
# Stream run logs in real time until the server closes the stream (Ctrl-C to stop)
>>> for line in api.fetch_space_logs(repo_id=repo_id, follow=True):
... print(line, end="")相同的功能也可以通过命令行界面使用:
hf spaces logs username/my-space # drain run logs
hf spaces logs username/my-space --build # read build logs
hf spaces logs username/my-space -f # stream in real time
hf spaces logs username/my-space -n 50 # last 50 lines only通过 SSH 连接到 Space(开发模式)
开发模式允许你通过 SSH 连接到正在运行的 Space 容器,以便进行实时调试和开发。使用 hf spaces ssh 可以直接从终端打开一个会话。如果该 Space 尚未启用开发模式,CLI 会提示你启用它(或者传入 --auto 以跳过提示)。
您的 SSH 公钥必须在您的设置中注册。
# SSH into a Space (enables Dev Mode if needed)
hf spaces ssh username/my-space
# Auto-enable Dev Mode without prompting
hf spaces ssh username/my-space --auto
# Print the SSH command without running it
hf spaces ssh username/my-space --dry-run
# Use a specific SSH key
hf spaces ssh username/my-space -i ~/.ssh/id_ed25519您也可以在不使用 SSH 的情况下,通过 hf spaces dev-mode 启用开发模式,该命令会打印出用于 SSH、VS Code、Cursor 和 Windsurf 的连接说明:
hf spaces dev-mode username/my-space
启用 Dev Mode 需要 PRO 或 Team & Enterprise 套餐。禁用 Dev Mode 始终被允许,例如,如果在 Dev Mode 开启期间您的订阅已过期:
hf spaces dev-mode username/my-space --stop
在您的 Space 中挂载卷
您可以将 Hub 资源(模型、数据集或存储桶)作为卷挂载到 Space 的容器中。这样,您的 Space 就可以直接通过文件系统访问这些资源,而无需在代码中下载它们。在创建或复制 Space 时,可以直接设置卷:
>>> from huggingface_hub import Volume
>>> api.create_repo(
... repo_id=repo_id,
... repo_type="space",
... space_sdk="gradio",
... space_volumes=[
... Volume(type="model", source="username/my-model", mount_path="/models", read_only=True),
... Volume(type="bucket", source="username/my-bucket", mount_path="/data"),
... ],
... )>>> api.duplicate_repo(
... from_id=repo_id,
... repo_type="space",
... space_volumes=[
... Volume(type="model", source="username/my-model", mount_path="/models", read_only=True),
... Volume(type="bucket", source="username/my-bucket", mount_path="/data"),
... ],
... )您可以通过 Space 运行时检查当前挂载了哪些卷:
>>> runtime = api.get_space_runtime(repo_id=repo_id)
>>> runtime.volumes
[Volume(type='model', source='username/my-model', mount_path='/models', read_only=True), ...]如果需要更新现有 Space 上的卷,请使用 set_space_volumes()。请注意,此操作会替换所有先前挂载的卷。
>>> api.set_space_volumes(
... repo_id=repo_id,
... volumes=[
... Volume(type="model", source="username/my-model", mount_path="/models", read_only=True),
... Volume(type="dataset", source="username/my-dataset", mount_path="/data", read_only=True),
... Volume(type="bucket", source="username/my-bucket", mount_path="/output"),
... ],
... )要从您的 Space 中移除所有卷:
>>> api.delete_space_volumes(repo_id=repo_id)模型、数据集和 Spaces 始终以只读方式挂载。只有存储桶支持读写挂载。
设置卷会替换之前挂载的所有卷。若要向现有列表中添加卷,请先从运行时读取当前卷,并将其包含在新列表中。
所有卷操作也可从命令行界面(CLI)中调用:
# List current volumes
hf spaces volumes ls username/my-space
# Set (replace) volumes
hf spaces volumes set username/my-space \
-v hf://models/username/my-model:/models \
-v hf://buckets/username/my-bucket:/data
# Remove all volumes
hf spaces volumes delete username/my-space更高级的操作:临时升级你的 Space!
Spaces 支持多种不同的使用场景。有时,您可能希望临时在特定硬件上运行一个 Space,完成某些操作后再将其关闭。在本节中,我们将探讨如何利用 Spaces 按需微调模型。这只是解决该特定问题的一种方法,应将其视为一种建议,并根据您的具体使用场景进行调整。
假设我们有一个用于微调模型的 Space。它是一个 Gradio 应用,接收模型 ID 和数据集 ID 作为输入。工作流程如下:
- (提示用户输入模型和数据集)
- 从 Hub 加载模型。
- 从 Hub 加载数据集。
- 在数据集上微调模型。
- 将新模型上传到 Hub。
步骤 3. 需要自定义硬件,但你又不希望你的 Space 一直在付费 GPU 上运行。一种解决方案是动态请求用于训练的硬件,并在训练结束后将其关闭。由于请求硬件会重启你的 Space,你的应用必须以某种方式“记住”当前正在执行的任务。实现这一点有多种方法。在本指南中,我们将展示一种使用 Dataset 作为“任务调度器”的解决方案。
应用骨架
以下是您的应用运行时的样子。启动时,检查是否有已调度的任务,如果有,则在正确的硬件上运行它。完成后,将硬件重置为空闲的 cpu-basic CPU,并提示用户输入新任务。
此类工作流不支持像普通演示那样进行并发访问。 特别是,在训练发生时,界面将被禁用。 建议将您的仓库设置为私有,以确保您是唯一的使用者。
# Space will need your token to request hardware: set it as a Secret !
HF_TOKEN = os.environ.get("HF_TOKEN")
# Space own repo_id
TRAINING_SPACE_ID = "Wauplin/dreambooth-training"
from huggingface_hub import HfApi, SpaceHardware
api = HfApi(token=HF_TOKEN)
# On Space startup, check if a task is scheduled. If yes, finetune the model. If not,
# display an interface to request a new task.
task = get_task()
if task is None:
# Start Gradio app
def gradio_fn(task):
# On user request, add task and request hardware
add_task(task)
api.request_space_hardware(repo_id=TRAINING_SPACE_ID, hardware=SpaceHardware.T4_MEDIUM)
gr.Interface(fn=gradio_fn, ...).launch()
else:
runtime = api.get_space_runtime(repo_id=TRAINING_SPACE_ID)
# Check if Space is loaded with a GPU.
if runtime.hardware == SpaceHardware.T4_MEDIUM:
# If yes, finetune base model on dataset !
train_and_upload(task)
# Then, mark the task as "DONE"
mark_as_done(task)
# DO NOT FORGET: set back CPU hardware
api.request_space_hardware(repo_id=TRAINING_SPACE_ID, hardware=SpaceHardware.CPU_BASIC)
else:
api.request_space_hardware(repo_id=TRAINING_SPACE_ID, hardware=SpaceHardware.T4_MEDIUM)任务调度器
任务调度可以通过多种方式实现。下面是一个使用以 Dataset 形式存储的简单 CSV 文件来完成任务调度的示例。
# Dataset ID in which a `tasks.csv` file contains the tasks to perform.
# Here is a basic example for `tasks.csv` containing inputs (base model and dataset)
# and status (PENDING or DONE).
# multimodalart/sd-fine-tunable,Wauplin/concept-1,DONE
# multimodalart/sd-fine-tunable,Wauplin/concept-2,PENDING
TASK_DATASET_ID = "Wauplin/dreambooth-task-scheduler"
def _get_csv_file():
return hf_hub_download(repo_id=TASK_DATASET_ID, filename="tasks.csv", repo_type="dataset", token=HF_TOKEN)
def get_task():
with open(_get_csv_file()) as csv_file:
csv_reader = csv.reader(csv_file, delimiter=',')
for row in csv_reader:
if row[2] == "PENDING":
return row[0], row[1] # model_id, dataset_id
def add_task(task):
model_id, dataset_id = task
with open(_get_csv_file()) as csv_file:
with open(csv_file, "r") as f:
tasks = f.read()
api.upload_file(
repo_id=repo_id,
repo_type=repo_type,
path_in_repo="tasks.csv",
# Quick and dirty way to add a task
path_or_fileobj=(tasks + f"\n{model_id},{dataset_id},PENDING").encode()
)
def mark_as_done(task):
model_id, dataset_id = task
with open(_get_csv_file()) as csv_file:
with open(csv_file, "r") as f:
tasks = f.read()
api.upload_file(
repo_id=repo_id,
repo_type=repo_type,
path_in_repo="tasks.csv",
# Quick and dirty way to set the task as DONE
path_or_fileobj=tasks.replace(
f"{model_id},{dataset_id},PENDING",
f"{model_id},{dataset_id},DONE"
).encode()
)