Compute adapters¶
Driven adapters for the compute bounded context: a Slurm job dispatcher and a
Redis-backed task run repository.
SlurmJobDispatcher¶
Implements JobDispatcher using sbatch / squeue / sacct / scancel.
from pathlib import Path
from iris.adapters.driven.dispatchers.slurm import SlurmJobDispatcher
dispatcher = SlurmJobDispatcher(
submit_dir=Path("/scratch/project/.dispatch"),
log_dir=Path("/scratch/project/logs"), # defaults to submit_dir/logs
queue="short", # passed as --partition
)
Polling strategy — poll_one() queries squeue first (live jobs); if the
job is not found there it falls back to sacct (accounting data for finished
jobs). Both squeue and sacct output is translated to ExternalJobState via
slurm_state_to_external().
Script rendering — each run gets its own .sbatch file under submit_dir
named after the run_id. The script sets TASK_ID and TASK_RUN_ID as
environment variables so the payload can identify itself if needed.
Escape hatch for Slurm-specific options — pass rare sbatch flags via
DispatchHints.extra:
from iris.domain.compute.objects import DispatchHints
hints = DispatchHints(
queue="gpu",
extra={
"slurm.exclusive": "true", # → --exclusive
"slurm.raw.mail-type": "END,FAIL", # → --mail-type=END,FAIL
},
)
RedisTaskRunRepository¶
Implements TaskRunRepository with Redis as the backing store. Stores the full
TaskRun aggregate as a Redis Hash and maintains three secondary indices:
| Key pattern | Type | Purpose |
|---|---|---|
iris:compute:run:{run_id} |
Hash | Full serialized TaskRun |
iris:compute:ref:{dispatcher}:{external_id} |
String | Reverse lookup by ExternalJobRef |
iris:compute:runs |
Set | All known run_ids |
iris:compute:runs:status:{STATUS} |
Set | run_ids grouped by status |
Optimistic concurrency — save() watches the run key and retries on
WatchError. When check_version=True (default), a write with an older
version than the stored one raises StaleTaskRunError.
from iris.adapters.driven.repositories.redis_compute import make_redis_task_run_repository
# From environment variable IRIS_REDIS_URL, or defaults to redis://localhost:6379/0
repo = make_redis_task_run_repository()
# Explicit URL + optional TTL
repo = make_redis_task_run_repository(
url="redis://redis-host:6379/1",
default_ttl=86_400, # expire run keys after 24 h
)
UI-oriented reads — two extra methods not in the port are available for dashboards:
Reference¶
Slurm dispatcher¶
iris.adapters.driven.dispatchers.slurm
¶
Slurm implementation of the compute domain's :class:JobDispatcher port.
This is the only place where Slurm-specific concepts appear: sbatch,
squeue, sacct, scancel and native states such as PD, R,
CD, OOM, TIMEOUT. Everything crossing back into the domain is
expressed as :class:ExternalJobRef / :class:JobObservation.
JobDispatchError
¶
Bases: RuntimeError
Raised when a Slurm command fails.
SlurmJobDispatcher
¶
Bases: JobDispatcher
Dispatch compute jobs to Slurm via sbatch / squeue / sacct.
Renders an sbatch script per run under submit_dir and submits it with
--parsable for robust job-id parsing. Polling first consults squeue
(live jobs) and falls back to sacct (accounting) for finished jobs.
submit
¶
Render an sbatch script and submit it, returning the job reference.
Source code in src/iris/adapters/driven/dispatchers/slurm.py
cancel
¶
Cancel the job identified by ref via scancel.
Source code in src/iris/adapters/driven/dispatchers/slurm.py
poll
¶
Yield a :class:JobObservation for each reference.
poll_one
¶
Poll a single reference, preferring squeue then sacct.
Source code in src/iris/adapters/driven/dispatchers/slurm.py
format_slurm_time
¶
Format a duration in seconds as a Slurm --time string.
Returns D-HH:MM:SS when the duration spans one or more days, otherwise
HH:MM:SS.
Source code in src/iris/adapters/driven/dispatchers/slurm.py
parse_exit_status
¶
Parse a Slurm ExitCode field (code or code:signal).
Source code in src/iris/adapters/driven/dispatchers/slurm.py
parse_sbatch_parsable
¶
Parse sbatch --parsable output into (job_id, cluster | None).
Output is either <jobid> or <jobid>;<cluster>.
Source code in src/iris/adapters/driven/dispatchers/slurm.py
slurm_state_to_external
¶
Map a raw Slurm state (short or long form) to an :class:ExternalJobState.
Source code in src/iris/adapters/driven/dispatchers/slurm.py
Redis repository¶
iris.adapters.driven.repositories.redis_compute
¶
Redis-backed implementation of the compute domain's TaskRunRepository.
Stores the current state of each TaskRun as a Redis Hash and maintains secondary indices so the observation handler can resolve an external scheduler reference back to its run, and so a UI can list/filter runs by status without scanning.
Key layout
iris:compute:run:{run_id} Hash full serialized TaskRun iris:compute:ref:{dispatcher}:{external_id} String run_id (external-ref index) iris:compute:runs Set all run_ids iris:compute:runs:status:{STATUS} Set run_ids grouped by status
This is complementary to RedisEventPublisher (Redis Streams): the repository holds queryable current state, the publisher holds the append-only event log.
StaleTaskRunError
¶
Bases: RuntimeError
Raised when a save would overwrite a newer version of a run.
RedisTaskRunRepository
¶
Bases: TaskRunRepository
Persist TaskRun aggregates in Redis with external-ref and status indices.
| PARAMETER | DESCRIPTION |
|---|---|
client
|
Connected redis.Redis (expects
TYPE:
|
check_version
|
Reject writes whose version is older than the stored one.
TYPE:
|
default_ttl
|
Optional TTL (seconds) applied to run keys on save.
TYPE:
|
Initialize with a connected Redis client.
Source code in src/iris/adapters/driven/repositories/redis_compute.py
get
¶
Return the run with run_id == identifier, or None.
Source code in src/iris/adapters/driven/repositories/redis_compute.py
find_by_external_ref
¶
Return the run whose external_ref matches ref, or None.
Source code in src/iris/adapters/driven/repositories/redis_compute.py
save
¶
Persist entity atomically, updating all indices.
Uses optimistic concurrency: the run key is watched and the write is
retried if a concurrent modification is detected. When check_version
is set, a write carrying an older version than the stored one raises
:class:StaleTaskRunError.
Source code in src/iris/adapters/driven/repositories/redis_compute.py
find_all_ids
¶
find_ids_by_status
¶
Return run_ids currently in the given status.
make_redis_task_run_repository
¶
Construye un RedisTaskRunRepository.
| PARAMETER | DESCRIPTION |
|---|---|
url
|
URL de Redis. Si es None, lee IRIS_REDIS_URL del entorno. Default: redis://localhost:6379/0
TYPE:
|
check_version
|
Rechaza escrituras con una versión anterior a la guardada.
TYPE:
|
default_ttl
|
TTL en segundos para las claves de run (None = sin expiración).
TYPE:
|