Files
nmon/scripts/fetch-vm.sh

85 lines
4.0 KiB
Bash
Executable File

#!/usr/bin/env bash
# Fetch VictoriaMetrics single-node, verify it, and stage it for go:embed.
#
# For each of linux/amd64 and linux/arm64 this produces, in internal/vmsup/bin/:
# victoria-metrics-prod-linux-<arch> the extracted binary (used by tests)
# victoria-metrics-prod-linux-<arch>.gz gzbin of it (what vmembed embeds)
#
# The release tarball is checked against the release's _checksums.txt AND
# against the SHA-256 pinned below. The same hashes are pinned in
# internal/vmsup/pins.go; keep the two in step when bumping VM_VERSION.
# Idempotent: nothing is downloaded when the outputs already match the pins.
set -euo pipefail
VM_VERSION="v1.153.0"
BASE_URL="https://github.com/VictoriaMetrics/VictoriaMetrics/releases/download/${VM_VERSION}"
# SHA-256 of victoria-metrics-linux-<arch>-<version>.tar.gz
PIN_TAR_AMD64="1b495bde563825cf83dc7c0425a9d8fa03e7214858e0949f9177efc6bb1f8bfc"
PIN_TAR_ARM64="3d5f965b7a75f713742a7f37195c1d845f47d9dc9d096a2cce29e693f08fd641"
# SHA-256 of the extracted victoria-metrics-prod binary
PIN_BIN_AMD64="f7dcb151fd1fef69364d6d6da49c0d3f1b9c2415ef4b4432b08e416a5c73a49b"
PIN_BIN_ARM64="bba4c4f46cda51beff65b55c41e59b99e310387c72fd96ee83134d2fa20848e5"
# SHA-256 of the .gz produced by internal/vmsup/internal/gzbin (Go compress/gzip,
# BestCompression, zero header), so it does not depend on the host's gzip.
PIN_GZ_AMD64="2a5e0c1a7fe9825b3ab0a1f2652471608736736670eb6d8953273f4743f909d1"
PIN_GZ_ARM64="d7d763d9f81fc3ab7fb3da5a71ce36e8b3e3083d331f7733d1eec9998da23d78"
ROOT="$(cd "$(dirname "${BASH_SOURCE[0]}")/.." && pwd)"
OUT="${ROOT}/internal/vmsup/bin"
die() { echo "fetch-vm: $*" >&2; exit 1; }
sha() { sha256sum "$1" | awk '{print $1}'; }
if ! command -v sha256sum >/dev/null; then die "sha256sum not found"; fi
if ! command -v curl >/dev/null; then die "curl not found"; fi
mkdir -p "$OUT"
work="$(mktemp -d)"
trap 'rm -rf "$work"' EXIT
fetch_arch() {
local arch="$1" pin_tar="$2" pin_bin="$3" pin_gz="$4"
local bin="${OUT}/victoria-metrics-prod-linux-${arch}"
local gz="${bin}.gz"
if [[ -f "$bin" && -f "$gz" && "$(sha "$bin")" == "$pin_bin" ]]; then
echo "fetch-vm: linux/${arch} already present (${pin_bin:0:12})"
return 0
fi
local name="victoria-metrics-linux-${arch}-${VM_VERSION}"
local d="${work}/${arch}"
mkdir -p "$d/x"
echo "fetch-vm: downloading ${name}.tar.gz"
curl -fsSL --retry 3 -o "${d}/${name}.tar.gz" "${BASE_URL}/${name}.tar.gz"
curl -fsSL --retry 3 -o "${d}/${name}_checksums.txt" "${BASE_URL}/${name}_checksums.txt"
local got
got="$(sha "${d}/${name}.tar.gz")"
[[ "$got" == "$pin_tar" ]] || die "${name}.tar.gz: sha256 ${got} does not match pinned ${pin_tar}"
local listed
listed="$(awk -v f="${name}.tar.gz" '$2 == f {print $1}' "${d}/${name}_checksums.txt")"
[[ "$listed" == "$got" ]] || die "${name}.tar.gz: sha256 ${got} does not match release checksums (${listed:-none})"
# Extract only the one member, by name, into an empty directory.
tar -xzf "${d}/${name}.tar.gz" -C "${d}/x" victoria-metrics-prod
got="$(sha "${d}/x/victoria-metrics-prod")"
[[ "$got" == "$pin_bin" ]] || die "victoria-metrics-prod (${arch}): sha256 ${got} does not match pinned ${pin_bin}"
listed="$(awk '$2 == "victoria-metrics-prod" {print $1}' "${d}/${name}_checksums.txt")"
[[ -z "$listed" || "$listed" == "$got" ]] || die "victoria-metrics-prod (${arch}): does not match release checksums (${listed})"
command -v go >/dev/null || die "go not found (needed to build the reproducible .gz)"
(cd "$ROOT" && go run ./internal/vmsup/internal/gzbin "${d}/x/victoria-metrics-prod" "${d}/bin.gz")
got="$(sha "${d}/bin.gz")"
[[ "$got" == "$pin_gz" ]] || die "${arch} .gz: sha256 ${got} does not match pinned ${pin_gz}"
# Install atomically so an interrupted run never leaves a half file.
install -m 0755 "${d}/x/victoria-metrics-prod" "${bin}.tmp" && mv -f "${bin}.tmp" "$bin"
install -m 0644 "${d}/bin.gz" "${gz}.tmp" && mv -f "${gz}.tmp" "$gz"
echo "fetch-vm: linux/${arch} ready (${pin_bin:0:12})"
}
fetch_arch amd64 "$PIN_TAR_AMD64" "$PIN_BIN_AMD64" "$PIN_GZ_AMD64"
fetch_arch arm64 "$PIN_TAR_ARM64" "$PIN_BIN_ARM64" "$PIN_GZ_ARM64"