Skip to main content

Updates and release channels

Two things update independently, with two different commands:

  • The tritonadm binary on your workstation or head node. tritonadm self-update replaces it.
  • The deployed cloud, which is the control-plane zones and the global-zone agents. tritonadm update reprovisions the zones and extracts the agents again.

Both commands read the same signed release channel, so this page starts with the channel.

How a channel works

A channel is a minisign-signed JSON manifest published at https://tritoncloud.nyc3.digitaloceanspaces.com/channels/<NAME>.json. A detached signature is published at the same URL plus .minisig. Continuous integration publishes two named channels:

ChannelPublished from
edgeBuilds of main.
stableBuilds from a v* tag.

tritonadm uses stable when you pass neither --channel nor --channel-url. A channel exists only after something is published to it. stable resolves only after a tagged build has run. No tagged build has been published yet, so pass --channel edge on every command that reads the channel.

The manifest declares a schema version, the channel name, an updated_at timestamp, a publisher string, an optional sealed revision, and four artifact maps: images, agents, services, and tritonadm. Every artifact entry has a build stamp in YYYYMMDDTHHMMSSZ form, a lowercase hex sha256, and a size in bytes. Agent, service, and tritonadm entries have one url. An image entry has a manifest_url and a content_url. tritonadm understands schema version 1. It refuses a manifest that declares a higher schema version and does not parse it.

What tritonadm verifies

Every channel fetch that tritonadm performs downloads both the manifest and its .minisig. It verifies the signature against the publisher public key compiled into the binary from cli/tritonadm/publisher.pub (minisign key id 6A95AFF9C8B898E7). A signature that does not verify stops the command with channel signature did NOT verify against publisher pubkey. tritonadm then compares the downloaded artifact bytes against the sha256 in that signed manifest.

The tools/install.sh bootstrap script does not perform this check. It verifies the sha256 of the tritonadm tarball against the channel JSON it fetched over TLS, and nothing more. Its trust root is TLS to the channel host. Every later channel fetch by tritonadm itself, including self-update --check, enforces the publisher signature. See Install the tritonadm CLI.

Select a channel

Three flags select the manifest. They appear on install, update, and self-update.

FlagEffect
--channel <NAME>Expands to https://tritoncloud.nyc3.digitaloceanspaces.com/channels/<NAME>.json.
--channel-url <URL>Uses this manifest URL as given. Takes precedence over --channel.
--revision <REV>Points the resolved URL at the frozen snapshot .../channels/<NAME>/<REV>.json.

tritonadm channel revisions accepts only --channel-url and --channel.

The CLI config file does not store the selection. Pass the selector on each command, and pass the same selector to every command in one run.

The cluster records one upstream, the channel.upstream_url setting. tritonadm setup converge reads it when you pass no --channel. tritonadm channel refresh mirrors it into the in-cluster channel that compute nodes install from. Genesis does not set it. Set it once after genesis, on any host with a signed-in tritonadm:

tritonadm config set channel.upstream_url https://tritoncloud.nyc3.digitaloceanspaces.com/channels/edge.json

tritonadm channel refresh then fetches the upstream and verifies it against the publisher key. It signs the manifest again with the cluster's own channel-signing key and publishes it in the cluster. Compute nodes fetch from the booter's mirror, never from the upstream. --revision <STAMP> pins the mirror to a sealed revision. --no-wait returns the operation id instead of waiting.

Check what is installed

The CLI

Run this on any host where tritonadm is installed.

tritonadm self-update --check

The command prints the stamp compiled into the running binary and the stamp that the channel advertises for this binary's target triple.

installed: <INSTALLED_STAMP>
candidate: <CANDIDATE_STAMP> (<BYTES> bytes)

When the two stamps match, the command prints already up to date and exits zero. When they differ, --check exits non-zero. You can use this exit code as a gate in automation.

tritonadm --version prints the crate version from Cargo.toml. The channel identifies builds by stamp, not by that version. self-update --check is the comparison that matters.

The channel contents and the host

On the head node, in the global zone, as root:

tritonadm install --list

The command prints the channel name and updated_at, then the images, agents, and tritonadm maps. It reads the installed status from the host: imgadm list -H -o uuid for images, and /opt/triton/<NAME>/etc/version for agents.

The deployed components

On the head node, in the global zone, as root:

tritonadm update --check --all

--check plans every component without changes. It reports how many updates are available and how many components failed to plan. It changes nothing.

Update the CLI

Run self-update as a user that can write to the install directory. On a head node that directory is /opt/triton/bin, so run it as root.

tritonadm self-update

The sequence is:

  1. Resolve the channel URL from --channel-url, --channel, and --revision.
  2. Fetch the manifest and its .minisig. Verify the signature against the compiled-in publisher key.
  3. Find the entry for this binary's target triple. The triple is compiled in, not detected at run time. A channel with no entry for it fails with channel has no tritonadm entry for target <TARGET>.
  4. Compare the entry's stamp with the compiled-in build stamp. Stop if they match.
  5. Download the tarball. Verify its sha256 against the signed manifest. Extract the tritonadm binary from the top level of the archive.
  6. Replace the binary atomically.

The replacement copies the new binary to <INSTALL_DIR>/tritonadm.new. It renames the live binary to <INSTALL_DIR>/tritonadm.prev. Then it renames .new over tritonadm. Both the extracted binary and the staged copy get mode 0755. The command prints where the new binary is and where the previous binary is kept.

tritonadm updated at <INSTALL_DIR>/tritonadm
previous binary preserved at <INSTALL_DIR>/tritonadm.prev (manually delete when satisfied)
FlagEffect
--channel-url <URL>Override the channel manifest URL.
--channel <NAME>Named channel. --channel-url takes precedence.
--revision <REV>Update to, or roll back to, the frozen snapshot of a sealed revision.
--install-dir <DIR>Override the install directory. Defaults to the directory that contains the running executable.
--checkReport installed against candidate and exit. Exits non-zero when they differ.
--image-dir <DIR>Use the newest local tritonadm-<STAMP>.tar.gz instead of the channel. Conflicts with --channel-url, --channel, and --revision.

Roll back the CLI

tritonadm.prev survives one update cycle, so you can reverse a bad release without a download. Move tritonadm.prev back over tritonadm by hand, or run tritonadm self-update --revision <REV> with a known-good sealed revision.

Update the deployed cloud

danger

tritonadm update reprovisions and restarts running control-plane components. A zone reprovision replaces the immutable zone root and reboots the zone. NICs, customer_metadata, and a delegated /data dataset survive. Plan for the control plane to be unavailable while the command runs.

Run update on the head node, in the global zone, as root. Plan first:

tritonadm update --check --all

Then apply:

tritonadm update --all

You can name components instead of --all. A command with neither components nor --all is a usage error.

tritonadm update tritonagent proteusadm

Components

ComponentAliasesWhat the update does
tritonadmDelegates to self-update, with this run's channel or --image-dir.
tritondReprovisions the triton-tritond zone from the triton-platform image.
adminuiadmin-backend, uiReprovisions the same triton-tritond zone. The admin UI is part of the platform image.
tritonagentagentExtracts the agent bundle again under /opt/triton/tritonagent. Restarts its SMF service when the bundle changed.
proteusadmExtracts the bundle again. It has no SMF manifest, so no service is registered or restarted.
fdbtriton-fdb, triton-fdb0Reprovisions the triton-fdb0 zone from the triton-platform image.
clickhousetriton-clickhouseReprovisions the triton-clickhouse zone from the triton-clickhouse image.
mantadtriton-mantadReprovisions every contiguous triton-mantadN zone from the triton-platform image. Uses the unindexed triton-mantad alias when no numbered zone exists.

--all walks the components in this order: tritond, tritonagent, proteusadm, fdb, clickhouse, mantad, tritonadm. tritonadm runs last because it replaces the binary that drives the run. adminui is not a separate --all entry, because the tritond update already reprovisions that zone.

How a run behaves

update first plans every component without changes and prints a preview for each. Then it applies. Consequences of that split:

  • --check and --dry-run stop after the preview and change nothing.
  • An artifact that is missing from the source is reported as a skip that names the source. It is not an error. An agent reports not in channel; skip or not in --image-dir; skip. An image prefixes the image name, as in triton-platform not in channel; skip.
  • A zone that does not exist is reported as zone <ALIAS> not provisioned; skip. update never provisions an absent zone. That is what Genesis on the founder does.
  • An unknown component name logs a warning to stderr, and the command skips it.
  • Zone lookup uses triton-fdb1 when triton-fdb0 is absent, and triton-tritond1 when triton-tritond is absent.
  • A component that is already on the channel's stamp reports that and does nothing.
  • The tritonadm component is not counted in the --check and --dry-run totals. Under --check, its preview prints the tritonadm self-update --check command to run instead.

One confirmation covers the whole run. It appears only when at least one planned action would modify or remove running state:

Apply the updates above? This reprovisions/restarts running components.

The default answer is No. Pass --yes (visible alias --force) to skip the prompt in automation.

FlagEffect
--allUpdate every known component that is present in both the source and the host.
--checkReport what is outdated. Changes nothing.
--dry-runPrint the planned actions. Changes nothing.
--yes, --forceSkip the confirmation prompt.
--channel-url <URL>Override the channel manifest URL.
--channel <NAME>Named channel. --channel-url takes precedence.
--revision <REV>Update against the frozen snapshot of a sealed revision.
--image-dir <DIR>Use a local directory of built images and agent tarballs. Conflicts with --channel-url, --channel, and --revision.

The FoundationDB data-format gate

A reprovision of the FDB zone is gated on the data_format_min_read of the incoming image against the zone's on-disk /data/version. The planning pass evaluates the gate before any change, so the FDB zone is never reprovisioned across a data-format gap. A gate failure is reported as an error against that component. The error text names the migration runbook, and the run exits non-zero. The other components named in the same run still apply.

Pin or roll back to a revision

Every published build is also sealed as an immutable, signed snapshot named after its build stamp. A signed revision index records it next to the moving channel pointer. List the snapshots:

tritonadm channel revisions --channel edge

The listing names the channel. It marks the revision that the moving pointer advertises now. It prints the sealed revisions, newest first.

channel: <CHANNEL>
current: <REVISION>

=== revisions (newest first) ===
<REVISION> sealed=<PUBLISHED_AT> by=<PUBLISHER> <- current

Each of those ids is a valid --revision value for install, update, and self-update. To pin the whole head node to a known-good revision:

tritonadm update --all --revision <REVISION>

A frozen snapshot is a full manifest signed by the same publisher key as the moving pointer. It goes through the same verification.

Update from local artifacts

--image-dir replaces the signed channel with a directory of locally built files, for development and air-gapped hosts. It is available on update and self-update. On both commands it conflicts with --channel-url, --channel, and --revision.

tritonadm update --all --image-dir /var/tmp/artifacts

In that directory, update reads images from a <STEM>.imgmanifest or <STEM>.json paired with a <STEM>.zfs.gz next to it. It reads agents from <NAME>-<STAMP>.tar.gz for the known agent names tritonagent and proteusadm. It reads the CLI from the newest tritonadm-<STAMP>.tar.gz. When several stamps are present, the newest wins. If the directory has no tritonadm tarball, the self-update step reports not in --image-dir; skip and does not fail later.

warning

--image-dir bypasses the release channel. It therefore bypasses the minisign signature check and the sha256 comparison against a signed manifest. Point it only at artifacts that you built or trust.

Next steps