Skip to content

Deployment modes

The repository contains several ways to run the same gateway and witness-node binaries. They are examples and deployment assets, not a security-reviewed production topology.

Bare metal or VM

The gateway can run under systemd as a dedicated witness user. A typical topology is:

Internet -- TLS --> nginx / load balancer -- HTTP --> 127.0.0.1:8080 gateway
                                                     |
                                             HTTPS/HTTP dev only
                                                     v
                                           witness nodes / peers

The gateway speaks plain HTTP and does not terminate TLS. The repository's nginx template terminates TLS and applies per-route IP allowlists. In particular, witness /v1/sign and gateway /v1/federation/anchor should be restricted to gateway or peer sources, in addition to bearer authentication. When a proxy is trusted, run the gateway with --behind-proxy (or WITNESS_BEHIND_PROXY=true) so client-IP handling uses the forwarded address.

The gateway database must be on persistent local disk, not a network filesystem. Keep configuration, bearer tokens, private witness files, and any Ethereum signing credentials access-controlled. See the repository's operator deployment and storage guides for service examples.

Docker images

The root Dockerfile has multi-stage targets:

  • witness-node, a non-root runtime exposing port 3000 and reading a mounted node configuration; and
  • witness-gateway, a non-root runtime exposing port 8080 and including the gateway, CLI, and auditor binaries.

The gateway image uses /data for configuration and SQLite state. Mount the configuration read-only where possible and give the database a persistent local volume. Do not expose the plain HTTP container port directly to an untrusted network; put TLS and route restrictions in front of it.

The Docker build disables LTO and uses multiple codegen units to reduce build resource use. This differs from the root Cargo release profile and should not be assumed to produce byte-identical local release artifacts.

Compose example

docker-compose.yaml provides an example three-witness network. An ephemeral setup service generates keys, tokens, witness configurations, and network.json into a shared configuration volume. Three witness services then serve signing requests and the gateway stores SQLite data in a persistent gateway-data volume. docker-compose.build.yaml changes the setup to build the local Docker targets instead of pulling prebuilt images.

Generated configurations contain private keys or bearer tokens. Treat the shared configuration volume as secret material and do not commit generated files.

Repository examples

The shell examples follow a setup, start, demo, stop lifecycle:

  • the standard example runs three Ed25519 witnesses with threshold two, witnesses on ports 3001-3003, and a gateway on 8080;
  • the examples/bls/ variant runs BLS aggregation;
  • the examples/federation/ variant runs three independent networks and cross-anchors batches between their gateways; and
  • the gateway variants run multiple independent networks for local exercises.

These examples are useful for threshold failure, witness failure, duplicate hash, BLS, and federation demonstrations. They use local HTTP and generated secrets and are not production defaults.

Auditor placement

The auditor can run separately on a monitoring host or under cron/systemd. It needs network access to the gateway's log endpoints and its own persistent SQLite database. A watch process continuously checks new STHs; check can be run as a periodic one-shot. Keeping the auditor's database outside the gateway's host gives its rollback memory a more independent failure domain.

Availability and scaling caveats

The durable job lease permits multiple gateway processes to claim distinct jobs in the storage model, but operators must not run multiple independent gateway processes against the same SQLite file. SQLite's local-disk and single-writer constraints remain. Horizontal deployments need an explicitly designed storage and routing topology rather than simply sharing a network filesystem.