Hub Python Library documentation

Jobs 실행 및 관리

Hugging Face's logo
Join the Hugging Face community

and get access to the augmented documentation experience

to get started

Jobs 실행 및 관리

Hugging Face Hub는 Jobs를 통해 AI 및 데이터 워크플로우에 대한 컴퓨트를 제공합니다.

Jobs와 가격에 대한 일반적인 개요는 Hub Jobs 문서를 참고하세요.

Job은 Hugging Face 인프라에서 실행되며, 실행할 명령(예: python 명령), Hugging Face Spaces 또는 Docker Hub의 Docker Image, 그리고 하드웨어 flavor(CPU, GPU, TPU)로 정의됩니다. 이 가이드에서는 Hub에서 Job을 사용하는 방법을, 특히 다음을 중심으로 보여 드립니다:

  • job을 실행합니다.
  • 작업 상태를 확인합니다.
  • 하드웨어를 선택합니다.
  • 환경 변수와 시크릿을 구성합니다.
  • UV 스크립트를 실행합니다.

Hub에서 작업을 실행하고 관리하려면 머신이 로그인되어 있어야 합니다. 로그인되어 있지 않다면 이 섹션을 참조하세요. 이 가이드의 나머지 부분에서는 머신이 로그인되어 있다고 가정합니다.

Hugging Face Jobs는 크레딧 잔액이 양수인 모든 사용자 또는 조직에서 사용할 수 있습니다. 자세한 내용은 Jobs 가격 및 청구를 참조하세요.

Jobs 명령줄 인터페이스

hf jobs CLI를 사용하여 명령줄에서 Jobs를 실행하고, --flavor를 전달하여 하드웨어를 지정합니다.

hf jobs run은 Docker 이미지와 명령어를 사용하여 익숙한 Docker와 유사한 인터페이스로 Jobs를 실행합니다. docker run처럼 생각하되, 모든 하드웨어에서 코드를 실행하는 용도로 사용됩니다:

>>> hf jobs run --name hello-world python:3.12 python -c "print('Hello world')"
>>> hf jobs run --name gpu-check --flavor a10g-small pytorch/pytorch:2.6.0-cuda12.4-cudnn9-devel python -c "import torch; print(torch.cuda.get_device_name())"

hf jobs uv run를 사용하여 로컬 또는 원격 UV 스크립트를 실행합니다:

>>> hf jobs uv run --name my-script my_script.py
>>> hf jobs uv run --name sft-training --flavor a10g-small "https://raw.githubusercontent.com/huggingface/trl/main/trl/scripts/sft.py"

UV 스크립트는 UV 문서에서 정의한 특수한 주석 문법을 사용하여 파일 내에 직접 의존성을 포함하는 Python 스크립트입니다.

이제 나머지 가이드에서는 Python API를 보여드립니다. 대신 사용 가능한 모든 hf jobs 명령어와 옵션을 확인하려면 hf jobs 명령줄 인터페이스 가이드를 참고하세요.

Need an interactive machine instead of a fire-and-forget job — e.g. to run AI-generated code, with command execution and file transfer? Check out Sandboxes, built on top of Jobs.

Job 실행

명령어와 Docker Image로 정의된 compute Jobs를 Hugging Face 인프라(GPU 및 TPU 포함)에서 실행합니다.

사용자가 소유한 Job(사용자 이름 네임스페이스 아래) 또는 쓰기 권한이 있는 조직의 Job만 관리할 수 있습니다. 이 기능은 사용량 과금 방식입니다: 사용한 초당만 과금됩니다.

run_job()을 사용하면 Hugging Face 인프라에서 원하는 명령을 실행할 수 있습니다:

# Directly run Python code
>>> from huggingface_hub import run_job
>>> run_job(
...     image="python:3.12",
...     command=["python", "-c", "print('Hello from the cloud!')"],
... )

# Use GPUs without any setup
>>> run_job(
...     image="pytorch/pytorch:2.6.0-cuda12.4-cudnn9-devel",
...     command=["python", "-c", "import torch; print(torch.cuda.get_device_name())"],
...     flavor="a10g-small",
... )

# Run in an organization account
>>> run_job(
...     image="python:3.12",
...     command=["python", "-c", "print('Running in an org account')"],
...     namespace="my-org-name",
... )

# Run from Hugging Face Spaces
>>> run_job(
...     image="hf.co/spaces/lhoestq/duckdb",
...     command=["duckdb", "-c", "select 'hello world'"],
... )

# Run a Python script with `uv` (experimental)
>>> from huggingface_hub import run_uv_job
>>> run_uv_job("my_script.py")

중요: Job에는 기본 타임아웃(30분)이 설정되어 있으며, 해당 시간이 지나면 자동으로 중단됩니다. 모델 학습과 같은 장기 실행 작업의 경우, timeout 매개변수를 사용하여 사용자 지정 타임아웃을 설정해야 합니다. 자세한 내용은 Job 타임아웃 구성을 참조하세요.

run_job()은 Hugging Face에서 Job의 URL을 포함하는 JobInfo를 반환하며, 여기서 Job 상태와 로그를 확인할 수 있습니다. Job을 관리하려면 JobInfo에서 Job ID를 저장하세요:

>>> from huggingface_hub import run_job
>>> job = run_job(
...     image="python:3.12",
...     command=["python", "-c", "print('Hello from the cloud!')"]
... )
>>> job.url
https://huggingface.co/jobs/lhoestq/687f911eaea852de79c4a50a
>>> job.id
687f911eaea852de79c4a50a

Jobs는 백그라운드에서 실행됩니다. 다음 섹션에서는 inspect_job()을 사용하여 Job의 상태를 확인하고, fetch_job_logs()을 사용하여 로그를 표시하며, fetch_job_metrics()을 사용하여 리소스 사용량을 모니터링하는 방법을 안내합니다.

Job 재시도 및 재실행

attempts를 사용하여 실패한 Job을 재시도합니다. 이 숫자는 초기 시도를 포함하므로 attempts=3이면 최대 두 번까지 재시도할 수 있습니다. run_uv_job, create_scheduled_job, create_scheduled_uv_job에서도 사용할 수 있습니다.

>>> from huggingface_hub import rerun_job, run_job
>>> job = run_job(image="python:3.12", command=["python", "train.py"], attempts=3)
>>> job.retry
2

# Start a new Job with the same spec, including its retry setting
>>> new_job = rerun_job(job_id=job.id)

rerun_job은 새로운 ID를 가진 별도의 Job을 시작합니다. 완료되거나 실패한 Job에 적용되며, secrets와 하드웨어 설정을 포함한 저장된 spec을 재사용합니다. hf jobs rerun <job_id>을 실행하는 것도 가능합니다.

Job 상태 확인

# List your jobs (results are paginated and returned as an iterator)
>>> from huggingface_hub import list_jobs
>>> jobs = list_jobs()
>>> next(iter(jobs))
JobInfo(id='687f911eaea852de79c4a50a', created_at=datetime.datetime(2025, 7, 22, 13, 24, 46, 909000, tzinfo=datetime.timezone.utc), docker_image='python:3.12', space_id=None, command=['python', '-c', "print('Hello from the cloud!')"], arguments=[], environment={}, secrets={}, flavor='cpu-basic', status=JobStatus(stage='COMPLETED', message=None), owner=JobOwner(id='5e9ecfc04957053f60648a3e', name='lhoestq'), endpoint='https://huggingface.co', url='https://huggingface.co/jobs/lhoestq/687f911eaea852de79c4a50a')

# Materialize the iterator into a list
>>> all_jobs = [job for job in list_jobs()]

# List your running jobs
>>> running_jobs = list_jobs(status="RUNNING")

# Filter by one or more statuses and/or labels
>>> list_jobs(status=["RUNNING", "SCHEDULING"], labels={"env": "prod"})

# Inspect the status of a job
>>> from huggingface_hub import inspect_job
>>> inspect_job(job_id=job_id)
JobInfo(id='687f911eaea852de79c4a50a', created_at=datetime.datetime(2025, 7, 22, 13, 24, 46, 909000, tzinfo=datetime.timezone.utc), docker_image='python:3.12', space_id=None, command=['python', '-c', "print('Hello from the cloud!')"], arguments=[], environment={}, secrets={}, flavor='cpu-basic', status=JobStatus(stage='COMPLETED', message=None), owner=JobOwner(id='5e9ecfc04957053f60648a3e', name='lhoestq'), endpoint='https://huggingface.co', url='https://huggingface.co/jobs/lhoestq/687f911eaea852de79c4a50a')

# View logs from a job
>>> from huggingface_hub import fetch_job_logs
>>> for log in fetch_job_logs(job_id=job_id):
...     print(log)
Hello from the cloud!

# View resources usage metrics from a job
>>> from huggingface_hub import fetch_job_metrics
>>> for metrics in fetch_job_metrics(job_id=job_id):
...     print(metrics)
{
    "cpu_usage_pct": 0,
    "cpu_millicores": 2000,
    "memory_used_bytes": 929792,
    "memory_total_bytes": 17179869184,
    "rx_bps": 0,
    "tx_bps": 0,
    "gpus": {},
    "replica": "4dzsh"
}

# Cancel a job
>>> from huggingface_hub import cancel_job
>>> cancel_job(job_id=job_id)

Jobs가 완료될 때까지 기다립니다

Job이 종료 단계(COMPLETED, CANCELED, ERROR 또는 DELETED)에 도달할 때까지 블로킹하려면 wait_for_job()를 사용하세요. 최종 JobInfo는 항상 반환되며, 실패한 Job은 예외를 발생시키지 않으므로 결과를 처리하려면 job.status.stage를 확인해야 합니다. Job ID 목록을 전달하면 배치 전체를 한 번에 대기할 수 있습니다.

>>> from huggingface_hub import run_job, wait_for_job
>>> job = run_job(image="python:3.12", command=["python", "-c", "print('hello')"])
>>> wait_for_job(job_id=job.id).status.stage
'COMPLETED'

# Run multiple jobs in parallel and wait for all of them to finish
>>> jobs = [run_job(image=image, command=command) for command in commands]
>>> finished_jobs = wait_for_job(job_id=[job.id for job in jobs], timeout=3600)

CLI에서도 hf jobs wait로 동일한 기능을 사용할 수 있으며, 모든 Job이 성공적으로 완료된 경우에만 종료 코드 0을 반환합니다. 셸 스크립트나 CI에서 명령을 연쇄 실행할 때 유용합니다:

# Chain on success
hf jobs wait <job_id> && hf jobs run --detach python:3.12 python eval.py

# Wait for all currently running jobs
hf jobs ls -q | xargs hf jobs wait

Job이 실패하면 0이 아닌 코드로 종료되므로, 비디텍치드 hf jobs run (또는 hf jobs uv run)의 경우에도 hf jobs run ... && next-step이 명시적인 대기 없이 올바르게 체인됩니다.

하드웨어 선택

GPU에서 Jobs를 실행하는 것이 유용한 경우는 다음과 같습니다:

  • 모델 학습: 인프라를 관리하지 않고 GPU(T4, A10G, A100)에서 모델을 파인튜닝하거나 학습합니다
  • 합성 데이터 생성: 강력한 하드웨어에서 LLM을 사용하여 대규모 데이터셋 생성
  • 데이터 처리: 대규모 데이터셋을 병렬 워크로드를 위해 고 CPU 구성으로 처리
  • 배치 추론: 최적화된 GPU 구성을 사용하여 수천 개의 샘플에 대해 오프라인 추론을 실행
  • 실험 및 벤치마크: 재현 가능한 결과를 위해 일관된 하드웨어에서 ML 실험을 실행합니다
  • 개발 및 디버깅: 로컬 CUDA 설정 없이 GPU 코드 테스트

flavor 인수를 사용하여 GPU 또는 TPU에서 작업을 실행합니다. 예를 들어, A10G GPU에서 PyTorch 작업을 실행하려면:

# Use an A10G GPU to check PyTorch CUDA
>>> from huggingface_hub import run_job
>>> run_job(
...     image="pytorch/pytorch:2.6.0-cuda12.4-cudnn9-devel",
...     command=["python", "-c", "import torch; print(f'This code ran with the following GPU: {torch.cuda.get_device_name()}')"],
...     flavor="a10g-small",
... )

이것을 실행하면 다음과 같은 출력이 표시됩니다!

This code ran with the following GPU: NVIDIA A10G

UV로 trl/scripts/sft.py와 같은 파인튜닝 스크립트를 실행하려면 다음을 사용하세요:

>>> from huggingface_hub import run_uv_job
>>> run_uv_job(
...     "sft.py",
...     script_args=["--model_name_or_path", "Qwen/Qwen2-0.5B", ...],
...     dependencies=["trl"],
...     env={"HF_TOKEN": ...},
...     flavor="a10g-small",
... )

Hugging Face 인프라에서 TRL로 모델 학습 작업을 실행하는 방법에 대한 종합적인 가이드는 TRL Jobs Training 문서를 참고하세요. 이 문서에는 파인튜닝 레시피, 하드웨어 선택, 그리고 모델을 효율적으로 학습하기 위한 모범 사례가 포함되어 있습니다.

Jobs를 실행할 수 있는 사용 가능한 하드웨어 전체 목록은 다음과 같습니다:

이름이름cpuram저장accelerator비용/분시간당 비용
cpu-basicCPU 기본2 vCPU16 GB50 GB-$0.0002$0.01
cpu-upgradeCPU 업그레이드8 vCPU32 GB50 GB-$0.0005$0.03
cpu-performanceCPU 성능32 vCPU256 GB1024 GB-$0.0317$1.90
cpu-xlCPU XL16 vCPU124 GB1000 GB-$0.0167$1.00
t4-smallNvidia T4 - 소형4 vCPU15 GB50 GBT4 1개 (16 GB)$0.0067$0.40
t4-mediumNvidia T4 - 중간8 vCPU30 GB100 GBT4 1개 (16 GB)$0.0100$0.60
a10g-smallNvidia A10G - 소형4 vCPU15 GB110 GBA10G (24 GB) 1개$0.0167$1.00
a10g-largeNvidia A10G - 대형12 vCPU46 GB200 GBA10G (24 GB) 1개$0.0250$1.50
a10g-largex22x Nvidia A10G - 대형24 vCPU92 GB1000 GB2x A10G (48 GB)$0.0500$3.00
a10g-largex44x Nvidia A10G - 대형48 vCPU184 GB2000 GB4x A10G (96 GB)$0.0833$5.00
a100-largeNvidia A100 - 대형12 vCPU142 GB1000 GBA100 (80 GB) 1개$0.0417$2.50
a100x4Nvidia A100 4개48 vCPU568 GB4000 GB4x A100 (320 GB)$0.1667$10.00
a100x88x Nvidia A10096 vCPU1136 GB8000 GB8x A100 (640 GB)$0.3333$20.00
h200Nvidia H20023 vCPU256 GB3000 GB1x H200 (141 GB)$0.0833$5.00
h200x2Nvidia H20046 vCPU512 GB6000 GB2x H200 (282 GB)$0.1667$10.00
h200x4Nvidia H20092 vCPU1024 GB12000 GB4x H200 (564 GB)$0.3333$20.00
h200x8Nvidia H200184 vCPU2048 GB24000 GB8x H200 (1128 GB)$0.6667$40.00
rtx-pro-6000Nvidia RTX PRO 600023 vCPU256 GB475 GB1x RTX PRO 6000 (96 GB)$0.0458$2.75
rtx-pro-6000x2Nvidia RTX PRO 600046 vCPU512 GB950 GB2x RTX PRO 6000 (192 GB)$0.0917$5.50
rtx-pro-6000x4Nvidia RTX PRO 600092 vCPU1024 GB1900 GB4x RTX PRO 6000 (384 GB)$0.1833$11.00
rtx-pro-6000x8Nvidia RTX PRO 6000184 vCPU2048 GB3800 GB8x RTX PRO 6000 (768 GB)$0.3667$22.00
l4x1Nvidia L4 1개8 vCPU30 GB400 GBL4 1개 (24 GB)$0.0133$0.80
l4x4Nvidia L4 4개48 vCPU186 GB3200 GB4x L4 (96 GB)$0.0633$3.80
l40sx1Nvidia L40S 1개8 vCPU62 GB380 GBL40S 1개 (48 GB)$0.0300$1.80
l40sx4Nvidia L40S 4개48 vCPU382 GB3200 GB4x L40S (192 GB)$0.1383$8.30
l40sx88x Nvidia L40S192 vCPU1534 GB6500 GB8x L40S (384 GB)$0.3917$23.50

다음 명령을 실행하여 이 목록을 프로그래밍 방식으로 가져올 수 있습니다:

>>> hf jobs hardware

또는 Python API를 사용하여:

>>> from huggingface_hub import list_jobs_hardware
>>> list_jobs_hardware()

이것으로 끝입니다! 이제 Hugging Face의 인프라에서 코드를 실행하고 있습니다.

볼륨 마운트

Volume 목록을 사용하여 Jobs의 디스크에 볼륨을 마운트합니다.

Hugging Face 리포지토리(모델/데이터셋/스페이스) 또는 Storage Bucket를 마운트할 수 있습니다. 예를 들어:

  • 모델 저장소 마운트: Volume(type="model", source="openai/gpt-oss-120b", mount_path="/model")
  • 데이터셋 저장소를 마운트: Volume(type="dataset", source="HuggingFaceFW/fineweb", mount_path="/data")
  • 스토리지 버킷 마운트: Volume(type="bucket", source="username/my-bucket", mount_path="/mnt")

그런 다음 마운트된 볼륨을 로컬 디렉터리로 사용할 수 있습니다:

>>> from huggingface_hub import run_job, Volume
>>> job = run_job(
...     image="duckdb/duckdb",
...     command=["duckdb", "-c", "SELECT * FROM '/data/**/*.parquet' LIMIT 5"],
...     volumes=[Volume(type="dataset", source="HuggingFaceFW/fineweb", mount_path="/data")],
... )

마운트된 버킷에 쓸 수도 있습니다. 예를 들어, 모델을 학습하는 동안 체크포인트를 저장하는 용도로 사용할 수 있습니다:

>>> from huggingface_hub import run_uv_job, Volume
>>> script = "my_sft.py"
>>> script_args = ["--output_dir", "/training-outputs/training-v3-final", ...]
>>> checkpoints_bucket = Volume(type="bucket", source="username/my-bucket", mount_path="/training-outputs")
>>> run_uv_job(script, script_args=script_args, volumes=[checkpoints_bucket])

기본적으로 마운트된 스토리지 버킷은 읽기 및 쓰기 권한을 가집니다. 이는 데이터가 자주 변경되는 경우 빠른 변경 가능한 스토리지를 제공하는 스토리지 버킷에 특히 유용하며, 파일을 원위치에서 덮어쓰기하거나 삭제할 수 있습니다.

읽기 전용을 활성화하려면 read_only=True를 사용하세요: Volume(type="bucket", read_only=True, ...).

로컬 데이터 마운트

로컬 머신의 데이터를 대상으로 Job을 실행하려면 sync_job_volume()를 사용하세요. 이 함수는 로컬 디렉토리를 jobs-artifacts Storage Bucket(필요 시 자동으로 생성됨)에 동기화하고 마운트할 준비가 된 Volume을 반환합니다:

>>> from huggingface_hub import run_uv_job, sync_job_volume

# Upload ./training-data once...
>>> volume = sync_job_volume("./training-data", "/data")

# ...then run as many Jobs as you want against it
>>> run_uv_job("train.py", script_args=["--learning-rate", "0.01"], volumes=[volume])
>>> run_uv_job("train.py", script_args=["--learning-rate", "0.05"], volumes=[volume])

각 디렉터리는 버킷에서 고유한 안정적인 폴더를 사용합니다. 동일한 디렉터리에 대해 sync_job_volume()을 다시 실행해도 새로 추가되거나 수정된 파일만 업로드됩니다. 볼륨은 기본적으로 읽기 전용으로 마운트됩니다.

Job이 작성한 파일을 가져오려면 읽기/쓰기 볼륨(빈 출력 디렉터리도 사용 가능)을 마운트한 후, Job이 종료되면 해당 볼륨을 다시 동기화하세요:

>>> from huggingface_hub import run_uv_job, sync_bucket, sync_job_volume

>>> outputs = sync_job_volume("./outputs", "/outputs", read_only=False)
>>> job = run_uv_job("process.py", volumes=[outputs])

# ...once the Job completes, pull back the data:
>>> sync_bucket(f"hf://buckets/{outputs.source}/{outputs.path}", "./outputs")

CLI에서 -v의 소스 측으로 로컬 디렉토리를 전달하면 됩니다:

>>> hf jobs uv run -v ./pdfs:/input -v ./md-out:/output:rw ocr.py

Job 포트 노출

Jobs 프록시를 통해 컨테이너 포트에 접근할 수 있도록 하려면 expose를 전달하세요. 접근하려면 Job의 namespace에 대한 읽기 권한이 있는 HF 토큰이 필요합니다. 인증 없이 접근을 허용하려면 대신 expose_public을 사용하세요:

>>> from huggingface_hub import run_job, update_job_expose
>>> job = run_job(
...     image="python:3.12",
...     command=["python", "-m", "http.server", "8000"],
...     expose_public=[8000],
... )
>>> job.expose_public
[8000]

# Keep the port exposed, but require an HF token from now on
>>> job = update_job_expose(job_id=job.id, expose=[8000])

# Close all exposed ports
>>> job = update_job_expose(job_id=job.id)

expose와 expose_public는 함께 사용할 수 있습니다. update_job_expose는 재시작 없이 실행 중인 Job의 전체 포트 구성을 대체하며, 두 목록에 모두 없는 포트는 닫힙니다. 두 옵션은 UV 및 예약 Job을 생성할 때도 사용할 수 있습니다.

Job에 SSH로 접속

ssh=True를 run_job()(또는 run_uv_job())에 전달하여 Job 컨테이너를 SSH로 접근 가능하게 만듭니다. SSH 엔드포인트는 Job 상태에 표시됩니다:

>>> from huggingface_hub import run_job
>>> job = run_job(
...     image="python:3.12",
...     command=["sleep", "infinity"],
...     ssh=True,
... )
>>> job.status.ssh_url
'ssh://68498e23210b3a4f4e6e2a23@ssh.hf.jobs'

터미널에서 hf jobs ssh <job_id>(또는 ssh <job_id>@ssh.hf.jobs로 직접) 연결합니다:

>>> hf jobs ssh 68498e23210b3a4f4e6e2a23

Job의 namespace에 쓰기 권한이 있는 사용자만(Job 생성자 또는 소유 조직의 멤버) https://huggingface.co/settings/keys에 등록된 SSH 공개 키로 인증되어 접근할 수 있습니다.

네트워크 그룹

network_group="<name>"을 run_job()(또는 run_uv_job())에 전달하면 같은 namespace와 resource group에 있는 Jobs가 모든 포트에서 서로 통신할 수 있습니다. 각 멤버 내부에서 HF_NETWORK_GROUP_HOSTNAME은 그룹의 모든 Job으로 해석되며, ${HF_NETWORK_GROUP_PREFIX}<alias>는 network_aliases=[...]로 alias를 선언한 멤버로 해석됩니다:

>>> from huggingface_hub import run_job
>>> server = run_job(
...     image="python:3.12",
...     command=["python", "-m", "http.server", "8000"],
...     network_group="train",
...     network_aliases=["master"],
... )
>>> client = run_job(
...     image="python:3.12",
...     command=["sh", "-c", 'curl --retry 10 --retry-connrefused "http://${HF_NETWORK_GROUP_PREFIX}master:8000/"'],
...     network_group="train",
... )
>>> server.network
JobNetwork(group='train', aliases=['master'])

멤버는 준비가 완료되기 전에도 해석될 수 있으므로, 재시도(retry)를 사용하여 연결하세요. 그룹 이름과 별칭은 소문자 영숫자 및 대시(-)로만 구성되며, 최대 길이는 각각 46자 및 34자입니다.

작업 시간 초과 구성

Jobs에는 기본 타임아웃(30분)이 있으며, 이 시간이 지나면 자동으로 중지됩니다. 모델 학습과 같은 장기 실행 작업을 수행할 때 이 점을 알아두는 것이 중요합니다.

사용자 지정 타임아웃 설정

timeout 매개변수를 사용하여 작업을 실행할 때 사용자 지정 타임아웃 값을 지정할 수 있습니다. 타임아웃은 두 가지 방식으로 지정할 수 있습니다:

  1. 숫자 (초로 해석):
>>> from huggingface_hub import run_job
>>> job = run_job(
...     image="pytorch/pytorch:2.6.0-cuda12.4-cudnn9-devel",
...     command=["python", "train_model.py"],
...     flavor="a10g-large",
...     timeout=7200,  # 2 hours in seconds
... )
  1. 시간 단위를 가진 문자열로:
>>> # Using different time units
>>> job = run_job(
...     image="pytorch/pytorch:2.6.0-cuda12.4-cudnn9-devel",
...     command=["python", "train_model.py"],
...     flavor="a10g-large",
...     timeout="2h",  # 2 hours
... )

>>> # Other examples:
>>> # timeout="30m"    # 30 minutes
>>> # timeout="1.5h"   # 1.5 hours
>>> # timeout="1d"     # 1 day
>>> # timeout="3600s"  # 3600 seconds

지원되는 시간 단위:

  • s - 초
  • m - 분
  • h - 시간
  • d - 일

UV 작업에서 timeout 사용

UV 작업의 경우, 타임아웃도 지정할 수 있습니다:

>>> from huggingface_hub import run_uv_job
>>> job = run_uv_job(
...     "training_script.py",
...     flavor="a10g-large",
...     timeout="90m",  # 90 minutes
... )

timeout을 지정하지 않으면 작업에 기본 timeout이 적용됩니다. 수 시간 이상 걸릴 수 있는 모델 학습과 같은 장기 실행 작업의 경우, 예상치 못한 작업 종료를 방지하기 위해 적절한 timeout을 설정하세요.

작업 시간 모니터링

긴 작업을 실행할 때 다음을 수행하는 것이 좋습니다:

  • job의 예상 실행 시간을 추정하고, 여유 시간을 포함하여 timeout을 설정하세요
  • 로그를 통해 작업 진행 상황을 모니터링합니다
  • 작업이 시간 초과되지 않았는지 확인하려면 작업 상태를 확인하세요
>>> from huggingface_hub import inspect_job, fetch_job_logs
>>> # Check job status
>>> job_info = inspect_job(job_id=job.id)
>>> if job_info.status.stage == "ERROR":
...     print(f"Job failed: {job_info.status.message}")
...     # Check logs for more details
...     for log in fetch_job_logs(job_id=job.id):
...         print(log)

timeout 파라미터에 대한 자세한 내용은 run_job API 참고 문서를 참조하세요.

환경 변수 및 Secrets 전달

env와 secrets를 사용하여 작업에 환경 변수를 전달할 수 있습니다:

# Pass environment variables
>>> from huggingface_hub import run_job
>>> run_job(
...     image="python:3.12",
...     command=["python", "-c", "import os; print(os.environ['FOO'], os.environ['BAR'])"],
...     env={"FOO": "foo", "BAR": "bar"},
... )
# Pass secrets - they will be encrypted server side
>>> from huggingface_hub import run_job
>>> run_job(
...     image="python:3.12",
...     command=["python", "-c", "import os; print(os.environ['MY_SECRET'])"],
...     secrets={"MY_SECRET": "psswrd"},
... )

내장 환경 변수

컨테이너 내부에서 다음 환경 변수가 자동으로 사용 가능합니다:

변수설명
JOB_ID현재 작업의 고유 식별자입니다. 이를 사용하여 작업을 프로그래매틱하게 참조할 수 있으며, 예를 들어 고유한 이름으로 데이터셋에 출력을 저장하는 데 사용할 수 있습니다.
ACCELERATOR사용 가능한 가속기의 유형(예: t4-medium, a10g-small, a100x4). 가속기가 없으면 비어 있습니다.
CPU_CORES작업에 사용할 수 있는 CPU 코어의 수 (예: 2, 4, 8).
MEMORY작업에 사용할 수 있는 메모리 양(예: 16Gi, 32Gi).
# Access job environment information
>>> from huggingface_hub import run_job
>>> run_job(
...     image="python:3.12",
...     command=["python", "-c", """
... import os
... print(f"Job ID: {os.environ.get('JOB_ID')}")
... print(f"Accelerator: {os.environ.get('ACCELERATOR', 'none')}")
... print(f"CPU cores: {os.environ.get('CPU_CORES')}")
... print(f"Memory: {os.environ.get('MEMORY')}")
... """],
... )

이 변수들은 출력을 위한 고유 식별자를 생성하거나, 사용 가능한 하드웨어에 따라 코드를 조정하거나, 리소스 정보를 기록할 필요가 있을 때 유용합니다.

레이블

Labels는 Job에 메타데이터를 연결하는 key=value 쌍입니다:

UI에서 Jobs를 더 쉽게 찾고 식별할 수 있도록 name을 사용하세요. 이름은 선택 사항이며 고유할 필요가 없습니다:

>>> from huggingface_hub import run_job
>>> run_job(name="daily-report", image="python:3.12", command=["python", "report.py"])

CLI에서 --name를 전달하여 Job을 생성하거나, labels 명령을 통해 기존 Job에 이름을 지정합니다:

>>> hf jobs run --name daily-report python:3.12 python report.py
>>> hf jobs labels <job_id> --name daily-report

hf jobs ls는 NAME 열을 표시하며 이름으로 필터링할 수 있습니다(--label name=NAME의 단축어):

>>> hf jobs ls -a --name daily-report
# Pass extra metadata with Labels
>>> from huggingface_hub import run_job
>>> run_job(
...     image="python:3.12",
...     command=["python", "-c", "import os; print(os.environ['MY_SECRET'])"],
...     labels={"my-label": "my-value", "foo": "bar"},
... )

이름을 전달하지 않으면 Docker 이미지 또는 스크립트에서 자동으로 이름이 유도되며 짧은 해시가 추가됩니다(예: python:3.12 foo --truc → python-3-12-1a2b3c4d). CLI에서는 해당 해시가 명령어와 해석된 런타임 설정(플래버, 타임아웃, 환경 변수 값 등)을 모두 포함하므로 동일한 구성은 항상 동일한 이름을 생성합니다. 설정을 변경하면 이름도 변경되며, 스크립트의 [tool.hf-jobs] 헤더에서 가져온 설정도 포함됩니다. Python API에서는 해시가 명령어만 포함합니다.

레이블 업데이트

update_job_labels()를 사용하여 기존 작업의 라벨을 교체합니다. 이 작업은 모든 기존 사용자 지정 라벨을 대체합니다:

>>> from huggingface_hub import update_job_labels
>>> update_job_labels(job_id=job_id, labels={"env": "prod", "team": "ml"})

This also works for scheduled jobs with update_scheduled_job_labels():

>>> from huggingface_hub import update_scheduled_job_labels
>>> update_scheduled_job_labels(scheduled_job_id=scheduled_job_id, labels={"env": "staging"})

CLI에서:

>>> hf jobs labels <job_id> --label env=prod --label team=ml
>>> hf jobs scheduled labels <scheduled_job_id> --label env=staging

모든 라벨을 제거하려면 --clear를 전달하세요:

>>> hf jobs labels <job_id> --clear

UV 스크립트 (실험적)

바로 사용할 수 있는 UV 스크립트를 찾고 계신가요? Hugging Face Hub의 uv-scripts organization을 확인해 보세요. 모델 학습, 합성 데이터 생성, 데이터 처리 등 다양한 작업을 위한 커뮤니티 기반 UV 스크립트 컬렉션을 제공합니다.

HF 인프라에서 UV 스크립트(인라인 의존성이 포함된 Python 스크립트)를 실행합니다:

# Run a UV script (creates temporary repo)
>>> from huggingface_hub import run_uv_job
>>> run_uv_job("my_script.py")

# Run with GPU
>>> run_uv_job("ml_training.py", flavor="gpu-t4-small")

# Run with dependencies
>>> run_uv_job("inference.py", dependencies=["transformers", "torch"])

# Run a script directly from a URL
>>> run_uv_job("https://huggingface.co/datasets/username/scripts/resolve/main/example.py")

# Run a command
>>> run_uv_job("python", script_args=["-c", "import lighteval"], dependencies=["lighteval"])

UV 스크립트는 특수한 주석 문법을 사용하여 의존성을 파일 내에 직접 포함하는 Python 스크립트입니다. 이는 복잡한 프로젝트 설정이 필요하지 않은 자체 완결형 작업에 적합합니다. UV 문서에서 UV 스크립트에 대해 자세히 알아보세요.

launch config를 스크립트와 함께 배포

특정 런타임에서만 올바르게 실행되는 스크립트는 PEP 723 헤더의 선택적 [tool.hf-jobs] 테이블에 해당 런타인을 포함할 수 있습니다:

# /// script
# requires-python = ">=3.11"
# dependencies = ["vllm", "datasets"]
#
# [tool.hf-jobs]
# image   = "vllm/vllm-openai:unlimited-ocr"
# flavor  = "l4x1"
# python  = "/usr/bin/python3"
# secrets = ["HF_TOKEN"]
# ///

hf jobs uv run ocr.py를 실행하면 올바른 이미지, 하드웨어 및 인터프리터로 시작되며, --flavor, -e, …는 여전히 스크립트가 선언한 값을 덮어씁니다. 전체 키 목록과 병합 규칙은 CLI 가이드를 참조하세요.

해당 테이블은 hf CLI에서만 읽힙니다: run_uv_job()과 create_scheduled_uv_job()은 이를 무시하고 주어진 인수를 그대로 사용합니다. 즉, run_uv_job("ocr.py")와 hf jobs uv run ocr.py는 동일한 Job을 실행하지 않으며, Python API에서는 image=, flavor=, …를 명시적으로 전달해야 합니다.

UV 스크립트용 Docker 이미지

UV 스크립트는 인라인으로 의존성을 지정할 수 있지만, ML 워크로드에는 복잡한 의존성이 있는 경우가 많습니다. 이러한 라이브러리가 이미 설치된 사전 구축된 Docker 이미지를 사용하면 작업 시작 시간을 크게 단축하고 의존성 문제를 방지할 수 있습니다.

기본적으로 hf jobs uv run을 실행하면 astral-sh/uv:python3.12-bookworm 이미지가 사용됩니다. 이 이미지는 uv가 사전 설치된 Python 3.12 Bookworm 배포판 기반입니다.

--image 플래그를 사용하여 다른 이미지를 지정할 수 있습니다:

hf jobs uv run \
 --flavor a10g-large \
 --image vllm/vllm-openai:latest \
...

위 명령은 vllm/vllm-openai:latest 이미지를 사용하여 실행됩니다. 합성 데이터 생성에 vLLM을 사용하는 경우 이 접근 방식이 유용할 수 있습니다.

많은 추론 프레임워크가 최적화된 docker 이미지를 제공합니다. Python 생태계에서 uv의 채택이 점차 확대됨에 따라, 이러한 이미지 중에서도 uv가 사전 설치된 경우가 많아지고 있으며, 이는 hf jobs uv run을 사용할 때 정상적으로 동작한다는 것을 의미합니다.

예약된 작업

HF 인프라에서 실행될 작업을 예약하고 관리합니다.

@annually, @yearly, @monthly, @weekly, @daily, @hourly 또는 CRON 스케줄 표현식(예: 매주 월요일 오전 9시를 나타내는 "0 9 * * 1")을 사용하여 create_scheduled_job() 또는 create_scheduled_uv_job()를 실행합니다:

# Schedule a job that runs every hour
>>> from huggingface_hub import create_scheduled_job
>>> create_scheduled_job(
...     image="python:3.12",
...     command=["python",  "-c", "print('This runs every hour!')"],
...     schedule="@hourly"
... )

# Use the CRON syntax
>>> create_scheduled_job(
...     image="python:3.12",
...     command=["python",  "-c", "print('This runs every 5 minutes!')"],
...     schedule="*/5 * * * *"
... )

# Schedule with GPU
>>> create_scheduled_job(
...     image="pytorch/pytorch:2.6.0-cuda12.4-cudnn9-devel",
...     command=["python",  "-c", 'import torch; print(f"This code ran with the following GPU: {torch.cuda.get_device_name()}")'],
...     schedule="@hourly",
...     flavor="a10g-small",
... )

# Schedule a UV script
>>> from huggingface_hub import create_scheduled_uv_job
>>> create_scheduled_uv_job("my_script.py", schedule="@hourly")

환경 변수, 시크릿, 타임아웃 등을 전달하려면 run_job() 및 run_uv_job()과 동일한 매개변수를 사용합니다.

list_scheduled_jobs(), inspect_scheduled_job(), suspend_scheduled_job(), resume_scheduled_job(), update_scheduled_job_schedule(), trigger_scheduled_job(), delete_scheduled_job()를 사용하여 예약된 작업을 관리합니다:

# List your active scheduled jobs
>>> from huggingface_hub import list_scheduled_jobs
>>> list_scheduled_jobs()

# Only list scheduled jobs with the given labels
>>> list_scheduled_jobs(labels={"env": "prod"})

# Inspect the status of a job
>>> from huggingface_hub import inspect_scheduled_job
>>> inspect_scheduled_job(scheduled_job_id=scheduled_job_id)

# Suspend (pause) a scheduled job
>>> from huggingface_hub import suspend_scheduled_job
>>> suspend_scheduled_job(scheduled_job_id=scheduled_job_id)

# Resume a scheduled job
>>> from huggingface_hub import resume_scheduled_job
>>> resume_scheduled_job(scheduled_job_id=scheduled_job_id)

# Change future run times without recreating the scheduled job
>>> from huggingface_hub import update_scheduled_job_schedule
>>> updated = update_scheduled_job_schedule(scheduled_job_id=scheduled_job_id, schedule="0 9 * * 1")
>>> updated.schedule
'0 9 * * 1'

# Trigger a scheduled job to run right now (does not change the schedule)
>>> from huggingface_hub import trigger_scheduled_job
>>> job = trigger_scheduled_job(scheduled_job_id=scheduled_job_id)
>>> job.url

# Delete a scheduled job
>>> from huggingface_hub import delete_scheduled_job
>>> delete_scheduled_job(scheduled_job_id=scheduled_job_id)

웹훅으로 Job 트리거

Webhooks를 사용하면 특정 저장소 또는 특정 사용자/조직에 속한 모든 저장소(내 저장소뿐만 아니라 모든 저장소)의 새로운 변경 사항을 수신할 수 있습니다.

Hugging Face 저장소에서 변경 사항이 발생하면 Job을 트리거하는 웹훅을 생성하려면 create_webhook()를 사용하세요:

from huggingface_hub import create_webhook

# Example: Creating a webhook that triggers a Job
webhook = create_webhook(
    job_id=job_id,
    watched=[{"type": "user", "name": "your-username"}, {"type": "org", "name": "your-org-name"}],
    domains=["repo", "discussion"],
    secret="your-secret"
)

Webhook은 환경 변수 WEBHOOK_PAYLOAD에 webhook payload를 담아 Job을 트리거합니다. Webhook에 대한 자세한 내용은 Webhooks 문서에서 확인하세요.

Update on GitHub