114 lines
3.5 KiB
Bash
Executable File
114 lines
3.5 KiB
Bash
Executable File
#!/bin/bash
|
|
set -euo pipefail
|
|
|
|
PROJECT="lobe-sandbox"
|
|
PROFILE="sandbox-default"
|
|
BUILDER="sb-builder"
|
|
IMAGE_ALIAS="lobe-sandbox-base"
|
|
BASE="images:debian/13"
|
|
|
|
log() { echo "==> [$(date +%H:%M:%S)] $*"; }
|
|
|
|
if incus info "$BUILDER" --project "$PROJECT" >/dev/null 2>&1; then
|
|
log "Removing existing builder"
|
|
incus delete "$BUILDER" --project "$PROJECT" --force
|
|
fi
|
|
|
|
log "Launching builder from $BASE (4GB/4CPU for fast build)"
|
|
incus launch "$BASE" "$BUILDER" --project "$PROJECT" -p "$PROFILE" \
|
|
-c limits.memory=4GiB -c limits.cpu=4
|
|
|
|
log "Waiting for network"
|
|
for i in {1..60}; do
|
|
if incus exec "$BUILDER" --project "$PROJECT" -- bash -c "getent hosts deb.debian.org >/dev/null 2>&1"; then
|
|
log "Network ready after ${i}s"; break
|
|
fi
|
|
sleep 1
|
|
done
|
|
|
|
log "Installing apt packages"
|
|
incus exec "$BUILDER" --project "$PROJECT" -- bash -c '
|
|
set -e
|
|
export DEBIAN_FRONTEND=noninteractive
|
|
apt-get update
|
|
apt-get install -y --no-install-recommends \
|
|
python3 python3-dev python3-venv python3-pip \
|
|
ca-certificates curl wget git gnupg build-essential pkg-config \
|
|
jq ripgrep fd-find bat fonts-noto-cjk \
|
|
less tree unzip zip xz-utils sudo locales tzdata
|
|
ln -sf /usr/bin/fdfind /usr/local/bin/fd
|
|
ln -sf /usr/bin/batcat /usr/local/bin/bat
|
|
sed -i "/zh_CN.UTF-8/s/^# //;/en_US.UTF-8/s/^# //" /etc/locale.gen
|
|
locale-gen
|
|
ln -sf /usr/share/zoneinfo/Asia/Shanghai /etc/localtime
|
|
'
|
|
|
|
log "Installing Node.js 20 via NodeSource"
|
|
incus exec "$BUILDER" --project "$PROJECT" -- bash -c '
|
|
set -e
|
|
export DEBIAN_FRONTEND=noninteractive
|
|
curl -fsSL https://deb.nodesource.com/setup_20.x | bash -
|
|
apt-get install -y --no-install-recommends nodejs
|
|
corepack enable
|
|
'
|
|
|
|
log "Installing uv"
|
|
incus exec "$BUILDER" --project "$PROJECT" -- bash -c '
|
|
curl -LsSf https://astral.sh/uv/install.sh | sh -s -- --no-modify-path --install-dir /usr/local/bin
|
|
ls -la /usr/local/bin/uv /usr/local/bin/uvx
|
|
'
|
|
|
|
log "Installing bun"
|
|
incus exec "$BUILDER" --project "$PROJECT" -- bash -c '
|
|
curl -fsSL https://bun.sh/install | env BUN_INSTALL=/usr/local bash
|
|
ls -la /usr/local/bin/bun
|
|
'
|
|
|
|
log "Creating sandbox user and /workspace"
|
|
incus exec "$BUILDER" --project "$PROJECT" -- bash -c '
|
|
set -e
|
|
useradd --create-home --shell /bin/bash --uid 1000 sandbox
|
|
mkdir -p /workspace/data /workspace/output /workspace/tmp
|
|
chown -R sandbox:sandbox /workspace /home/sandbox
|
|
printf "cd /workspace\nexport LANG=zh_CN.UTF-8\n" >> /home/sandbox/.bashrc
|
|
'
|
|
|
|
log "Cleaning apt cache"
|
|
incus exec "$BUILDER" --project "$PROJECT" -- bash -c '
|
|
apt-get clean
|
|
rm -rf /var/lib/apt/lists/* /tmp/* /var/tmp/*
|
|
'
|
|
|
|
log "Verifying versions"
|
|
incus exec "$BUILDER" --project "$PROJECT" -- bash -c '
|
|
echo "python : $(python3 --version)"
|
|
echo "node : $(node --version)"
|
|
echo "bun : $(bun --version)"
|
|
echo "uv : $(uv --version)"
|
|
echo "git : $(git --version)"
|
|
echo "rg : $(rg --version | head -1)"
|
|
echo "fd : $(fd --version)"
|
|
echo "user : $(id sandbox)"
|
|
echo "space : $(du -sh /workspace)"
|
|
echo "rootfs : $(du -sh --one-file-system / 2>/dev/null | tail -1)"
|
|
'
|
|
|
|
log "Stopping builder"
|
|
incus stop "$BUILDER" --project "$PROJECT"
|
|
|
|
if incus image alias list --project "$PROJECT" | grep -q "$IMAGE_ALIAS"; then
|
|
log "Deleting old $IMAGE_ALIAS image"
|
|
incus image delete "$IMAGE_ALIAS" --project "$PROJECT"
|
|
fi
|
|
|
|
log "Publishing as $IMAGE_ALIAS"
|
|
incus publish "$BUILDER" --project "$PROJECT" --alias "$IMAGE_ALIAS"
|
|
|
|
log "Deleting builder"
|
|
incus delete "$BUILDER" --project "$PROJECT"
|
|
|
|
log "Image info"
|
|
incus image list --project "$PROJECT"
|
|
|
|
log "DONE"
|