163 lines
5.1 KiB
Bash
Executable File
163 lines
5.1 KiB
Bash
Executable File
#!/usr/bin/env bash
|
||
# 构建 Docker 镜像脚本
|
||
# 用法: ./build-docker.sh [amd64|arm64]
|
||
# 如果不指定架构,将使用本机架构
|
||
|
||
set -euo pipefail
|
||
|
||
# 颜色输出
|
||
RED='\033[0;31m'
|
||
GREEN='\033[0;32m'
|
||
YELLOW='\033[1;33m'
|
||
NC='\033[0m' # No Color
|
||
|
||
echo -e "${GREEN}=== 开始构建 PeiPei 后端 Docker 镜像 ===${NC}"
|
||
|
||
# 检测本机架构
|
||
NATIVE_ARCH=$(uname -m)
|
||
if [[ "$NATIVE_ARCH" == "x86_64" ]]; then
|
||
NATIVE_ARCH="amd64"
|
||
elif [[ "$NATIVE_ARCH" == "arm64" ]] || [[ "$NATIVE_ARCH" == "aarch64" ]]; then
|
||
NATIVE_ARCH="arm64"
|
||
fi
|
||
|
||
# 处理命令行参数(兼容未提供参数时的 set -u)
|
||
ARG1="${1-}"
|
||
if [[ "$ARG1" == "-h" || "$ARG1" == "--help" ]]; then
|
||
echo -e "${GREEN}PeiPei 后端 Docker 镜像构建脚本${NC}"
|
||
echo ""
|
||
echo -e "${YELLOW}用法:${NC}"
|
||
echo " ./build-docker.sh [选项] [架构]"
|
||
echo ""
|
||
echo -e "${YELLOW}选项:${NC}"
|
||
echo " -h, --help 显示此帮助信息"
|
||
echo ""
|
||
echo -e "${YELLOW}架构:${NC}"
|
||
echo " amd64 构建 Linux amd64 镜像 (适用于服务器)"
|
||
echo " arm64 构建 Linux arm64 镜像 (适用于 Apple Silicon Mac)"
|
||
echo " [空] 自动检测本机架构"
|
||
echo ""
|
||
echo -e "${YELLOW}示例:${NC}"
|
||
echo " ./build-docker.sh # 自动检测架构构建"
|
||
echo " ./build-docker.sh amd64 # 构建服务器镜像"
|
||
echo " ./build-docker.sh arm64 # 构建 Mac 镜像"
|
||
echo " ./build-docker.sh -h # 显示帮助"
|
||
echo ""
|
||
echo -e "${YELLOW}说明:${NC}"
|
||
echo " - 本机架构: ${NATIVE_ARCH}"
|
||
echo " - 使用 Docker Buildx 进行构建"
|
||
echo " - 镜像将带有架构后缀标签 (如: latest-amd64)"
|
||
echo " - 构建缓存存储在: .buildx-cache/"
|
||
echo " - 确保 Dockerfile 使用: FROM --platform=\$TARGETPLATFORM"
|
||
exit 0
|
||
fi
|
||
|
||
TARGET_ARCH="${ARG1:-$NATIVE_ARCH}"
|
||
|
||
# 验证架构参数
|
||
if [[ "$TARGET_ARCH" != "amd64" && "$TARGET_ARCH" != "arm64" ]]; then
|
||
echo -e "${RED}错误: 不支持的架构 '$TARGET_ARCH'${NC}"
|
||
echo -e "${YELLOW}支持的架构: amd64, arm64${NC}"
|
||
echo -e "${YELLOW}用法: ./build-docker.sh [amd64|arm64]${NC}"
|
||
exit 1
|
||
fi
|
||
|
||
echo -e "${YELLOW}目标架构: ${TARGET_ARCH}${NC}"
|
||
echo -e "${YELLOW}本机架构: ${NATIVE_ARCH}${NC}"
|
||
|
||
# 检查是否在正确的目录
|
||
if [ ! -f "docker/Dockerfile" ]; then
|
||
echo -e "${RED}错误: 请在项目根目录执行此脚本${NC}"
|
||
echo -e "${YELLOW}当前目录: $(pwd)${NC}"
|
||
echo -e "${YELLOW}期望目录应包含: docker/Dockerfile${NC}"
|
||
exit 1
|
||
fi
|
||
|
||
# 获取 UTC+8 时间戳
|
||
TIMESTAMP=$(TZ='Asia/Shanghai' date +"%Y-%m-%d-%Hh-%Mm")
|
||
echo -e "${YELLOW}构建时间戳 (UTC+8): ${TIMESTAMP}${NC}"
|
||
|
||
# 镜像名称和标签
|
||
IMAGE_NAME="peipei-backend"
|
||
VERSION_TAG="${TIMESTAMP}-${TARGET_ARCH}"
|
||
LATEST_TAG="latest-${TARGET_ARCH}"
|
||
|
||
echo -e "${YELLOW}镜像名称: ${IMAGE_NAME}${NC}"
|
||
echo -e "${YELLOW}版本标签: ${VERSION_TAG}${NC}"
|
||
|
||
# 构建 Docker 镜像
|
||
echo -e "${GREEN}开始构建镜像...${NC}"
|
||
|
||
# 确保 buildx 可用
|
||
if ! docker buildx version >/dev/null 2>&1; then
|
||
echo -e "${RED}错误: 需要 Docker Buildx 支持${NC}"
|
||
exit 1
|
||
fi
|
||
|
||
# 创建并使用 builder(如果不存在)
|
||
if ! docker buildx inspect peipei-builder >/dev/null 2>&1; then
|
||
echo -e "${YELLOW}创建 buildx builder...${NC}"
|
||
docker buildx create --name peipei-builder --use
|
||
else
|
||
docker buildx use peipei-builder
|
||
fi
|
||
|
||
# 启动 builder 和 QEMU(用于跨架构支持)
|
||
echo -e "${YELLOW}初始化 buildx builder...${NC}"
|
||
docker buildx inspect --bootstrap >/dev/null
|
||
|
||
# 显示构建类型
|
||
if [[ "$TARGET_ARCH" != "$NATIVE_ARCH" ]]; then
|
||
echo -e "${YELLOW}跨平台构建: ${NATIVE_ARCH} -> ${TARGET_ARCH}${NC}"
|
||
else
|
||
echo -e "${YELLOW}本机架构构建: ${TARGET_ARCH}${NC}"
|
||
fi
|
||
|
||
# 创建缓存目录(可选优化)
|
||
CACHE_DIR=".buildx-cache"
|
||
mkdir -p "$CACHE_DIR"
|
||
|
||
# 始终使用 buildx 以保持行为一致
|
||
echo -e "${GREEN}执行构建...${NC}"
|
||
if docker buildx build \
|
||
--platform "linux/${TARGET_ARCH}" \
|
||
--load \
|
||
--cache-from="type=local,src=${CACHE_DIR}" \
|
||
--cache-to="type=local,dest=${CACHE_DIR}" \
|
||
-f docker/Dockerfile \
|
||
-t "${IMAGE_NAME}:${VERSION_TAG}" \
|
||
-t "${IMAGE_NAME}:${LATEST_TAG}" \
|
||
.; then
|
||
BUILD_SUCCESS=true
|
||
else
|
||
BUILD_SUCCESS=false
|
||
fi
|
||
|
||
# 检查构建结果
|
||
if [[ "$BUILD_SUCCESS" == "true" ]]; then
|
||
echo -e "${GREEN}✅ Docker 镜像构建成功!${NC}"
|
||
echo -e "${GREEN}镜像标签:${NC}"
|
||
echo -e " - ${IMAGE_NAME}:${VERSION_TAG}"
|
||
echo -e " - ${IMAGE_NAME}:${LATEST_TAG}"
|
||
|
||
echo -e "\n${YELLOW}镜像信息:${NC}"
|
||
docker images | grep -E "^${IMAGE_NAME}\s"
|
||
|
||
echo -e "\n${GREEN}使用说明:${NC}"
|
||
if [[ "$TARGET_ARCH" == "amd64" ]]; then
|
||
echo -e " - 该镜像适用于 Linux amd64 服务器部署"
|
||
echo -e " - 推送到服务器: ./push-docker.sh"
|
||
elif [[ "$TARGET_ARCH" == "arm64" ]]; then
|
||
echo -e " - 该镜像适用于 Apple Silicon Mac 本地运行"
|
||
echo -e " - 本地测试: docker run ${IMAGE_NAME}:${LATEST_TAG}"
|
||
fi
|
||
|
||
echo -e "\n${YELLOW}构建其他架构:${NC}"
|
||
echo -e " - 构建 amd64 (服务器): ./build-docker.sh amd64"
|
||
echo -e " - 构建 arm64 (Mac): ./build-docker.sh arm64"
|
||
echo -e " - 自动检测架构: ./build-docker.sh"
|
||
else
|
||
echo -e "${RED}❌ Docker 镜像构建失败!${NC}"
|
||
exit 1
|
||
fi
|