forked from Eeveid/lightOps
- 仅在 x86_64-unknown-linux-gnu 目标已安装且存在 x86_64-linux-gnu-gcc 时才选择 GNU 交叉目标 - 打包脚本在目标等于当前 Rust host target 时改为原生 cargo build,不再显式传 --target - 避免 cc-rs 在原生构建场景下错误寻找 x86_64-linux-gnu-gcc 导致发布失败
200 lines
5.2 KiB
Bash
Executable File
200 lines
5.2 KiB
Bash
Executable File
#!/usr/bin/env bash
|
||
set -Eeuo pipefail
|
||
|
||
VERSION=""
|
||
TARGET=""
|
||
OUTPUT_DIR="target/releases"
|
||
SKIP_BUILD="false"
|
||
|
||
usage() {
|
||
cat <<'EOF'
|
||
LightOps 发布包打包脚本
|
||
|
||
用法:
|
||
bash scripts/build-release.sh [选项]
|
||
|
||
选项:
|
||
--version <version> 发布版本,默认读取 Cargo.toml workspace 版本并追加 git 短提交
|
||
--target <triple> Rust target triple,例如 x86_64-unknown-linux-gnu
|
||
--output-dir <path> 输出目录,默认 target/releases
|
||
--skip-build 跳过构建,只打包现有产物
|
||
-h, --help 显示帮助
|
||
EOF
|
||
}
|
||
|
||
while [[ $# -gt 0 ]]; do
|
||
case "$1" in
|
||
--version)
|
||
VERSION="${2:?缺少 --version 参数值}"
|
||
shift 2
|
||
;;
|
||
--target)
|
||
TARGET="${2:?缺少 --target 参数值}"
|
||
shift 2
|
||
;;
|
||
--output-dir)
|
||
OUTPUT_DIR="${2:?缺少 --output-dir 参数值}"
|
||
shift 2
|
||
;;
|
||
--skip-build)
|
||
SKIP_BUILD="true"
|
||
shift
|
||
;;
|
||
-h|--help)
|
||
usage
|
||
exit 0
|
||
;;
|
||
*)
|
||
echo "未知参数:$1" >&2
|
||
usage >&2
|
||
exit 2
|
||
;;
|
||
esac
|
||
done
|
||
|
||
log() {
|
||
printf '\033[1;32m[LightOps]\033[0m %s\n' "$*"
|
||
}
|
||
|
||
fail() {
|
||
printf '\033[1;31m[LightOps]\033[0m %s\n' "$*" >&2
|
||
exit 1
|
||
}
|
||
|
||
require_cmd() {
|
||
command -v "$1" >/dev/null 2>&1 || fail "缺少命令:$1"
|
||
}
|
||
|
||
repo_root() {
|
||
git rev-parse --show-toplevel 2>/dev/null || pwd
|
||
}
|
||
|
||
detect_version() {
|
||
local base sha
|
||
base="$(sed -nE '/^\[workspace\.package\]/,/^\[/{s/^version[[:space:]]*=[[:space:]]*"([^"]+)".*/\1/p}' Cargo.toml | head -n 1)"
|
||
if [[ -z "$base" ]]; then
|
||
base="0.1.0"
|
||
fi
|
||
sha="$(git rev-parse --short HEAD 2>/dev/null || true)"
|
||
if [[ -n "$sha" ]]; then
|
||
echo "${base}-${sha}"
|
||
else
|
||
echo "$base"
|
||
fi
|
||
}
|
||
|
||
detect_platform() {
|
||
local os arch
|
||
os="$(uname -s | tr '[:upper:]' '[:lower:]')"
|
||
arch="$(uname -m)"
|
||
case "$arch" in
|
||
x86_64|amd64) arch="x86_64" ;;
|
||
aarch64|arm64) arch="aarch64" ;;
|
||
esac
|
||
echo "${arch}-${os}"
|
||
}
|
||
|
||
ROOT="$(repo_root)"
|
||
cd "$ROOT"
|
||
|
||
require_cmd tar
|
||
if [[ "$SKIP_BUILD" != "true" ]]; then
|
||
require_cmd npm
|
||
require_cmd cargo
|
||
fi
|
||
|
||
if [[ -z "$VERSION" ]]; then
|
||
VERSION="$(detect_version)"
|
||
fi
|
||
|
||
PLATFORM="${TARGET:-$(detect_platform)}"
|
||
PACKAGE_NAME="lightops-${VERSION}-${PLATFORM}"
|
||
STAGE_DIR="target/release-package/${PACKAGE_NAME}"
|
||
ARCHIVE_PATH="${OUTPUT_DIR}/${PACKAGE_NAME}.tar.gz"
|
||
HOST_TARGET="$(rustc -vV 2>/dev/null | sed -n 's/^host: //p')"
|
||
NATIVE_TARGET="false"
|
||
if [[ -n "$TARGET" && -n "$HOST_TARGET" && "$TARGET" == "$HOST_TARGET" ]]; then
|
||
NATIVE_TARGET="true"
|
||
fi
|
||
|
||
if [[ "$SKIP_BUILD" != "true" ]]; then
|
||
log "构建前端"
|
||
cd "$ROOT/web"
|
||
if [[ -f package-lock.json ]]; then
|
||
npm ci
|
||
else
|
||
npm install
|
||
fi
|
||
npm run build
|
||
|
||
log "构建 Rust 二进制"
|
||
cd "$ROOT"
|
||
if [[ -n "$TARGET" && "$NATIVE_TARGET" != "true" ]]; then
|
||
cargo build --release --target "$TARGET" -p lightops-server -p lightops-agent
|
||
BIN_DIR="target/${TARGET}/release"
|
||
else
|
||
cargo build --release -p lightops-server -p lightops-agent
|
||
BIN_DIR="target/release"
|
||
fi
|
||
else
|
||
cd "$ROOT"
|
||
if [[ -n "$TARGET" && "$NATIVE_TARGET" != "true" ]]; then
|
||
BIN_DIR="target/${TARGET}/release"
|
||
else
|
||
BIN_DIR="target/release"
|
||
fi
|
||
fi
|
||
|
||
SERVER_BIN="${BIN_DIR}/lightops-server"
|
||
AGENT_BIN="${BIN_DIR}/lightops-agent"
|
||
if [[ "$(uname -s)" == MINGW* || "$(uname -s)" == MSYS* || "$(uname -s)" == CYGWIN* ]]; then
|
||
[[ -f "${SERVER_BIN}.exe" ]] && SERVER_BIN="${SERVER_BIN}.exe"
|
||
[[ -f "${AGENT_BIN}.exe" ]] && AGENT_BIN="${AGENT_BIN}.exe"
|
||
fi
|
||
|
||
[[ -f "$SERVER_BIN" ]] || fail "缺少 lightops-server 构建产物:$SERVER_BIN"
|
||
[[ -f "$AGENT_BIN" ]] || fail "缺少 lightops-agent 构建产物:$AGENT_BIN"
|
||
[[ -d "$ROOT/web/dist" ]] || fail "缺少前端构建产物:web/dist"
|
||
|
||
log "整理发布目录:$STAGE_DIR"
|
||
rm -rf "$STAGE_DIR"
|
||
mkdir -p "$STAGE_DIR/bin" "$STAGE_DIR/web" "$STAGE_DIR/scripts" "$STAGE_DIR/config" "$OUTPUT_DIR"
|
||
|
||
install -m 0755 "$SERVER_BIN" "$STAGE_DIR/bin/lightops-server"
|
||
install -m 0755 "$AGENT_BIN" "$STAGE_DIR/bin/lightops-agent"
|
||
cp -a "$ROOT/web/dist" "$STAGE_DIR/web/dist"
|
||
cp -a "$ROOT/store" "$STAGE_DIR/store"
|
||
install -m 0755 "$ROOT/scripts/install-server-release.sh" "$STAGE_DIR/scripts/install-server-release.sh"
|
||
install -m 0755 "$ROOT/scripts/install-agent.sh" "$STAGE_DIR/scripts/install-agent.sh"
|
||
install -m 0755 "$ROOT/scripts/upgrade-agent.sh" "$STAGE_DIR/scripts/upgrade-agent.sh"
|
||
install -m 0755 "$ROOT/scripts/uninstall-agent.sh" "$STAGE_DIR/scripts/uninstall-agent.sh"
|
||
install -m 0755 "$ROOT/scripts/update-from-git.sh" "$STAGE_DIR/scripts/update-from-git.sh"
|
||
cp "$ROOT/config/server.toml.example" "$STAGE_DIR/config/server.toml.example"
|
||
|
||
cat >"$STAGE_DIR/RELEASE.txt" <<EOF
|
||
LightOps 发布包
|
||
|
||
版本:$VERSION
|
||
平台:$PLATFORM
|
||
构建时间:$(date -Is)
|
||
提交:$(git rev-parse HEAD 2>/dev/null || echo unknown)
|
||
EOF
|
||
|
||
log "生成压缩包:$ARCHIVE_PATH"
|
||
tar -C "$(dirname "$STAGE_DIR")" -czf "$ARCHIVE_PATH" "$(basename "$STAGE_DIR")"
|
||
|
||
if command -v sha256sum >/dev/null 2>&1; then
|
||
sha256sum "$ARCHIVE_PATH" >"${ARCHIVE_PATH}.sha256"
|
||
elif command -v shasum >/dev/null 2>&1; then
|
||
shasum -a 256 "$ARCHIVE_PATH" >"${ARCHIVE_PATH}.sha256"
|
||
fi
|
||
|
||
cat <<EOF
|
||
|
||
发布包已生成:
|
||
$ARCHIVE_PATH
|
||
|
||
安装命令示例:
|
||
curl -fsSL https://gitea.kmux.cn/Eeveid/lightOps/raw/branch/main/scripts/install-server-release.sh | bash -s -- --url <发布包下载地址>
|
||
EOF
|