Add Host API and fix kiosk performance

This commit is contained in:
Audiobuzz
2026-06-28 03:14:25 +00:00
parent b5163f958e
commit ad6b7e3366
12 changed files with 747 additions and 37 deletions
+56 -3
View File
@@ -233,6 +233,13 @@ build {
destination = "/tmp/"
}
# Workstation host-info API (Go). Source staged to /tmp/hostapi; compiled +
# installed in the 2b-hostapi step. The kiosk SPA reads it at localhost:9099.
provisioner "file" {
source = "files/hostapi"
destination = "/tmp/"
}
# Custom 'fleet' Plymouth theme (scripted security-handshake splash). Staged to
# /tmp/plymouth, installed + set default in the package step before dracut runs.
provisioner "file" {
@@ -418,8 +425,13 @@ build {
# --use-pixman + chromium --disable-gpu — candidate to drop once the kiosk
# is display-verified; see TODO #4.)
"dnf install -y --setopt=tsflags=nodocs weston chromium mesa-dri-drivers mesa-libEGL mesa-libgbm dejavu-sans-fonts",
# Unprivileged, passwordless kiosk user; video/input as a seat fallback.
# Unprivileged, passwordless kiosk user. Groups: 'video' (KMS /dev/dri/card0
# for weston) + 'input' (libinput) as a seat fallback; 'render'
# (/dev/dri/renderD128) so Chromium's GPU process can do hardware raster on
# real hardware (kiosk-session enables GPU when a real KMS driver is present;
# render nodes aren't logind-seat-ACL'd on EL9, so group membership is needed).
"id kiosk >/dev/null 2>&1 || useradd -m -G video,input kiosk",
"getent group render >/dev/null 2>&1 && usermod -aG render kiosk || true",
# Install the staged unit, weston config, and session wrapper.
"install -D -m0755 /tmp/kiosk/kiosk-session /usr/local/bin/kiosk-session",
"install -D -m0644 /tmp/kiosk/kiosk.service /etc/systemd/system/kiosk.service",
@@ -452,6 +464,44 @@ build {
]
}
# --- 2b-hostapi. Workstation host-info API (Go, loopback, read-only) ------
# Compiles files/hostapi into /usr/local/bin/fleet-hostapi and enables it as a
# systemd service the kiosk SPA reads at http://localhost:9099/v1/host (the
# HOST-API.md contract). Build-time, image-GENERIC facts (image version +
# weston/chromium versions) are written to /etc/fleet-hostinfo.json; everything
# host-specific (kernel, hostname, IP, MAC, board, uptime) is read at RUNTIME,
# so NO per-host state lands in the image (invariant #1). The Go toolchain is
# installed here and removed in 2d hygiene; it never ships.
provisioner "shell" {
environment_vars = [
"IMAGE_VERSION=${var.image_version}",
]
inline = [
"set -euxo pipefail",
"dnf -y install golang",
# Reproducible, dependency-free static build (the verity hash must be a pure
# function of the inputs — invariant #8). GOPROXY=off + GOTOOLCHAIN=local
# guarantee no network/toolchain fetch; -trimpath + -buildid= strip paths
# and the build id. Stdlib-only, so this needs no modules. NOTE: a golang
# package update changes the binary (hence the hash) — a reproducibility-
# sensitive input, like the STIG semanage store; build twice to confirm.
"install -d -m0755 /tmp/gocache",
"env -C /tmp/hostapi CGO_ENABLED=0 GOOS=linux GOARCH=amd64 GOPROXY=off GOTOOLCHAIN=local GOFLAGS=-mod=mod GOCACHE=/tmp/gocache GOPATH=/tmp/gopath go build -trimpath -buildvcs=false -ldflags '-s -w -buildid=' -o /usr/local/bin/fleet-hostapi .",
"chmod 0755 /usr/local/bin/fleet-hostapi",
"install -D -m0644 /tmp/hostapi/fleet-hostapi.service /etc/systemd/system/fleet-hostapi.service",
# Build-time facts file (image-generic; same for every host of a release).
# rpm '%%{...}' is doubled so Packer's HCL2 doesn't parse %{ as a directive.
"WESTON_VER=$(rpm -q --qf '%%{VERSION}' weston 2>/dev/null || echo '')",
"CHROMIUM_VER=$(rpm -q --qf '%%{VERSION}' chromium 2>/dev/null || rpm -q --qf '%%{VERSION}' chromium-browser 2>/dev/null || echo '')",
"printf '{\"image\":\"%s\",\"weston\":\"%s\",\"chromium\":\"%s\"}\\n' \"$IMAGE_VERSION\" \"$WESTON_VER\" \"$CHROMIUM_VER\" > /etc/fleet-hostinfo.json",
"chmod 0644 /etc/fleet-hostinfo.json",
"restorecon -R /usr/local/bin/fleet-hostapi /etc/systemd/system/fleet-hostapi.service /etc/fleet-hostinfo.json 2>/dev/null || true",
"systemctl enable fleet-hostapi.service",
"rm -rf /tmp/hostapi /tmp/gocache /tmp/gopath",
"echo '==> fleet-hostapi enabled (localhost:9099/v1/host)'",
]
}
# --- 2c. Admin access: sudo-enabled key user + locked root --------------
# Fleet-generic (same user + key on every host => NOT per-host state). The
# key comes from var.ssh_authorized_key (CI secret). If no key is supplied we
@@ -701,9 +751,9 @@ build {
# custom kiosk files: add them to fapolicyd's trust DB and rebuild it. weston
# /chromium are RPM-installed so already trusted. (See docs/stig-deviations.md.)
"if command -v fapolicyd-cli >/dev/null 2>&1; then",
" for f in /usr/local/bin/kiosk-session /usr/local/bin/fleet-sb-enroll; do { [ -f \"$f\" ] && fapolicyd-cli --file add \"$f\"; } || true; done",
" for f in /usr/local/bin/kiosk-session /usr/local/bin/fleet-sb-enroll /usr/local/bin/fleet-hostapi; do { [ -f \"$f\" ] && fapolicyd-cli --file add \"$f\"; } || true; done",
" fapolicyd-cli --update 2>/dev/null || true",
" echo '==> fapolicyd: trusted custom binaries (kiosk-session, fleet-sb-enroll) + rebuilt trust db'",
" echo '==> fapolicyd: trusted custom binaries (kiosk-session, fleet-sb-enroll, fleet-hostapi) + rebuilt trust db'",
"fi",
]
}
@@ -776,6 +826,9 @@ build {
# already downloaded to the host) — slims the erofs + cuts attack surface.
# Keep auditd (it's part of the hardened runtime). Best-effort.
"dnf remove -y openscap-scanner scap-security-guide openscap-utils 2>/dev/null || true",
# The Go toolchain was only needed to compile fleet-hostapi (2b-hostapi);
# the static binary ships, the compiler does not.
"dnf remove -y golang 2>/dev/null || true",
# The build-time STIG reports must not ship inside the read-only rootfs.
"rm -f /root/stig-report.html /root/stig-arf.xml",
"dnf clean all",