diff --git a/.gitea/workflows/deploy.yml b/.gitea/workflows/deploy.yml index 62c330a..1eb46b3 100644 --- a/.gitea/workflows/deploy.yml +++ b/.gitea/workflows/deploy.yml @@ -61,12 +61,55 @@ jobs: - name: 安装基础依赖 + 确保 Node 22 可用 + 校验 node/git/npm 可用 run: | set -euxo pipefail - command -v git || (apt-get update -qq && DEBIAN_FRONTEND=noninteractive apt-get install -yqq --no-install-recommends git ca-certificates) - command -v curl || (apt-get update -qq && DEBIAN_FRONTEND=noninteractive apt-get install -yqq --no-install-recommends curl ca-certificates) - command -v tar || (apt-get update -qq && DEBIAN_FRONTEND=noninteractive apt-get install -yqq --no-install-recommends tar) - command -v xz || command -v unxz || (apt-get update -qq && DEBIAN_FRONTEND=noninteractive apt-get install -yqq --no-install-recommends xz-utils) || true - command -v node && echo "系统 node: $(node -v)" || echo "系统 node: 未安装" - command -v npm && echo "系统 npm: $(npm -v)" || echo "系统 npm: 未安装" + + # 先统一探测:只有当下列命令/包任意一个缺失时,才统一执行 1 次 apt-get update + install + NEED_APT_UPDATE=0 + need_cmd() { + local cmd="$1" + if ! command -v "${cmd}" >/dev/null 2>&1; then + NEED_APT_UPDATE=1 + return 1 + fi + return 0 + } + need_pkg() { + local pkg="$1" + if command -v dpkg >/dev/null 2>&1; then + if dpkg -s "${pkg}" >/dev/null 2>&1; then + return 0 + fi + NEED_APT_UPDATE=1 + return 1 + fi + return 0 + } + + NEED_GIT=0; need_cmd git || NEED_GIT=1 + NEED_CURL=0; need_cmd curl || NEED_CURL=1 + NEED_CA=0; need_pkg ca-certificates || NEED_CA=1 + NEED_TAR=0; need_cmd tar || NEED_TAR=1 + NEED_XZ=0; (need_cmd xz || need_cmd unxz) || NEED_XZ=1 + + APT_MISSING=() + [ "${NEED_GIT}" = "1" ] && APT_MISSING+=("git") + [ "${NEED_CURL}" = "1" ] && APT_MISSING+=("curl") + [ "${NEED_CA}" = "1" ] && APT_MISSING+=("ca-certificates") + [ "${NEED_TAR}" = "1" ] && APT_MISSING+=("tar") + [ "${NEED_XZ}" = "1" ] && APT_MISSING+=("xz-utils") + + if [ "${#APT_MISSING[@]}" -gt 0 ]; then + echo "[apt][preflight] 检测到缺包: ${APT_MISSING[*]},执行 1 次 apt-get update + install" + if command -v sudo >/dev/null 2>&1; then + sudo apt-get update -qq 2>/dev/null || apt-get update -qq 2>/dev/null || true + sudo DEBIAN_FRONTEND=noninteractive apt-get install -yqq --no-install-recommends "${APT_MISSING[@]}" 2>/dev/null || \ + DEBIAN_FRONTEND=noninteractive apt-get install -yqq --no-install-recommends "${APT_MISSING[@]}" 2>/dev/null || true + else + apt-get update -qq 2>/dev/null || true + DEBIAN_FRONTEND=noninteractive apt-get install -yqq --no-install-recommends "${APT_MISSING[@]}" 2>/dev/null || true + fi + else + echo "[apt][preflight] 所有基础命令/包已存在,跳过 apt-get update(节省 30-90s)" + fi if command -v node >/dev/null 2>&1; then CUR_NODE_MAJOR="$(node -v | tr -d 'v' | cut -d. -f1 || echo 0)" @@ -365,32 +408,92 @@ jobs: steps: - name: 系统环境准备(Ubuntu 22.04 默认镜像源换清华 + 全局 GitHub gh-proxy) run: | - set -euxo pipefail - if command -v apt-get >/dev/null 2>&1; then - sudo apt-get update -qq 2>/dev/null || apt-get update -qq 2>/dev/null || true - sudo DEBIAN_FRONTEND=noninteractive apt-get install -yqq --no-install-recommends ca-certificates 2>/dev/null || \ - DEBIAN_FRONTEND=noninteractive apt-get install -yqq --no-install-recommends ca-certificates 2>/dev/null || true + set -euo pipefail + + # 只在真的缺包时才跑 apt-get update(Runner 通常自带 git/curl/ca-certificates/tar/xz,99% 场景直接跳过) + NEED_APT_UPDATE=0 + need_cmd() { + local cmd="$1" + if ! command -v "${cmd}" >/dev/null 2>&1; then + NEED_APT_UPDATE=1 + return 1 + fi + return 0 + } + need_pkg() { + local pkg="$1" + if command -v dpkg >/dev/null 2>&1; then + if dpkg -s "${pkg}" >/dev/null 2>&1; then + return 0 + fi + NEED_APT_UPDATE=1 + return 1 + fi + return 0 + } + + NEED_GIT=0; need_cmd git || NEED_GIT=1 + NEED_CURL=0; need_cmd curl || NEED_CURL=1 + NEED_CA=0; need_pkg ca-certificates || NEED_CA=1 + NEED_TAR=0; need_cmd tar || NEED_TAR=1 + NEED_XZ=0; (need_cmd xz || need_cmd unxz) || NEED_XZ=1 + + APT_MISSING=() + [ "${NEED_GIT}" = "1" ] && APT_MISSING+=("git") + [ "${NEED_CURL}" = "1" ] && APT_MISSING+=("curl") + [ "${NEED_CA}" = "1" ] && APT_MISSING+=("ca-certificates") + [ "${NEED_TAR}" = "1" ] && APT_MISSING+=("tar") + [ "${NEED_XZ}" = "1" ] && APT_MISSING+=("xz-utils") + + if [ "${#APT_MISSING[@]}" -gt 0 ]; then + echo "[apt] 检测到缺包: ${APT_MISSING[*]},执行 apt-get update + install" + if command -v sudo >/dev/null 2>&1; then + sudo apt-get update -qq 2>/dev/null || apt-get update -qq 2>/dev/null || true + sudo DEBIAN_FRONTEND=noninteractive apt-get install -yqq --no-install-recommends "${APT_MISSING[@]}" 2>/dev/null || \ + DEBIAN_FRONTEND=noninteractive apt-get install -yqq --no-install-recommends "${APT_MISSING[@]}" 2>/dev/null || true + else + apt-get update -qq 2>/dev/null || true + DEBIAN_FRONTEND=noninteractive apt-get install -yqq --no-install-recommends "${APT_MISSING[@]}" 2>/dev/null || true + fi + else + echo "[apt] 所有基础命令/包已存在,跳过 apt-get update(节省 30-90s)" + fi + if command -v update-ca-certificates >/dev/null 2>&1; then sudo update-ca-certificates 2>/dev/null || update-ca-certificates 2>/dev/null || true fi + # 镜像源替换:只在命中官方 archive.ubuntu.com / security.ubuntu.com 时才 sed,避免破坏 Runner 已配好的公司/国内镜像 + APT_SOURCES_HIT=0 if command -v apt-get >/dev/null 2>&1 && [ -f /etc/apt/sources.list ]; then - sudo sed -i \ - -e 's|http://archive.ubuntu.com/ubuntu|'"${APT_MIRROR_UBUNTU}"'|g' \ - -e 's|http://security.ubuntu.com/ubuntu|'"${APT_MIRROR_UBUNTU_SECURITY}"'|g' \ - -e 's|https://archive.ubuntu.com/ubuntu|'"${APT_MIRROR_UBUNTU}"'|g' \ - -e 's|https://security.ubuntu.com/ubuntu|'"${APT_MIRROR_UBUNTU_SECURITY}"'|g' \ - /etc/apt/sources.list - fi - if command -v apt-get >/dev/null 2>&1 && ls /etc/apt/sources.list.d/*.sources 1>/dev/null 2>&1; then - for f in /etc/apt/sources.list.d/*.sources; do + if grep -qE 'archive\.ubuntu\.com|security\.ubuntu\.com' /etc/apt/sources.list 2>/dev/null; then + APT_SOURCES_HIT=1 sudo sed -i \ -e 's|http://archive.ubuntu.com/ubuntu|'"${APT_MIRROR_UBUNTU}"'|g' \ -e 's|http://security.ubuntu.com/ubuntu|'"${APT_MIRROR_UBUNTU_SECURITY}"'|g' \ -e 's|https://archive.ubuntu.com/ubuntu|'"${APT_MIRROR_UBUNTU}"'|g' \ -e 's|https://security.ubuntu.com/ubuntu|'"${APT_MIRROR_UBUNTU_SECURITY}"'|g' \ - "${f}" 2>/dev/null || true + /etc/apt/sources.list + fi + fi + if command -v apt-get >/dev/null 2>&1 && ls /etc/apt/sources.list.d/*.sources 1>/dev/null 2>&1; then + for f in /etc/apt/sources.list.d/*.sources; do + if grep -qE 'archive\.ubuntu\.com|security\.ubuntu\.com' "${f}" 2>/dev/null; then + APT_SOURCES_HIT=1 + sudo sed -i \ + -e 's|http://archive.ubuntu.com/ubuntu|'"${APT_MIRROR_UBUNTU}"'|g' \ + -e 's|http://security.ubuntu.com/ubuntu|'"${APT_MIRROR_UBUNTU_SECURITY}"'|g' \ + -e 's|https://archive.ubuntu.com/ubuntu|'"${APT_MIRROR_UBUNTU}"'|g' \ + -e 's|https://security.ubuntu.com/ubuntu|'"${APT_MIRROR_UBUNTU_SECURITY}"'|g' \ + "${f}" 2>/dev/null || true + fi done fi + if [ "${APT_SOURCES_HIT}" = "1" ]; then + echo "[apt] 检测到官方 Ubuntu 源域名,已替换为清华镜像,下次缺包 install 会走国内源" + else + echo "[apt] 未在 sources(.list.d) 中发现官方 archive.ubuntu.com 域名,跳过镜像源替换(保留 Runner 原有配置)" + fi + sudo git config --system url."${GH_PROXY_PREFIX}https://github.com/".insteadOf "https://github.com/" || true npm config set registry https://registry.npmmirror.com >/dev/null 2>&1 || true