# Parked/Awaiting-Agent Signal Tracking in no-mistakes: How Runs Pause for Human Input

> Understand parked awaiting agent signal tracking in no-mistakes runs. Learn how runs pause for human input using database timestamps and IPC for clear CLI durations.

- Repository: [Kun Chen/no-mistakes](https://github.com/kunchenguid/no-mistakes)
- Tags: internals
- Published: 2026-07-16

---

**In no-mistakes, runs enter a "parked" awaiting-agent state when they reach gates requiring human approval, tracked via database timestamps in `awaiting_agent_since` and exposed through IPC to render human-readable duration in the CLI.**

The **no-mistakes** repository implements a sophisticated pipeline execution system where automated runs can pause at designated gates to await human intervention. When a run encounters a gate requiring an agent—such as a reviewer or fixer—it transitions into an **awaiting-agent** state, recording the exact moment it parked to enable precise duration tracking and user visibility.

## What Is the Awaiting-Agent Signal?

The awaiting-agent signal consists of two distinct data points that work together to represent a parked run:

1. **Presence flag** – A boolean indicating the run is currently parked, derived from whether `awaiting_agent_since` is non-null.
2. **Timestamp** – The Unix-seconds value recording exactly when the run entered the parked state, enabling duration calculations across the stack.

This signal propagates from the database layer through the IPC protocol to the CLI, allowing the system to display real-time "parked" status while accumulating total wait time for metrics.

## Database Layer: Tracking Parked State in SQLite

The persistence layer in [`internal/db/run.go`](https://github.com/kunchenguid/no-mistakes/blob/main/internal/db/run.go) manages the lifecycle of the awaiting-agent marker through three critical functions.

### Setting the Marker with SetRunAwaitingAgent

When a run reaches an agent gate, the executor calls `DB.SetRunAwaitingAgent(run.ID)`, which writes the current Unix timestamp into the `awaiting_agent_since` column of the `runs` table.

```go
// internal/pipeline/executor.go
if err := e.db.SetRunAwaitingAgent(run.ID); err != nil {
    return err
}

```

The underlying schema defines this column as a nullable integer to accommodate the transient nature of the parked state:

```sql
-- internal/db/schema.go
awaiting_agent_since INTEGER,

```

### Clearing and Recording Duration

Upon agent response, the system clears the marker while optionally recording the elapsed parked time. The `CompleteRunAwaitingAgent` function calculates the duration in milliseconds, increments the `parked_ms` accumulator, and sets `awaiting_agent_since` to NULL.

```go
// internal/pipeline/executor.go
parkStart := time.Unix(*run.AwaitingAgentSince, 0)
if dbErr := e.db.CompleteRunAwaitingAgent(run.ID,
    time.Since(parkStart).Milliseconds()); dbErr != nil {
    return dbErr
}

```

Alternatively, `ClearRunAwaitingAgent` simply nullifies the timestamp without updating metrics, used when parking is cancelled rather than completed.

## Executor Integration: When Runs Enter the Parked State

The pipeline executor in [`internal/pipeline/executor.go`](https://github.com/kunchenguid/no-mistakes/blob/main/internal/pipeline/executor.go) orchestrates the transition into and out of the awaiting-agent state around gate handling logic.

### Gate Entry Triggers Parking

When the execution engine encounters a gate requiring human approval, it immediately persists the awaiting-agent marker before pausing the run. This ensures that even if the daemon restarts, the parked state and entry time are preserved in the database.

### Agent Response Clears the Marker

Once the user submits a response via `axi respond`, the executor retrieves the original timestamp from `run.AwaitingAgentSince`, calculates the elapsed duration, and calls the database layer to record the metrics and clear the flag. This atomic operation ensures no parked time is lost to race conditions.

## IPC Protocol and CLI Rendering

The awaiting-agent signal surfaces to end users through a structured IPC protocol and specialized rendering logic.

### Exposing State via RunInfo

The `RunInfo` struct in [`internal/ipc/protocol.go`](https://github.com/kunchenguid/no-mistakes/blob/main/internal/ipc/protocol.go) carries the awaiting-agent data across process boundaries:

```go
// internal/ipc/protocol.go
type RunInfo struct {
    AwaitingAgent      bool
    AwaitingAgentSince *int64
    // ... other fields
}

```

The daemon populates these fields directly from the database row, ensuring the CLI receives authoritative state without secondary queries.

### Displaying Parked Duration in axi status

The CLI rendering engine in [`internal/cli/axi_render.go`](https://github.com/kunchenguid/no-mistakes/blob/main/internal/cli/axi_render.go) converts the raw timestamp into a human-readable duration, but only for non-terminal runs. This prevents displaying "parked" status for completed or failed executions.

```go
// internal/cli/axi_render.go
if rv.AwaitingAgentSince != nil && !terminalStatus(rv.Status) {
    fields = append(fields,
        toon.Field{Key: "awaiting_agent",
                   Value: formatParkedFor(*rv.AwaitingAgentSince)})
}

```

The `formatParkedFor` function calculates the delta between the recorded timestamp and current time, presenting users with intuitive "parked 5m 32s" messaging.

## Metrics and Telemetry

Beyond real-time status display, the no-mistakes system accumulates total parked time in the `parked_ms` column. This metric aggregates across multiple agent interactions within a single run, providing telemetry data for pipeline optimization and bottleneck analysis. The `CompleteRunAwaitingAgent` query handles this accumulation atomically, ensuring accurate reporting even under concurrent access patterns.

## Summary

- **The awaiting-agent signal** combines a boolean presence flag with a Unix timestamp to track when runs pause for human input.
- **Database functions** `SetRunAwaitingAgent`, `ClearRunAwaitingAgent`, and `CompleteRunAwaitingAgent` in [`internal/db/run.go`](https://github.com/kunchenguid/no-mistakes/blob/main/internal/db/run.go) manage the state transitions and metrics accumulation.
- **The executor** in [`internal/pipeline/executor.go`](https://github.com/kunchenguid/no-mistakes/blob/main/internal/pipeline/executor.go) triggers parking at gate entry and clears markers upon agent response, calculating durations for telemetry.
- **IPC protocol** exposes the state via `RunInfo` in [`internal/ipc/protocol.go`](https://github.com/kunchenguid/no-mistakes/blob/main/internal/ipc/protocol.go), while [`internal/cli/axi_render.go`](https://github.com/kunchenguid/no-mistakes/blob/main/internal/cli/axi_render.go) formats the duration for `axi status` output.
- **Persistent metrics** store total parked time in the `parked_ms` column, enabling long-term performance analysis across pipeline runs.

## Frequently Asked Questions

### What triggers the awaiting-agent state in no-mistakes?

The awaiting-agent state triggers when a pipeline run encounters a gate requiring human approval, such as review or fix stages. The executor calls `SetRunAwaitingAgent` at the moment the run parks, recording the Unix timestamp in the database before pausing execution.

### How does the CLI calculate the parked duration?

The CLI retrieves the `AwaitingAgentSince` timestamp via the IPC protocol and passes it to `formatParkedFor`, which computes the elapsed time against the current system clock. This calculation occurs in [`internal/cli/axi_render.go`](https://github.com/kunchenguid/no-mistakes/blob/main/internal/cli/axi_render.go) and displays only while the run maintains a non-terminal status.

### What happens to the parked time after an agent responds?

When an agent responds, the executor calls `CompleteRunAwaitingAgent`, which calculates the elapsed milliseconds since the original timestamp, adds this value to the cumulative `parked_ms` column, and sets `awaiting_agent_since` to NULL, effectively clearing the parked state while preserving the duration for metrics.

### Where is the awaiting-agent timestamp stored?

The timestamp resides in the `awaiting_agent_since` column of the `runs` table in SQLite, defined in [`internal/db/schema.go`](https://github.com/kunchenguid/no-mistakes/blob/main/internal/db/schema.go) as an nullable integer. This column is updated exclusively through the database abstraction layer in [`internal/db/run.go`](https://github.com/kunchenguid/no-mistakes/blob/main/internal/db/run.go) to ensure consistency across the application.