Files
MoShiro/packaging/install.sh
T
justme 83e5120377 refactor!: rename the project from Monitor to MoShiro
Namespaces, assemblies, projects and directories, the solution, binaries,
images, systemd units, config paths, environment variables, protocol method
names, the media type and the raw chunk magic all move to MoShiro/moshiro.
Existing data and deployments are not compatible and must be recreated.
Also fix the architecture tests after the solution layout change and make
the update tests independent of their order.
2026-10-07 01:49:04 +08:00

190 lines
7.3 KiB
Bash

#!/bin/sh
# Installs moshiro-agent or moshiro-probe from an extracted release directory (the directory this script lives in).
# POSIX sh: runs on Debian/Ubuntu/Alpine/OpenWrt (busybox).
#
# ./install.sh agent --server https://panel.example.com --join <join-token> --name hk-1
# ./install.sh probe [--probe-json /path/to/probe.json]
# ./install.sh uninstall agent|probe [--purge]
#
# Binaries go to /usr/lib/moshiro (root-owned: the collector cannot rewrite its own executable);
# config and identity go to /etc/moshiro (owned by the unprivileged `moshiro` user).
set -eu
PREFIX=/usr/lib/moshiro
CONFIG=/etc/moshiro
USER_NAME=moshiro
HERE="$(cd "$(dirname "$0")" && pwd)"
# busybox on OpenWrt has no `install`
put() { cp "$2" "$3" && chmod "$1" "$3"; }
die() { echo "install.sh: $*" >&2; exit 1; }
say() { echo "==> $*"; }
[ "$(id -u)" -eq 0 ] || die "run as root"
init_system() {
if [ -d /run/systemd/system ]; then echo systemd
elif [ -f /etc/openwrt_release ]; then echo procd
else echo none; fi
}
check_openssl() {
for dir in /lib /usr/lib /lib64 /usr/lib64 /usr/lib/x86_64-linux-gnu /usr/lib/aarch64-linux-gnu /lib/x86_64-linux-gnu /lib/aarch64-linux-gnu; do
ls "$dir"/libssl.so.3* >/dev/null 2>&1 && return 0
done
die "OpenSSL 3 (libssl.so.3) is required. Debian/Ubuntu: apt install libssl3 | Alpine: apk add libssl3 | OpenWrt: opkg install libopenssl3 (newer snapshots: apk add libopenssl3)"
}
ensure_user() {
id "$USER_NAME" >/dev/null 2>&1 && return 0
if command -v useradd >/dev/null 2>&1; then
useradd --system --no-create-home --shell /usr/sbin/nologin "$USER_NAME"
elif command -v adduser >/dev/null 2>&1; then
adduser -S -D -H -s /sbin/nologin "$USER_NAME" 2>/dev/null || adduser -S -H -s /bin/false "$USER_NAME" 2>/dev/null || true
fi
if ! id "$USER_NAME" >/dev/null 2>&1 && [ -w /etc/passwd ] && [ -w /etc/group ]; then
# OpenWrt: no useradd/adduser in the default busybox; add a system user by hand
uid=900
while grep -q "^[^:]*:[^:]*:$uid:" /etc/passwd /etc/group 2>/dev/null; do uid=$((uid + 1)); done
echo "$USER_NAME:x:$uid:" >>/etc/group
echo "$USER_NAME:x:$uid:$uid:$USER_NAME:/var/run/$USER_NAME:/bin/false" >>/etc/passwd
fi
id "$USER_NAME" >/dev/null 2>&1 || {
echo "warning: could not create the '$USER_NAME' user; the service will run as root" >&2
return 1
}
}
install_binary() {
src="$1"
[ -f "$HERE/$src" ] || die "$HERE/$src not found (is this an extracted release?)"
mkdir -p "$PREFIX"
put 0755 "$HERE/$src" "$PREFIX/$src"
}
write_agent_config() {
cat >"$CONFIG/agent.json" <<JSON
{
"fleet": { "server": "$1", "identity_dir": "$CONFIG" },
"listen": { "control_port": 7443, "udp_ports": [7443], "tcp_ports": [7444] },
"limits": { "max_total_mbps": 200, "max_total_pps": 20000, "allowed_target_cidrs": [], "max_concurrent_tests": 1 }
}
JSON
chmod 0640 "$CONFIG/agent.json"
if [ "$have_user" -eq 1 ]; then chown "root:$(id -gn "$USER_NAME")" "$CONFIG/agent.json"; fi
}
install_role() {
role="$1"; shift
server=""; join=""; name=""; probe_json=""; no_start=0
while [ $# -gt 0 ]; do
case "$1" in
--server) server="$2"; shift 2 ;;
--join) join="$2"; shift 2 ;;
--name) name="$2"; shift 2 ;;
--probe-json) probe_json="$2"; shift 2 ;;
--no-start) no_start=1; shift ;;
*) die "unknown option: $1" ;;
esac
done
check_openssl
have_user=0
ensure_user && have_user=1
mkdir -p "$CONFIG"
if [ "$have_user" -eq 1 ]; then chown "$USER_NAME" "$CONFIG"; fi
chmod 0750 "$CONFIG"
install_binary "moshiro-$role"
if [ "$role" = agent ]; then install_binary fleet-enroll; fi
say "installed binaries to $PREFIX"
init="$(init_system)"
case "$init" in
systemd)
put 0644 "$HERE/systemd/moshiro-$role.service" "/etc/systemd/system/moshiro-$role.service"
if [ "$have_user" -eq 0 ]; then sed -i '/^User=/d;/^Group=/d' "/etc/systemd/system/moshiro-$role.service"; fi
systemctl daemon-reload ;;
procd)
[ "$role" = probe ] || die "the agent is meant for servers; on OpenWrt only the probe is supported"
put 0755 "$HERE/openwrt/moshiro-probe.init" /etc/init.d/moshiro-probe
mkdir -p /lib/upgrade/keep.d
put 0644 "$HERE/openwrt/moshiro.keep" /lib/upgrade/keep.d/moshiro ;;
*) echo "warning: no systemd or procd found: start $PREFIX/moshiro-$role --config $CONFIG/$role.json with your own supervisor" >&2 ;;
esac
ready=0
if [ "$role" = agent ]; then
if [ -n "$server" ] && [ ! -f "$CONFIG/node.json" ]; then
[ -n "$join" ] && [ -n "$name" ] || die "--server needs --join and --name to enroll"
say "enrolling as $name"
if [ "$have_user" -eq 1 ]; then
su -s /bin/sh "$USER_NAME" -c "'$PREFIX/fleet-enroll' --server '$server' --join '$join' --name '$name' --identity-dir '$CONFIG'"
else
"$PREFIX/fleet-enroll" --server "$server" --join "$join" --name "$name" --identity-dir "$CONFIG"
fi
fi
if [ ! -f "$CONFIG/agent.json" ] && [ -n "$server" ]; then write_agent_config "$server"; fi
if [ -f "$CONFIG/agent.json" ] && [ -f "$CONFIG/node.json" ]; then ready=1; fi
else
if [ -n "$probe_json" ]; then
put 0600 "$probe_json" "$CONFIG/probe.json"
if [ "$have_user" -eq 1 ]; then chown "$USER_NAME" "$CONFIG/probe.json"; fi
fi
if [ -f "$CONFIG/probe.json" ]; then ready=1; fi
fi
if [ "$ready" -eq 1 ] && [ "$no_start" -eq 0 ]; then
case "$init" in
systemd) systemctl enable --now "moshiro-$role" ;;
procd) /etc/init.d/moshiro-probe enable; /etc/init.d/moshiro-probe restart ;;
esac
say "moshiro-$role is installed"
else
say "installed, not started yet. Next:"
if [ "$role" = agent ]; then
echo " $PREFIX/fleet-enroll --server <panel-url> --join <token> --name <name> --identity-dir $CONFIG (as the '$USER_NAME' user)"
echo " write $CONFIG/agent.json (see README.md), then: systemctl enable --now moshiro-agent"
else
echo " save the panel's probe identity (POST /api/admin/probe/identity) as $CONFIG/probe.json (mode 0600, owner $USER_NAME)"
echo " then: systemctl enable --now moshiro-probe (OpenWrt: /etc/init.d/moshiro-probe enable && /etc/init.d/moshiro-probe start)"
fi
fi
}
uninstall() {
role="$1"; purge=0
if [ "${2:-}" = "--purge" ]; then purge=1; fi
case "$(init_system)" in
systemd)
systemctl disable --now "moshiro-$role" 2>/dev/null || true
rm -f "/etc/systemd/system/moshiro-$role.service"
systemctl daemon-reload ;;
procd)
/etc/init.d/moshiro-probe stop 2>/dev/null || true
/etc/init.d/moshiro-probe disable 2>/dev/null || true
rm -f /etc/init.d/moshiro-probe /lib/upgrade/keep.d/moshiro ;;
esac
rm -f "$PREFIX/moshiro-$role"
if [ "$role" = agent ]; then rm -f "$PREFIX/fleet-enroll"; fi
rmdir "$PREFIX" 2>/dev/null || true
if [ "$purge" -eq 1 ]; then
rm -rf "$CONFIG"
say "removed $CONFIG (identity included: the node must enroll again)"
else
say "kept $CONFIG (use --purge to remove the identity as well)"
fi
}
cmd="${1:-}"
case "$cmd" in
agent|probe) shift; install_role "$cmd" "$@" ;;
uninstall)
shift
role="${1:-}"
[ "$role" = agent ] || [ "$role" = probe ] || die "usage: install.sh uninstall agent|probe [--purge]"
shift
uninstall "$role" "$@" ;;
*) die "usage: install.sh agent|probe [options] | uninstall agent|probe [--purge]" ;;
esac