156 lines
5.6 KiB
Bash
156 lines
5.6 KiB
Bash
#!/usr/bin/env bash
|
||
# 不通过 Docker,直接在本机启动:API(9527) + Web(9528) + Admin(9529)
|
||
# 自动检测并安装 Go、Node.js:Debian/Ubuntu 用 apt;Alibaba Cloud Linux(含等保三级版)用 yum/dnf;否则装到 $HOME。MongoDB 需自行安装或配置远程 MONGODB_URI
|
||
# 用法:chmod +x start-direct.sh && ./start-direct.sh
|
||
# 行尾:LF
|
||
set -e
|
||
ROOT="${PROJECT_ROOT:-$(cd "$(dirname "$0")" && pwd)}"
|
||
cd "$ROOT"
|
||
PIDFILE="$ROOT/.direct-run.pids"
|
||
INSTALL_ROOT="${INSTALL_ROOT:-$HOME}"
|
||
|
||
# 是否能用 apt(Debian/Ubuntu 且可 sudo)
|
||
USE_APT=false
|
||
if command -v apt-get >/dev/null 2>&1; then
|
||
if [ "$(id -u)" = 0 ] || sudo -n true 2>/dev/null; then
|
||
USE_APT=true
|
||
fi
|
||
fi
|
||
# 是否能用 yum/dnf(Alibaba Cloud Linux / CentOS / RHEL 等,含等保三级版)
|
||
USE_YUM=false
|
||
if command -v dnf >/dev/null 2>&1 || command -v yum >/dev/null 2>&1; then
|
||
if [ "$(id -u)" = 0 ] || sudo -n true 2>/dev/null; then
|
||
USE_YUM=true
|
||
fi
|
||
fi
|
||
|
||
# ---------- 自动安装 Go(未安装时)----------
|
||
if ! command -v go >/dev/null 2>&1; then
|
||
if [ "$USE_APT" = true ]; then
|
||
echo "未检测到 Go,正在通过 apt 安装..."
|
||
sudo -n apt-get update -qq
|
||
sudo -n apt-get install -y golang-go
|
||
echo "Go 已安装: $(go version)"
|
||
elif [ "$USE_YUM" = true ]; then
|
||
echo "未检测到 Go,正在通过 yum/dnf 安装(兼容等保镜像)..."
|
||
if command -v dnf >/dev/null 2>&1; then
|
||
sudo -n dnf install -y golang
|
||
else
|
||
sudo -n yum install -y golang
|
||
fi
|
||
echo "Go 已安装: $(go version)"
|
||
else
|
||
echo "未检测到 Go,正在安装到 $INSTALL_ROOT/go-install ..."
|
||
GO_VER="1.21.13"
|
||
case "$(uname -m)" in
|
||
x86_64) GO_ARCH=amd64 ;;
|
||
aarch64|arm64) GO_ARCH=arm64 ;;
|
||
*) GO_ARCH=amd64 ;;
|
||
esac
|
||
GO_TGZ="go${GO_VER}.linux-${GO_ARCH}.tar.gz"
|
||
GO_URL="https://go.dev/dl/${GO_TGZ}"
|
||
mkdir -p "$INSTALL_ROOT/go-install"
|
||
( cd "$INSTALL_ROOT" && ( curl -sL "$GO_URL" -o "$GO_TGZ" || wget -q -O "$GO_TGZ" "$GO_URL" ) && tar -xzf "$GO_TGZ" && mv go go-install && rm -f "$GO_TGZ" )
|
||
export GOROOT="$INSTALL_ROOT/go-install"
|
||
export PATH="$GOROOT/bin:$PATH"
|
||
echo "Go 已安装: $(go version)"
|
||
fi
|
||
fi
|
||
|
||
# ---------- 自动安装 Node.js(未安装时)----------
|
||
if ! command -v node >/dev/null 2>&1; then
|
||
if [ "$USE_APT" = true ]; then
|
||
echo "未检测到 Node.js,正在通过 apt + NodeSource 安装 Node 20..."
|
||
curl -fsSL https://deb.nodesource.com/setup_20.x | sudo -E bash -
|
||
sudo -n apt-get install -y nodejs
|
||
echo "Node 已安装: $(node -v)"
|
||
elif [ "$USE_YUM" = true ]; then
|
||
echo "未检测到 Node.js,正在通过 dnf/yum + NodeSource 安装 Node 20(兼容等保镜像)..."
|
||
curl -fsSL https://rpm.nodesource.com/setup_20.x | sudo bash -
|
||
if command -v dnf >/dev/null 2>&1; then
|
||
sudo -n dnf install -y nodejs
|
||
else
|
||
sudo -n yum install -y nodejs
|
||
fi
|
||
echo "Node 已安装: $(node -v)"
|
||
else
|
||
echo "未检测到 Node.js,正在通过 nvm 安装..."
|
||
export NVM_DIR="${NVM_DIR:-$HOME/.nvm}"
|
||
if [ ! -s "$NVM_DIR/nvm.sh" ]; then
|
||
mkdir -p "$NVM_DIR"
|
||
( curl -sL https://raw.githubusercontent.com/nvm-sh/nvm/v0.40.1/install.sh || wget -qO- https://raw.githubusercontent.com/nvm-sh/nvm/v0.40.1/install.sh ) | bash
|
||
fi
|
||
[ -s "$NVM_DIR/nvm.sh" ] && \. "$NVM_DIR/nvm.sh"
|
||
nvm install 20
|
||
nvm use 20
|
||
echo "Node 已安装: $(node -v)"
|
||
fi
|
||
fi
|
||
# 若已有 nvm,确保当前 shell 可用
|
||
[ -s "${NVM_DIR:-$HOME/.nvm}/nvm.sh" ] && \. "${NVM_DIR:-$HOME/.nvm}/nvm.sh" 2>/dev/null || true
|
||
|
||
[ -f server/.env ] && sed -i 's/\r$//' server/.env
|
||
[ -f server/.env ] && set -a && source server/.env && set +a
|
||
export PORT="${PORT:-9527}"
|
||
|
||
mkdir -p "$ROOT/logs"
|
||
echo "=========================================="
|
||
echo " yh_web 直接启动(无 Docker)"
|
||
echo " 路径: $ROOT"
|
||
echo " API:9527 Web:9528 Admin:9529"
|
||
echo "=========================================="
|
||
: > "$PIDFILE"
|
||
|
||
# 1) API
|
||
echo "启动 API (port $PORT)..."
|
||
cd "$ROOT/server"
|
||
go build -o yh_api . 2>/dev/null || true
|
||
nohup ./yh_api >> "$ROOT/logs/api.log" 2>&1 &
|
||
echo $! >> "$PIDFILE"
|
||
cd "$ROOT"
|
||
sleep 1
|
||
|
||
# 避免 npm/vite 在脚本里只显示不刷新的 spinner,改为逐行输出
|
||
export CI=1
|
||
export FORCE_COLOR=0
|
||
|
||
# 2) Web 前端(需先构建;在服务器上重新安装依赖以获取当前平台 rollup 等原生包)
|
||
echo "构建并启动 Web (port 9528)..."
|
||
cd "$ROOT/web"
|
||
rm -rf node_modules package-lock.json
|
||
echo " [web] npm install(约 1~3 分钟)..."
|
||
npm install
|
||
echo " [web] vite build..."
|
||
chmod -R u+x node_modules/.bin 2>/dev/null || true
|
||
npx vite build
|
||
nohup npx serve -s dist -l 9528 >> "$ROOT/logs/web.log" 2>&1 &
|
||
echo $! >> "$PIDFILE"
|
||
cd "$ROOT"
|
||
sleep 1
|
||
|
||
# 3) Admin 前端(base /admin/,需放到 /admin 路径下再 serve)
|
||
echo "构建并启动 Admin (port 9529)..."
|
||
cd "$ROOT/admin"
|
||
rm -rf node_modules package-lock.json
|
||
echo " [admin] npm install(约 1~3 分钟)..."
|
||
npm install
|
||
echo " [admin] vite build..."
|
||
chmod -R u+x node_modules/.bin 2>/dev/null || true
|
||
npx vite build
|
||
ADMIN_SERVE="$ROOT/.admin-serve"
|
||
mkdir -p "$ADMIN_SERVE/admin"
|
||
cp -r dist/* "$ADMIN_SERVE/admin/"
|
||
nohup npx serve -s "$ADMIN_SERVE" -l 9529 >> "$ROOT/logs/admin.log" 2>&1 &
|
||
echo $! >> "$PIDFILE"
|
||
cd "$ROOT"
|
||
|
||
echo ""
|
||
echo "已启动。PID 见 $PIDFILE"
|
||
echo "停止:xargs -a $PIDFILE kill 2>/dev/null"
|
||
echo ""
|
||
echo "检查是否成功:"
|
||
echo " 端口:ss -tlnp | grep -E '9527|9528|9529'"
|
||
echo " 请求:curl -s -o /dev/null -w '%{http_code}' http://127.0.0.1:9527/api/web/info (期望 200)"
|
||
echo " 日志:tail -5 $ROOT/logs/api.log $ROOT/logs/web.log $ROOT/logs/admin.log"
|
||
echo "完成. api:9527 web:9528 admin:9529"
|