Skip to main content

Quick start

The shortest path from the delivery archive to a working login: one Linux host, Docker, an existing Elasticsearch, one run of deploy.sh.

Prerequisites

ItemRequirement
HostUbuntu 20.04 / 22.04 / 24.04 or equivalent Linux, 2 vCPU / 4 GB / 20 GB+
RuntimeDocker Engine 24+ and Docker Compose v2
ElasticsearchYour existing 8.x, reachable from the gateway host; Kibana optional
LLMURL / API key / model name of an OpenAI-compatible endpoint (ark-code-latest on the Volcengine Ark coding plan)
HostnameA domain name (e.g. copilot.corp.local), not a bare IP (an IP is not a valid TLS SNI and some browsers refuse the handshake); without internal DNS, add a hosts entry on the analysts' machines

Inbound: only 443 (80 for the redirect, optional). Outbound: the LLM endpoint on 443, your ES on 9200, license.reallysec.com on 443 (not needed for air-gapped installs, see Licensing).

Install

Install Docker (if missing)

curl -fsSL https://get.docker.com | sudo sh
sudo usermod -aG docker $USER   # log out and back in
docker compose version

Unpack the delivery archive

The archive RST-Elastic-AI-Copilot-<version>.tar.gz carries the images; no registry access is needed.

sha256sum -c RST-Elastic-AI-Copilot-<version>.tar.gz.sha256
tar xzf RST-Elastic-AI-Copilot-<version>.tar.gz
cd RST-Elastic-AI-Copilot-<version>

Run deploy.sh

./deploy.sh

It checks Docker, generates state/machine-id and state/server_guid (the licence's hardware fingerprint - never regenerate them), docker loads the images, asks for the auth mode (1, built-in login) and ES source (1, existing ELK), then the LLM URL / key / model, timezone, ES / Kibana URLs, the site hostname and an admin password, writes the generated internal secrets to .env (mode 600), and runs docker compose up -d until everything is healthy.

It prints the URL at the end. About two minutes end to end.

Verify

curl -k https://copilot.corp.local/healthz   # {"status":"ok"}
curl -k https://copilot.corp.local/readyz    # es / es_write / timezone

es_write in readyz must be ok. denied means the ES account lacks permissions on the .rst_copilot_* indices, see below.

Log in

Open https://copilot.corp.local/v2/, accept the self-signed certificate (swap in your own for production by editing Caddyfile), user admin, the password you just set.

Login

You land on the Smart query home; the parts of the screen are explained in A tour of the UI.

ES account permissions

If your ES has security enabled, give ES_USER a role with at least:

  • your log indices (e.g. logs-*): read, view_index_metadata
  • the gateway's own indices .rst_copilot_*: create_index, read, write, manage, with one wildcard
  • to pull live alerts, additionally read and view_index_metadata on .alerts-security.alerts-* and .internal.alerts-security.alerts-* (hidden indices: the Kibana role page will not autocomplete them, type the pattern and press Enter)

Recommended: set RST_INDEX_WHITELIST=logs-*,filebeat-* in .env to limit which indices can be queried.

After install

  1. Activate a licence: the paid engines need one; trials are free.
  2. /v2/settings: index whitelist, masking mode, audit.
  3. Backups: copy the whole ./state/ directory; export the gateway_state volume with the bundled scripts/backup.sh (it covers the volume only, not ./state/).

Upgrading

Unpack the new archive into the same directory and run ./deploy.sh again, choosing "keep existing .env" - it loads the new image, switches GATEWAY_IMAGE_TAG and restarts. To roll back, restart on the previous tag; licence state lives in state/ and the volume and survives.

Never regenerate state/machine-id or state/server_guid, and never docker compose down -v. Changing either is a new host to the licence, which then has to be re-activated.

Troubleshooting

SymptomWhere to look
/v2/ does not opendocker compose -f docker-compose.prod.yml logs caddy gateway; 443 open, CADDY_SITE_ADDRESS is a hostname
TLS handshake failsCADDY_SITE_ADDRESS is a bare IP; use a hostname + hosts entry
readyz says es_write=deniedES account lacks create / write on .rst_copilot_*
Queries fail or come back emptyES reachable? RST_INDEX_WHITELIST missing the target index? LLM key / endpoint correct?
Licence suddenly invalidWas state/machine-id / state/server_guid regenerated?

On this page