# Docker

> Run the hub with the shipped docker-compose.yml. What each service and volume holds, which ports it opens, and how to start, stop and adjust it.

Source: https://proxus.io/docs/operate/docker

At the end of this guide, the Proxus hub runs on one machine with Docker Compose, under a fixed project name, with
the time zone and settings of your site. For a first test installation, [Install Proxus](https://proxus.io/docs/get-started/install)
is shorter.

## Before you start

- A Linux machine (or a Windows or macOS machine with Docker Desktop) that meets the
  [system requirements](https://proxus.io/docs/get-started/system-requirements).
- Docker Engine with the Docker Compose plugin (`docker compose version` prints a version).
- The `docker-compose.yml` file for Proxus 2.0.0, in a folder of its own, for example `/opt/proxus`.
- Access to Docker Hub, where the images `proxusplatform/proxus-ui` and `proxusplatform/proxus-server` are
  published, or the images loaded beforehand with `docker load`. See
  [Install without internet access](https://proxus.io/docs/operate/offline-install).

> **Note:**
Older Proxus packages also contained a `Deployment/docker-compose.yml` with Redis, a separate API service and
TimescaleDB. That file is not used by 2.0.0. Use the `docker-compose.yml` that comes with the release.

## What the compose file runs

| Service | Image | Published ports | Data |
| --- | --- | --- | --- |
| `proxus-ui` (the hub) | `proxusplatform/proxus-ui` | `8443` HTTPS and `8080` HTTP: web interface, REST API, MCP | volumes `config`, `proxus_modules` |
| `proxus-server` (gateway **SYSTEM**) | `proxusplatform/proxus-server` | `8083` gateway HTTP, `1883` MQTT, `8883` MQTT over TLS | volume `config` |
| `hub-server` (message broker) | `nats` | `4222` clients and `7422` edge gateways (both TLS), `8222` monitoring | volumes `nats`, `config` |
| `postgresql` (configuration database) | `postgres:16` | `5442` | volume `proxus-db-volume` |
| `clickhouse` (telemetry database) | `bitnamilegacy/clickhouse` | `8123`, `9000`, `9004`, `9005` | volume `clickhouse_data`, folder `./clickhouse-logs` |

Every service restarts by itself (`restart: always`) and the hub, the gateway and the databases have health checks.
The `config` volume is shared by the hub, the gateway and the broker: it holds the configuration file, the
broker's credentials and TLS certificate, the keys that protect sign-ins, and the Certificate Store key
(`keys/STORE/certificate-store.key`). Without the Certificate Store key, the certificates in the database cannot be
read, so back up the `config` volume together with the database. See [Backup and restore](https://proxus.io/docs/operate/backup-and-restore).

The `proxus-ui` container also mounts the Docker socket (`/var/run/docker.sock`). The hub uses it to restart the
stack after a configuration change.

## Start the stack

Run the stack under the project name `proxus`. The hub's **Restart** button in the
[Config Editor](https://proxus.io/docs/administer/configuration) only finds containers of a project with that name, and the
volume names in this documentation (`proxus_config` and so on) assume it.

```bash
cd /opt/proxus
docker compose -p proxus up -d
```

On the first start, the hub creates the message broker's credentials on the `config` volume. Until it has done
that, `hub-server` prints "Waiting for Proxus UI to create the NATS trust" every two seconds. This is expected.

Check that everything runs:

```bash
docker compose -p proxus ps
```

`proxus-ui`, `proxus-server` and `postgresql` show `healthy` once they are ready. Then open
`https://<host>:8443` and sign in. HTTPS is on by default, with a certificate from the platform's own certificate
authority; `http://<host>:8080` stays available for local access. See [Security](https://proxus.io/docs/operate/security#https).

> **Tip:**
Naming the folder `proxus` has the same effect as `-p proxus`, because Compose uses the folder name as the project
name. Use the same project name every time: the volumes belong to the project, so another name finds none of your
data. The containers have fixed names, so only one Proxus hub stack can run on a host.

## Day-to-day commands

| Task | Command |
| --- | --- |
| Stop everything (data stays) | `docker compose -p proxus stop` |
| Start again | `docker compose -p proxus start` |
| Restart the hub only | `docker compose -p proxus restart proxus-ui` |
| Follow a service's output | `docker compose -p proxus logs -f proxus-ui` |
| Remove the containers (volumes stay) | `docker compose -p proxus down` |

> **Danger:**
`docker compose down -v` also deletes the volumes: every device, rule, user and stored value, and the broker
credentials that edge gateways need. Never use `-v` on an installation you want to keep.

## Adjust the stack for your site

Change these in `docker-compose.yml`, then apply them with `docker compose -p proxus up -d`. Compose recreates only
the containers whose settings changed.

**Time zone.** The file sets `TZ: Europe/Istanbul` for the hub and the gateway. Log times and times on screen use
it. Set it to the time zone of the plant, for example `TZ: Europe/Paris`.

**Settings as environment variables.** Any key of the [configuration file](https://proxus.io/docs/administer/configuration) can be
set under `environment:` as `Section__Key`. Values set here win over the file and survive upgrades:

```yaml
    environment:
      <<: *dotnet-env
      ASPNETCORE_URLS: http://+:8080
      Service__UI-Port: "8080"
      Logging__Loglevel: "3"
      NATS__BrokerUrl: nats://hub-server:4222
      Security__Lockout__MaxFailedAccessAttempts: "5"
```

**Ports.** To publish the web interface on another port of the host, change only the left side: `"80:8080"`. To
keep a port reachable only from the host itself, bind it to the loopback address: `"127.0.0.1:5442:5442"`. The
services reach each other on the internal `proxus` network and do not need the published ports. See
[Security](https://proxus.io/docs/operate/security) for which ports must be open.

**HTTPS.** The hub serves HTTPS on `8443`. To publish it on another host port, for example `"443:8443"`, also set
`Service__PublicHttpsPort: "443"`. Add the names users type to reach the hub with `Service__PublicHostNames`, so the
hub's certificates cover them.

**MQTT over TLS.** The **SYSTEM** gateway's broker also listens for TLS on `8883`, which the shipped file publishes
next to `1883`. A file from an earlier version does not: add `"8883:8883"` to the ports of `proxus-server`.

**ClickHouse memory.** The `clickhouse` service is limited to 8 GB of memory (`memory: 8g` under
`deploy.resources.limits`). Lower it on a small machine, raise it for a large installation.

## After an upgrade to 2.0.0

Restart the message broker once after the hub has started, so it picks up its TLS certificate:

```bash
docker restart hub-server
```

Then run the install command of every remote edge gateway again. See [Upgrade](https://proxus.io/docs/operate/upgrade#upgrading-to-200).

## What's next

- [Upgrade](https://proxus.io/docs/operate/upgrade)
- [Back up the installation](https://proxus.io/docs/operate/backup-and-restore)
- [Harden the installation](https://proxus.io/docs/operate/security)
- [Install an edge gateway on another host](https://proxus.io/docs/connect/edge-gateways/install-a-gateway)
