feat(install): default to Go agent binary from release agent-v0.6.8, drop Node.js dependency; NG_AGENT_IMPL=node fallback via run.sh; shell-only enroll JSON; units ExecStart the Go binary
This commit is contained in:
@@ -1,12 +1,20 @@
|
|||||||
#!/sbin/openrc-run
|
#!/sbin/openrc-run
|
||||||
|
|
||||||
description="NexusGate node agent"
|
description="NexusGate node agent"
|
||||||
command="/opt/nexusgate-agent/run.sh"
|
command="/opt/nexusgate-agent/nexusgate-agent"
|
||||||
command_background="yes"
|
command_background="yes"
|
||||||
pidfile="/run/nexusgate-agent.pid"
|
pidfile="/run/nexusgate-agent.pid"
|
||||||
output_log="/var/log/nexusgate/agent.log"
|
output_log="/var/log/nexusgate/agent.log"
|
||||||
error_log="/var/log/nexusgate/agent-error.log"
|
error_log="/var/log/nexusgate/agent-error.log"
|
||||||
|
|
||||||
|
# Go 二进制直接从环境变量读取 NG_CONTROLLER/NG_AGENT_KEY;OpenRC 不读
|
||||||
|
# /etc/nexusgate/agent.env,这里在服务脚本里手动 source 并导出。
|
||||||
|
if [ -f /etc/nexusgate/agent.env ]; then
|
||||||
|
set -a
|
||||||
|
. /etc/nexusgate/agent.env
|
||||||
|
set +a
|
||||||
|
fi
|
||||||
|
|
||||||
depend() {
|
depend() {
|
||||||
need net
|
need net
|
||||||
use nexusgate-sing-box
|
use nexusgate-sing-box
|
||||||
|
|||||||
+81
-11
@@ -3,6 +3,11 @@ set -Eeuo pipefail
|
|||||||
|
|
||||||
REPO="${NG_REPO:-aaaamoooo/NexusGate}"
|
REPO="${NG_REPO:-aaaamoooo/NexusGate}"
|
||||||
BRANCH="${NG_BRANCH:-main}"
|
BRANCH="${NG_BRANCH:-main}"
|
||||||
|
# Agent 实现:默认 go(静态二进制,节点机不再需要 Node.js)。
|
||||||
|
# NG_AGENT_IMPL=node 可回退到旧版 Node agent(agent/agent.js + nodejs 包)。
|
||||||
|
AGENT_IMPL="${NG_AGENT_IMPL:-go}"
|
||||||
|
# Go agent 二进制所在的 GitHub Release tag
|
||||||
|
AGENT_RELEASE="${NG_AGENT_RELEASE:-agent-v0.6.8}"
|
||||||
CONTROLLER=""
|
CONTROLLER=""
|
||||||
TOKEN=""
|
TOKEN=""
|
||||||
|
|
||||||
@@ -20,6 +25,44 @@ fetch() {
|
|||||||
fi
|
fi
|
||||||
}
|
}
|
||||||
|
|
||||||
|
# uname -m → release 资产架构名(amd64/arm64)
|
||||||
|
agent_arch() {
|
||||||
|
case "$(uname -m)" in
|
||||||
|
x86_64|amd64) printf 'amd64' ;;
|
||||||
|
aarch64|arm64) printf 'arm64' ;;
|
||||||
|
*) return 1 ;;
|
||||||
|
esac
|
||||||
|
}
|
||||||
|
|
||||||
|
# uname -m → Node 风格架构名(注册信息用,与旧版 process.arch 输出一致)
|
||||||
|
node_arch() {
|
||||||
|
case "$(uname -m)" in
|
||||||
|
x86_64|amd64) printf 'x64' ;;
|
||||||
|
aarch64|arm64) printf 'arm64' ;;
|
||||||
|
*) uname -m ;;
|
||||||
|
esac
|
||||||
|
}
|
||||||
|
|
||||||
|
# 下载 Go agent 二进制到 $1(NG_LOCAL_SRC 时从 agent-go/ 取已构建产物)
|
||||||
|
fetch_agent_binary() {
|
||||||
|
local arch out="$1"
|
||||||
|
arch="$(agent_arch)" || die "不支持的架构:$(uname -m)"
|
||||||
|
if [[ -n "${NG_LOCAL_SRC:-}" && -f "${NG_LOCAL_SRC}/agent-go/nexusgate-agent-linux-${arch}" ]]; then
|
||||||
|
cp -a "${NG_LOCAL_SRC}/agent-go/nexusgate-agent-linux-${arch}" "$out"
|
||||||
|
else
|
||||||
|
curl -fL --retry 3 "https://github.com/${REPO}/releases/download/${AGENT_RELEASE}/nexusgate-agent-linux-${arch}" -o "$out"
|
||||||
|
fi
|
||||||
|
[[ -s "$out" ]] || die 'Agent 二进制下载不完整'
|
||||||
|
}
|
||||||
|
|
||||||
|
# 极简 JSON 字符串转义(注册请求拼 JSON 用)
|
||||||
|
json_escape() {
|
||||||
|
local s="$1"
|
||||||
|
s="${s//\\/\\\\}"
|
||||||
|
s="${s//\"/\\\"}"
|
||||||
|
printf '"%s"' "$s"
|
||||||
|
}
|
||||||
|
|
||||||
while [[ $# -gt 0 ]]; do
|
while [[ $# -gt 0 ]]; do
|
||||||
case "$1" in
|
case "$1" in
|
||||||
--server) CONTROLLER="${2:-}"; shift 2 ;;
|
--server) CONTROLLER="${2:-}"; shift 2 ;;
|
||||||
@@ -33,25 +76,43 @@ done
|
|||||||
[[ "${EUID}" -eq 0 ]] || die "请使用 root 运行"
|
[[ "${EUID}" -eq 0 ]] || die "请使用 root 运行"
|
||||||
[[ "$CONTROLLER" =~ ^https?:// ]] || die "--server 必须是完整的 HTTP(S) 地址"
|
[[ "$CONTROLLER" =~ ^https?:// ]] || die "--server 必须是完整的 HTTP(S) 地址"
|
||||||
[[ -n "$TOKEN" ]] || die "缺少 --token"
|
[[ -n "$TOKEN" ]] || die "缺少 --token"
|
||||||
|
[[ "$AGENT_IMPL" == "go" || "$AGENT_IMPL" == "node" ]] || die "NG_AGENT_IMPL 只能是 go 或 node"
|
||||||
|
extra_pkgs=()
|
||||||
|
if [[ "$AGENT_IMPL" == "node" ]]; then
|
||||||
|
# 仅回退到 Node 实现时才需要 nodejs
|
||||||
|
extra_pkgs=(nodejs)
|
||||||
|
fi
|
||||||
if command -v apt-get >/dev/null; then
|
if command -v apt-get >/dev/null; then
|
||||||
export DEBIAN_FRONTEND=noninteractive
|
export DEBIAN_FRONTEND=noninteractive
|
||||||
apt-get update -qq && apt-get install -y -qq ca-certificates curl unzip nodejs openssl logrotate
|
apt-get update -qq && apt-get install -y -qq ca-certificates curl unzip openssl logrotate "${extra_pkgs[@]}"
|
||||||
elif command -v dnf >/dev/null; then
|
elif command -v dnf >/dev/null; then
|
||||||
dnf install -y ca-certificates curl unzip nodejs openssl logrotate
|
dnf install -y ca-certificates curl unzip openssl logrotate "${extra_pkgs[@]}"
|
||||||
elif command -v apk >/dev/null; then
|
elif command -v apk >/dev/null; then
|
||||||
apk add --no-cache bash ca-certificates curl unzip nodejs openrc openssl logrotate
|
apk add --no-cache bash ca-certificates curl unzip openrc openssl logrotate "${extra_pkgs[@]}"
|
||||||
else
|
else
|
||||||
die "当前安装器支持 Debian/Ubuntu、RHEL 系和 Alpine"
|
die "当前安装器支持 Debian/Ubuntu、RHEL 系和 Alpine"
|
||||||
fi
|
fi
|
||||||
node_major="$(node -p 'process.versions.node.split(`.`)[0]')"
|
if [[ "$AGENT_IMPL" == "node" ]]; then
|
||||||
[[ "$node_major" -ge 18 ]] || die "需要 Node.js 18 或更高版本"
|
node_major="$(node -p 'process.versions.node.split(`.`)[0]')"
|
||||||
|
[[ "$node_major" -ge 18 ]] || die "需要 Node.js 18 或更高版本"
|
||||||
|
fi
|
||||||
|
|
||||||
tmp_dir="$(mktemp -d /tmp/nexusgate-agent.XXXXXX)"
|
tmp_dir="$(mktemp -d /tmp/nexusgate-agent.XXXXXX)"
|
||||||
trap 'rm -rf -- "$tmp_dir"' EXIT
|
trap 'rm -rf -- "$tmp_dir"' EXIT
|
||||||
|
|
||||||
install -d -m 0755 /opt/nexusgate-agent /usr/local/sbin
|
install -d -m 0755 /opt/nexusgate-agent /usr/local/sbin
|
||||||
fetch agent/agent.js /opt/nexusgate-agent/agent.js
|
if [[ "$AGENT_IMPL" == "node" ]]; then
|
||||||
fetch agent/run.sh /opt/nexusgate-agent/run.sh
|
fetch agent/agent.js /opt/nexusgate-agent/agent.js
|
||||||
|
fetch agent/run.sh /opt/nexusgate-agent/run.sh
|
||||||
|
chmod 0644 /opt/nexusgate-agent/agent.js
|
||||||
|
chmod 0755 /opt/nexusgate-agent/run.sh
|
||||||
|
rm -f -- /opt/nexusgate-agent/nexusgate-agent
|
||||||
|
else
|
||||||
|
fetch_agent_binary "$tmp_dir/nexusgate-agent"
|
||||||
|
install -m 0755 "$tmp_dir/nexusgate-agent" /opt/nexusgate-agent/nexusgate-agent
|
||||||
|
# 从 Node 实现迁移过来的节点:清掉旧文件,避免新旧实现混淆
|
||||||
|
rm -f -- /opt/nexusgate-agent/agent.js /opt/nexusgate-agent/run.sh
|
||||||
|
fi
|
||||||
fetch scripts/agent-update.sh /usr/local/sbin/ng-agent-update
|
fetch scripts/agent-update.sh /usr/local/sbin/ng-agent-update
|
||||||
fetch scripts/agent-uninstall.sh /usr/local/sbin/ng-agent-uninstall
|
fetch scripts/agent-uninstall.sh /usr/local/sbin/ng-agent-uninstall
|
||||||
fetch scripts/agent-doctor.sh /usr/local/sbin/ng-agent-doctor
|
fetch scripts/agent-doctor.sh /usr/local/sbin/ng-agent-doctor
|
||||||
@@ -71,8 +132,7 @@ case "${1:-}" in
|
|||||||
*) printf 'NexusGate Agent: ng-agent doctor | ng-agent cert | ng-agent engine install | ng-agent update | ng-agent uninstall\n' ;;
|
*) printf 'NexusGate Agent: ng-agent doctor | ng-agent cert | ng-agent engine install | ng-agent update | ng-agent uninstall\n' ;;
|
||||||
esac
|
esac
|
||||||
EOF
|
EOF
|
||||||
chmod 0644 /opt/nexusgate-agent/agent.js
|
chmod 0755 /usr/local/sbin/ng-agent-update /usr/local/sbin/ng-agent-uninstall /usr/local/sbin/ng-agent-doctor /usr/local/sbin/ng-agent-cert /usr/local/sbin/ng-agent-singbox /usr/local/sbin/ng-agent
|
||||||
chmod 0755 /opt/nexusgate-agent/run.sh /usr/local/sbin/ng-agent-update /usr/local/sbin/ng-agent-uninstall /usr/local/sbin/ng-agent-doctor /usr/local/sbin/ng-agent-cert /usr/local/sbin/ng-agent-singbox /usr/local/sbin/ng-agent
|
|
||||||
install -d -m 0700 /etc/nexusgate /etc/nexusgate/agent /etc/nexusgate/agent/resources /etc/nexusgate/sing-box
|
install -d -m 0700 /etc/nexusgate /etc/nexusgate/agent /etc/nexusgate/agent/resources /etc/nexusgate/sing-box
|
||||||
install -d -m 0750 /var/log/nexusgate
|
install -d -m 0750 /var/log/nexusgate
|
||||||
install -m 0644 "$tmp_dir/logrotate.conf" /etc/nexusgate/agent-logrotate.conf
|
install -m 0644 "$tmp_dir/logrotate.conf" /etc/nexusgate/agent-logrotate.conf
|
||||||
@@ -81,9 +141,11 @@ install -m 0755 "$tmp_dir/logrotate-setup.sh" /usr/local/sbin/ng-agent-logrotate
|
|||||||
NG_REPO="$REPO" NG_BRANCH="$BRANCH" ng-agent-singbox install || die 'sing-box 引擎安装失败;修复后运行 ng-agent engine install'
|
NG_REPO="$REPO" NG_BRANCH="$BRANCH" ng-agent-singbox install || die 'sing-box 引擎安装失败;修复后运行 ng-agent engine install'
|
||||||
|
|
||||||
info "向控制面注册"
|
info "向控制面注册"
|
||||||
enroll_json="$(TOKEN_VALUE="$TOKEN" node -e 'process.stdout.write(JSON.stringify({token:process.env.TOKEN_VALUE,hostname:require("node:os").hostname(),version:"0.6.8",system:{platform:process.platform,arch:process.arch}}))')"
|
enroll_json="$(printf '{"token":%s,"hostname":%s,"version":"0.6.8","system":{"platform":"linux","arch":%s}}' \
|
||||||
|
"$(json_escape "$TOKEN")" "$(json_escape "$(hostname)")" "$(json_escape "$(node_arch)")")"
|
||||||
response="$(curl -fsS -H 'content-type: application/json' --data "$enroll_json" "${CONTROLLER%/}/api/agent/enroll")" || die "注册失败,请检查地址和令牌"
|
response="$(curl -fsS -H 'content-type: application/json' --data "$enroll_json" "${CONTROLLER%/}/api/agent/enroll")" || die "注册失败,请检查地址和令牌"
|
||||||
agent_key="$(RESPONSE_VALUE="$response" node -e 'const r=JSON.parse(process.env.RESPONSE_VALUE); if(!r.agentKey) process.exit(1); process.stdout.write(r.agentKey)')" || die "控制面返回无效"
|
agent_key="$(printf '%s' "$response" | grep -o '"agentKey"[[:space:]]*:[[:space:]]*"[^"]*"' | head -n 1 | sed -E 's/^"agentKey"[[:space:]]*:[[:space:]]*"//; s/"$//')"
|
||||||
|
[[ -n "$agent_key" ]] || die "控制面返回无效"
|
||||||
|
|
||||||
{
|
{
|
||||||
printf 'NG_CONTROLLER=%q\n' "${CONTROLLER%/}"
|
printf 'NG_CONTROLLER=%q\n' "${CONTROLLER%/}"
|
||||||
@@ -96,6 +158,10 @@ chmod 0600 /etc/nexusgate/agent.env
|
|||||||
if command -v systemctl >/dev/null && [[ -d /run/systemd/system ]]; then
|
if command -v systemctl >/dev/null && [[ -d /run/systemd/system ]]; then
|
||||||
fetch systemd/nexusgate-agent.service /etc/systemd/system/nexusgate-agent.service
|
fetch systemd/nexusgate-agent.service /etc/systemd/system/nexusgate-agent.service
|
||||||
fetch systemd/nexusgate-sing-box.service /etc/systemd/system/nexusgate-sing-box.service
|
fetch systemd/nexusgate-sing-box.service /etc/systemd/system/nexusgate-sing-box.service
|
||||||
|
if [[ "$AGENT_IMPL" == "node" ]]; then
|
||||||
|
# 仓库里的 unit 默认指向 Go 二进制;Node 回退改为经 run.sh 启动
|
||||||
|
sed -i 's|^ExecStart=.*|ExecStart=/opt/nexusgate-agent/run.sh|' /etc/systemd/system/nexusgate-agent.service
|
||||||
|
fi
|
||||||
systemctl daemon-reload
|
systemctl daemon-reload
|
||||||
systemctl enable nexusgate-sing-box.service nexusgate-agent.service
|
systemctl enable nexusgate-sing-box.service nexusgate-agent.service
|
||||||
rm -f -- /etc/nexusgate/last-heartbeat.json
|
rm -f -- /etc/nexusgate/last-heartbeat.json
|
||||||
@@ -107,6 +173,10 @@ elif command -v rc-service >/dev/null; then
|
|||||||
fetch openrc/nexusgate-agent /etc/init.d/nexusgate-agent
|
fetch openrc/nexusgate-agent /etc/init.d/nexusgate-agent
|
||||||
fetch openrc/nexusgate-sing-box /etc/init.d/nexusgate-sing-box
|
fetch openrc/nexusgate-sing-box /etc/init.d/nexusgate-sing-box
|
||||||
chmod 0755 /etc/init.d/nexusgate-agent /etc/init.d/nexusgate-sing-box
|
chmod 0755 /etc/init.d/nexusgate-agent /etc/init.d/nexusgate-sing-box
|
||||||
|
if [[ "$AGENT_IMPL" == "node" ]]; then
|
||||||
|
# 仓库里的 OpenRC 服务默认指向 Go 二进制;Node 回退改为经 run.sh 启动
|
||||||
|
sed -i 's|^command=.*|command="/opt/nexusgate-agent/run.sh"|' /etc/init.d/nexusgate-agent
|
||||||
|
fi
|
||||||
rc-update add nexusgate-sing-box default >/dev/null
|
rc-update add nexusgate-sing-box default >/dev/null
|
||||||
rc-update add nexusgate-agent default >/dev/null
|
rc-update add nexusgate-agent default >/dev/null
|
||||||
# Alpine runs the dedicated hourly task through BusyBox crond.
|
# Alpine runs the dedicated hourly task through BusyBox crond.
|
||||||
|
|||||||
@@ -6,7 +6,7 @@ Wants=network-online.target
|
|||||||
[Service]
|
[Service]
|
||||||
Type=simple
|
Type=simple
|
||||||
EnvironmentFile=/etc/nexusgate/agent.env
|
EnvironmentFile=/etc/nexusgate/agent.env
|
||||||
ExecStart=/usr/bin/node --max-old-space-size=64 --optimize-for-size --max-semi-space-size=4 /opt/nexusgate-agent/agent.js
|
ExecStart=/opt/nexusgate-agent/nexusgate-agent
|
||||||
Restart=always
|
Restart=always
|
||||||
RestartSec=5
|
RestartSec=5
|
||||||
NoNewPrivileges=true
|
NoNewPrivileges=true
|
||||||
|
|||||||
Reference in New Issue
Block a user