rig/bin/rig
Daniel Marin be3761a5df
Merge pull request #27 from dan-claude-bot/feat/users-and-traits
Machine traits + fleet users: class/host/join presets and rig users apply/status/close-root (#26 + #24)
2026-07-17 22:24:50 +01:00

170 lines
5 KiB
Bash
Executable file

#!/usr/bin/env bash
set -euo pipefail
ROOT="$(cd "$(dirname "$(readlink -f "${BASH_SOURCE[0]}")")/.." && pwd)"
usage() {
cat <<'EOF'
usage: rig <command> [args]
commands:
bootstrap <control-plane|workload|runner|staging|dev|workstation|custom>
[--hostname <name>] [--class <human|server>] [--host <yes|no>]
[--join <authkey|login>]
OS plumbing on a pristine Debian box: hardening, unattended-upgrades,
tailscale join. Roles are presets over the three traits; any flag
overrides its trait, and custom states all of them. Prompts for a
single-use TAGGED tailnet pre-auth key (TS_AUTHKEY env overrides the
prompt); the key's tags are the tailnet tag, verified after join —
only control-plane and workload may carry tag:server. join=login
(workstation) needs no key: interactive login, node must come up
untagged. Run as root.
coolify install --version <pin>
Pinned Coolify install (AUTOUPDATE=false). Control-plane box only.
coolify backup install [options]
Nightly age-encrypted dump of the control-plane database, as a
systemd timer. rig installs the machinery and templates an empty
0600 bindings file; you fill in the age recipient and S3 details.
Control-plane box only. Run as root.
db <dump|restore> ...
Ad-hoc PostgreSQL dump/restore for a container on this box. `dump`
writes a gzipped SQL artifact (--no-owner --no-acl, so it restores
onto a different instance); `restore` loads one back, connecting as
the container's own superuser, behind a confirm gate. Run as root.
runner install --repo <owner/repo> [options]
GitHub Actions runner as a systemd service under an unprivileged
user — outbound-only, no Docker. Prompts for the short-lived
registration token (RUNNER_TOKEN env overrides). Run as root.
runner status [--user <name>]
What this box's runner is registered to: repo, name, labels, unit.
Reads the box only — no token, no network call. Run as root.
runner remove [--local] [--user <name>]
Take the service down and deregister the runner. Prompts for the
short-lived removal token (RUNNER_REMOVE_TOKEN env overrides).
Run as root.
runner repoint --repo <owner/repo> [options]
Move an installed runner to another repository — deregister, then
re-register, reusing the binary already on the box. Needs a removal
token for the old repo and a registration token for the new one.
Run as root.
users apply --file <path>
Converge named operator accounts from a declarative users file, on
every class: groups by role (admin/rig/box), passwords locked always,
authorized_keys made exact, visudo-gated sudoers rules. Users dropped
from the file are locked, never deleted. '-' reads stdin. Run as root.
users status
Roles (derived from actual group membership), key counts and lock
state for the rig-managed users. Reads the box only. Run as root.
users close-root
Shut root SSH on a class=human box once an admin key works. Refuses
on class=server — root there is the control plane's automation door —
and while no admin holds a key. Run as root.
install/upgrade:
curl -fsSL https://raw.githubusercontent.com/heavy-duty/rig/main/install.sh | bash
EOF
}
cmd="${1:-}"
case "$cmd" in
bootstrap)
shift
exec "$ROOT/commands/bootstrap.sh" "$@"
;;
coolify)
shift
sub="${1:-}"
case "$sub" in
install)
shift
exec "$ROOT/commands/coolify-install.sh" "$@"
;;
backup)
shift
if [ "${1:-}" != "install" ]; then
usage >&2
exit 2
fi
shift
exec "$ROOT/commands/coolify-backup-install.sh" "$@"
;;
*)
usage >&2
exit 2
;;
esac
;;
db)
shift
case "${1:-}" in
dump|restore|-h|--help)
exec "$ROOT/commands/db.sh" "$@"
;;
*)
usage >&2
exit 2
;;
esac
;;
runner)
shift
sub="${1:-}"
case "$sub" in
install)
shift
exec "$ROOT/commands/runner-install.sh" "$@"
;;
status)
shift
exec "$ROOT/commands/runner-status.sh" "$@"
;;
remove)
shift
exec "$ROOT/commands/runner-remove.sh" "$@"
;;
repoint)
shift
exec "$ROOT/commands/runner-repoint.sh" "$@"
;;
*)
usage >&2
exit 2
;;
esac
;;
users)
shift
sub="${1:-}"
case "$sub" in
apply)
shift
exec "$ROOT/commands/users-apply.sh" "$@"
;;
status)
shift
exec "$ROOT/commands/users-status.sh" "$@"
;;
close-root)
shift
exec "$ROOT/commands/users-close-root.sh" "$@"
;;
*)
usage >&2
exit 2
;;
esac
;;
-h|--help|help)
usage
exit 0
;;
"")
usage >&2
exit 2
;;
*)
printf 'rig: unknown command: %s\n' "$cmd" >&2
usage >&2
exit 2
;;
esac