# Docker Example

This page shows a reproducible Docker setup for running an AugeLab Studio `.pmod` scenario headlessly.

The image is built locally from a Dockerfile. Customers do not need the AugeLab Studio source code. The container installs the closed-source `studio` package from the AugeLab package index during image build.

## Prerequisites

* Docker Desktop or Docker Engine with Docker Compose.
* Access to the AugeLab package index.
* An AugeLab verification code.
* A `.pmod` scenario that can run headlessly.
* For GPU/CUDA: NVIDIA Container Toolkit installed on the host.

## Quick path

1. Create the folder layout below.
2. Put your `.pmod` file in `app/`.
3. Add your verification code to `.env`.
4. Use the CPU or GPU Dockerfile.
5. Run `docker compose up --build`.
6. Check `output_on_host`.

## Project layout

```
augelab-docker-example/
  .env
  docker-compose.yml
  docker-compose.cuda.yml
  output_on_host/
  app/
    Dockerfile
    Dockerfile.cuda
    run_scenario.py
    your_scenario.pmod
```

Replace `your_scenario.pmod` with your own scenario file.

## Environment file

Create `.env` next to `docker-compose.yml`:

<details>

<summary>.env</summary>

```env
AUGELAB_VERIFICATION_CODE=PASTE_YOUR_VERIFICATION_CODE_HERE
SCENARIO_PATH=your_scenario.pmod
```

</details>

Do not commit `.env` if it contains a real verification code.

## Scenario runner

Create `app/run_scenario.py`:

<details>

<summary>app/run_scenario.py</summary>

```python
import os
from pathlib import Path

from studio import StudioScenario


OUTPUT_DIR = Path("/app/app_output")
OUTPUT_DIR.mkdir(parents=True, exist_ok=True)

verification_code = os.environ.get("AUGELAB_VERIFICATION_CODE")
if not verification_code:
    raise RuntimeError("AUGELAB_VERIFICATION_CODE is not set.")

scenario_path = os.environ.get("SCENARIO_PATH", "your_scenario.pmod")
if not Path(scenario_path).is_file():
    raise FileNotFoundError(f"Scenario file not found: {scenario_path}")

scenario = StudioScenario(verification_code=verification_code)
scenario.enable_logging_stdout()
scenario.load_scenario(scenario_path)

try:
    print("Scenario result:", scenario.run())
finally:
    scenario.cleanup()
```

</details>

If your scenario writes files, configure the scenario to write them under `/app/app_output`.

## CPU Dockerfile

Use this for regular headless CPU runs.

<details>

<summary>app/Dockerfile</summary>

```dockerfile
FROM python:3.12-slim-bookworm

WORKDIR /app

RUN apt-get update -y && \
    apt-get install -y --no-install-recommends \
    libdmtx0b \
    zbar-tools \
    build-essential \
    libgl1-mesa-glx \
    curl \
    ca-certificates \
    && rm -rf /var/lib/apt/lists/*

ADD https://astral.sh/uv/0.9.17/install.sh /uv-installer.sh
RUN sh /uv-installer.sh && rm /uv-installer.sh

ENV PATH="/root/.local/bin/:$PATH"

RUN uv pip install studio --system \
    --extra-index-url https://pyrepo.augelab.com \
    --extra-index-url https://download.pytorch.org/whl/cpu \
    --index-strategy unsafe-best-match

RUN python -c "from studio import StudioScenario; print('studio import ok')"

COPY run_scenario.py .
COPY your_scenario.pmod .

CMD ["python", "run_scenario.py"]
```

</details>

## GPU/CUDA Dockerfile

Use this when your scenario needs CUDA acceleration. The host must have compatible NVIDIA drivers and NVIDIA Container Toolkit.

<details>

<summary>app/Dockerfile.cuda</summary>

```dockerfile
FROM nvidia/cuda:12.8.0-cudnn-runtime-ubuntu22.04

WORKDIR /app

RUN apt-get update -y && \
    apt-get install -y --no-install-recommends \
    python3 \
    python3-venv \
    python3-pip \
    libdmtx0b \
    zbar-tools \
    build-essential \
    libgl1-mesa-glx \
    curl \
    ca-certificates \
    && rm -rf /var/lib/apt/lists/*

ADD https://astral.sh/uv/0.9.17/install.sh /uv-installer.sh
RUN sh /uv-installer.sh && rm /uv-installer.sh

ENV PATH="/root/.local/bin/:$PATH"
ENV NVIDIA_VISIBLE_DEVICES=all
ENV NVIDIA_DRIVER_CAPABILITIES=compute,utility

RUN uv pip install "studio[gpu]" --system \
    --extra-index-url https://pyrepo.augelab.com \
    --index-strategy unsafe-best-match

RUN python3 -c "from studio import StudioScenario; print('studio gpu import ok')"

COPY run_scenario.py .
COPY your_scenario.pmod .

CMD ["python3", "run_scenario.py"]
```

</details>

## Compose file

Use this for the CPU Dockerfile:

<details>

<summary>docker-compose.yml</summary>

```yaml
services:
  augelab-headless:
    build:
      context: ./app
      dockerfile: Dockerfile
    env_file:
      - .env
    volumes:
      - ./output_on_host:/app/app_output
```

</details>

This mounts `./output_on_host` from your project folder into the container as `/app/app_output`.

{% hint style="warning" %}
On Windows, use forward slashes in absolute Docker mount paths, for example `C:/work/augelab_output:/app/app_output`. Relative mounts like `./output_on_host:/app/app_output` are usually easier to share across machines.
{% endhint %}

## GPU/CUDA compose file

Use this for `Dockerfile.cuda`:

<details>

<summary>docker-compose.cuda.yml</summary>

```yaml
services:
  augelab-headless-gpu:
    build:
      context: ./app
      dockerfile: Dockerfile.cuda
    env_file:
      - .env
    volumes:
      - ./output_on_host:/app/app_output
    gpus: all
```

</details>

## Build and run

CPU:

```bash
docker compose up --build
```

GPU/CUDA:

```bash
docker compose -f docker-compose.cuda.yml up --build
```

You should see AugeLab Studio logs and the scenario result in the terminal.

## Verify output

Check `output_on_host` on your host machine. Files written by the scenario to `/app/app_output` should appear there.

## Troubleshooting

| Problem                       | Check                                                                                                                       |
| ----------------------------- | --------------------------------------------------------------------------------------------------------------------------- |
| `studio` install fails        | Confirm network access and AugeLab package index access.                                                                    |
| License/activation fails      | Confirm `AUGELAB_VERIFICATION_CODE` is set and the container has internet access.                                           |
| Scenario file not found       | Confirm `SCENARIO_PATH` matches the `.pmod` copied by the Dockerfile.                                                       |
| Output folder empty           | Confirm the `.pmod` writes to `/app/app_output`.                                                                            |
| Windows volume does not mount | Use forward slashes and confirm Docker Desktop can access the drive.                                                        |
| GPU container cannot see GPU  | Install NVIDIA Container Toolkit and test with `docker run --rm --gpus all nvidia/cuda:12.8.0-base-ubuntu22.04 nvidia-smi`. |


---

# Agent Instructions: Querying This Documentation

If you need additional information that is not directly available in this page, you can query the documentation dynamically by asking a question.

Perform an HTTP GET request on the current page URL with the `ask` query parameter:

```
GET https://docs.augelab.com/key-features/headless/docker-example.md?ask=<question>
```

The question should be specific, self-contained, and written in natural language.
The response will contain a direct answer to the question and relevant excerpts and sources from the documentation.

Use this mechanism when the answer is not explicitly present in the current page, you need clarification or additional context, or you want to retrieve related documentation sections.
