> ## Documentation Index
> Fetch the complete documentation index at: https://mintlify.com/harbor-framework/harbor/llms.txt
> Use this file to discover all available pages before exploring further.

# Job

> The main entrypoint for launching and managing Harbor evaluation trials

## Overview

The `Job` class is the single entrypoint for launching a set of trials in Harbor. It handles database initialization, task and dataset management, and saves job-level results to the database and filesystem.

**Import:** `from harbor import Job`

## Constructor

<ParamField path="config" type="JobConfig" required>
  The job configuration object that defines all aspects of the evaluation run.
</ParamField>

### Properties

After initialization, the Job instance has these key attributes:

* `config: JobConfig` - The job configuration
* `is_resuming: bool` - Whether this job is resuming from a previous run
* `job_dir: Path` - Directory where job results are stored

## Methods

### run

```python theme={null}
async def run(self) -> JobResult
```

Executes all trials defined in the job configuration.

<ResponseField name="JobResult" type="JobResult">
  Contains comprehensive results including:

  * Trial results for all executions
  * Aggregate statistics across agents and datasets
  * Timing information
  * Computed metrics
</ResponseField>

**Example:**

```python theme={null}
from harbor import Job
from harbor.models.job.config import JobConfig

config = JobConfig(
    job_name="my-evaluation",
    agents=[{"name": "claude-code", "model_name": "anthropic/claude-opus-4-1"}],
    datasets=[{"name": "terminal-bench", "version": "2.0"}]
)

job = Job(config)
result = await job.run()

print(f"Completed {result.stats.n_trials} trials")
print(f"Errors: {result.stats.n_errors}")
```

### Lifecycle Hooks

Register callbacks for various trial lifecycle events. All hooks return `self` for method chaining.

#### on\_trial\_started

```python theme={null}
def on_trial_started(self, callback: HookCallback) -> "Job"
```

<ParamField path="callback" type="Callable[[TrialHookEvent], Awaitable[None]]" required>
  Async function called when a trial begins execution.
</ParamField>

**Example:**

```python theme={null}
async def log_trial_start(event: TrialHookEvent):
    print(f"Trial {event.trial_id} started")

job.on_trial_started(log_trial_start)
```

#### on\_environment\_started

```python theme={null}
def on_environment_started(self, callback: HookCallback) -> "Job"
```

<ParamField path="callback" type="Callable[[TrialHookEvent], Awaitable[None]]" required>
  Async function called when a trial's environment is ready.
</ParamField>

#### on\_agent\_started

```python theme={null}
def on_agent_started(self, callback: HookCallback) -> "Job"
```

<ParamField path="callback" type="Callable[[TrialHookEvent], Awaitable[None]]" required>
  Async function called when an agent begins execution.
</ParamField>

#### on\_verification\_started

```python theme={null}
def on_verification_started(self, callback: HookCallback) -> "Job"
```

<ParamField path="callback" type="Callable[[TrialHookEvent], Awaitable[None]]" required>
  Async function called when verification begins.
</ParamField>

#### on\_trial\_ended

```python theme={null}
def on_trial_ended(self, callback: HookCallback) -> "Job"
```

<ParamField path="callback" type="Callable[[TrialHookEvent], Awaitable[None]]" required>
  Async function called when a trial ends (success or failure). The `TrialHookEvent.result` field will contain the `TrialResult`.
</ParamField>

**Example:**

```python theme={null}
async def handle_trial_end(event: TrialHookEvent):
    if event.result:
        print(f"Trial completed with rewards: {event.result.verifier_result.rewards}")

job.on_trial_ended(handle_trial_end)
```

#### on\_trial\_cancelled

```python theme={null}
def on_trial_cancelled(self, callback: HookCallback) -> "Job"
```

<ParamField path="callback" type="Callable[[TrialHookEvent], Awaitable[None]]" required>
  Async function called when a trial is cancelled.
</ParamField>

## Complete Example

```python theme={null}
import asyncio
from harbor import Job
from harbor.models.job.config import JobConfig, OrchestratorConfig
from harbor.models.trial.config import AgentConfig
from harbor.trial.hooks import TrialHookEvent

async def on_start(event: TrialHookEvent):
    print(f"Starting trial: {event.trial_id}")

async def on_end(event: TrialHookEvent):
    if event.result:
        print(f"Finished: {event.result.trial_name}")
        print(f"Rewards: {event.result.verifier_result.rewards}")

async def main():
    config = JobConfig(
        job_name="benchmark-run",
        n_attempts=3,
        agents=[
            AgentConfig(
                name="claude-code",
                model_name="anthropic/claude-opus-4-1"
            )
        ],
        datasets=[
            {"name": "terminal-bench", "version": "2.0"}
        ],
        orchestrator=OrchestratorConfig(
            n_concurrent_trials=8
        )
    )
    
    job = Job(config)
    job.on_trial_started(on_start)
    job.on_trial_ended(on_end)
    
    result = await job.run()
    print(f"\nJob complete: {result.stats.n_trials} trials")
    return result

if __name__ == "__main__":
    asyncio.run(main())
```

## Related Types

* [JobConfig](/api/job-config) - Configuration for the Job
* [JobResult](/api/job-result) - Results returned from job execution
* [TrialConfig](/api/trial-config) - Configuration for individual trials
* [TrialResult](/api/trial-result) - Results from individual trial execution
