Operate a customer-run pilot
This is the procedure qualified for a customer-operated pilot on one host. Every
step below runs in the Integration CI job pilot-lifecycle on a clean Ubuntu 24.04
container with pinned component versions. It is not a turnkey production release:
container images, a compose file, a privately managed mode and server-to-server
migration are not part of this pilot.
The operator tool is tools/pilot/pilot.py in the Integration repository; it keeps
one deployment directory with its configuration, owner-only secrets, process ids, the
gateway state (journal and payload store) and a journey record.
Install and sign in
Section titled “Install and sign in”Prerequisites: PostgreSQL you operate (an empty database and a login without a
password in the connection string — use peer authentication or a PGPASSFILE), the
pinned component checkouts, and the native arraybridge_server built from them.
python3 tools/pilot/pilot.py install --deployment /srv/ophiolite/pilot \ --dsn "host=db port=5432 user=ophiolite dbname=ophiolite" \ --components /srv/ophiolite/components --server /srv/ophiolite/bin/arraybridge_serverpython3 tools/pilot/pilot.py start --deployment /srv/ophiolite/pilotinstall applies the project schema and migrations in their documented order and
creates the pilot identities with the operator CLI (tools/project-admin.py): token
files are written owner-only and only their hashes enter the database. No Ophiolite
account, subscription or licence server is contacted. Browser sign-in through your own
identity provider is configured separately (see Deployment choices).
Upgrade
Section titled “Upgrade”python3 tools/pilot/pilot.py upgrade --deployment /srv/ophiolite/pilot \ --components /srv/ophiolite/components-next --archive /backups/before-upgrade.tar.gzThe sequence stops every process (native service, worker, gateway), takes a backup,
switches to the new pinned components (and binary, with --server), re-applies the
schema and migrations, starts and re-verifies every recorded exact revision and
refusal. Keep each release’s components in their own directory; do not check a new
release out over a running one. Downgrade is not supported: restore the
before-upgrade backup into a fresh database and directory instead.
Back up and restore
Section titled “Back up and restore”python3 tools/pilot/pilot.py stop --deployment /srv/ophiolite/pilotpython3 tools/pilot/pilot.py backup --deployment /srv/ophiolite/pilot --archive /backups/pilot.tar.gzpython3 tools/pilot/pilot.py restore --archive /backups/pilot.tar.gz --deployment /srv/ophiolite/restored \ --dsn "host=db2 port=5432 user=ophiolite dbname=ophiolite" --components /srv/ophiolite/components \ --server /srv/ophiolite/bin/arraybridge_server --secrets /srv/ophiolite/pilot/secretsA backup is taken while the deployment is stopped (a controlled write pause). It holds the project database dump, the gateway journal with every payload-store object it references (verified), and the source configuration, with a SHA-256 manifest. Restore checks the whole archive before touching anything (a changed, missing, extra, duplicated or unsafe member refuses), requires an empty target database and a new directory, then restores. If a restore fails part-way, drop that database and directory and run it again; the archive is never modified. Keep backups off the host.
Storage and limits
Section titled “Storage and limits”Retained bytes live in a content-addressed payload store. The default is a directory
beside the gateway journal; set OPHIOLITE_PAYLOAD_STORE to use another place:
OPHIOLITE_PAYLOAD_STORE=local:/srv/ophiolite/payloadsOPHIOLITE_PAYLOAD_STORE=s3:https://objects.example.com/ophiolite-bucket/pilotOPHIOLITE_PAYLOAD_STORE_CREDENTIALS=/srv/ophiolite/secrets/s3.json # {"access_key", "secret_key", "region"}, mode 0600An S3-compatible store keeps the same rules as the local one: objects are written once and verified on every read, one store serves one gateway journal, unreferenced objects are removed only by the offline sweep after a grace period. Credentials come only from the private file; bucket names and keys never appear in responses. A store that cannot be reached answers “busy, retry” (HTTP 503) rather than reporting damaged data. Backups copy the objects into local files; restore fills an empty store (an interrupted restore of the same backup resumes) before the journal is published.
Limits are per deployment: OPHIOLITE_MAX_UPLOAD_BYTES (default 8 MiB, at most
32 MiB) is enforced from the declared size before any upload byte is read;
OPHIOLITE_SCIENTIFIC_READS (default 2) and OPHIOLITE_SCIENTIFIC_READ_WAIT_MS
(default 10000) set how many exact reads run at once and how long a request waits for a
turn before “busy, retry”. Exact reads accept one HTTP byte range and always carry the
whole representation’s SHA-256 in X-Content-SHA256.
Leave with your data
Section titled “Leave with your data”python3 tools/pilot/pilot.py exit --deployment /srv/ophiolite/pilot --output /exports/bundleexit exports the recorded exact revisions (well log, result, tops, survey, grid) as a
portable bundle through the Python SDK, stops the server, and reads and
recalculates them in a separate Python process with networking blocked. See
Take exact curves with you. A backup restores a
deployment; a bundle is how you use the data without one.
Who is responsible for what (customer-operated mode)
Section titled “Who is responsible for what (customer-operated mode)”| Area | Operator (you) | Ophiolite software |
|---|---|---|
| Storage | Hosts the PostgreSQL database, the gateway journal and the payload store; can read all of them | Stores exact bytes content-addressed; never deletes during operation |
| Compute | Runs the native service, gateway and worker; Python calculations run on users’ computers | Records runs and results; no hosted execution |
| Access | Creates identities and project membership; configures the identity provider | Enforces project membership, per-asset grants, revocation and withdrawal |
| Operations | Backups, restores, upgrades, monitoring, TLS, network policy | Provides the pilot tool, migrations and verification |
| Exit | Chooses when to export | Portable bundles readable without the server |
| Telemetry | Disabled by default; an operator may configure an OpenTelemetry endpoint of their own | Sends nothing to Ophiolite |
What the operator can see: everything stored on the host — database rows (members, grants, activity), journal records (uploads, runs, receipts, sharing), payload bytes and logs. Users’ local Python work stays on their computers.
Release notes — pilot release 2026-09-27
Section titled “Release notes — pilot release 2026-09-27”- Sharing cutover announced. Replacing recipients without the version you saw
(unconditional sharing) is deprecated. This release adds the switch
OPHIOLITE_REQUIRE_CONDITIONAL_SHARING=1, which refuses it (HTTP 428,condition-required) and changes nothing. It is off by default in this release and will be on by default in the next release. Workspace and the current SDK already share conditionally. - New since the previous pilot release: result versions, the local payload store, portable bundles, well tops/trajectories/horizon grids, connector capability pages and explicit updates for locked sources.
Not covered by this pilot
Section titled “Not covered by this pilot”Container images and compose, systemd activation with install-server.py --apply,
Caddy TLS and Keycloak/browser sign-in in the automated job, ARM64, privately managed
mode, server-to-server migration with identity mapping, public build inputs and
licence files (E17), and the matching source/notices package.
