#!/bin/bash
set -euo pipefail
SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)"
PROJECT_ROOT="$(cd "${SCRIPT_DIR}/.." && pwd)"
BUILD_DIR="${PROJECT_ROOT}/build"
WORK_DIR="${PROJECT_ROOT}/work"
RELEASES_DIR="${PROJECT_ROOT}/releases"
VSCODIUM_REF="${VSCODIUM_REF:-master}"
APP_NAME="AbysiusCodium"
APP_NAME_SHORT="abysius-codium"
PLATFORM=""
ARCH="x64"
CLEAN=0
SKIP_EXT=0
usage() {
echo "Usage: $0 [options]"
echo " -p, --platform <platform> linux|darwin|win32"
echo " -a, --arch <arch> x64|arm64|armhf"
echo " -t, --tag <tag> VSCodium ref/tag/branch"
echo " -c, --clean Clean work directory"
echo " -s, --skip-ext Skip Abysius extension"
echo " -h, --help Show help"
exit 0
}
while [[ $# -gt 0 ]]; do
case "$1" in
-p|--platform) PLATFORM="$2"; shift 2 ;;
-a|--arch) ARCH="$2"; shift 2 ;;
-t|--tag) VSCODIUM_REF="$2"; shift 2 ;;
-c|--clean) CLEAN=1; shift ;;
-s|--skip-ext) SKIP_EXT=1; shift ;;
-h|--help) usage ;;
*) echo "Unknown option: $1"; usage ;;
esac
done
if [[ -z "$PLATFORM" ]]; then
case "$(uname -s)" in
Linux*) PLATFORM="linux" ;;
Darwin*) PLATFORM="darwin" ;;
MINGW*|MSYS*|CYGWIN*) PLATFORM="win32" ;;
*) echo "[BUILD] ERROR: Unsupported platform: $(uname -s)"; exit 1 ;;
esac
fi
# VS Code / VSCodium Windows builds are fragile in paths with spaces.
if [[ "$PROJECT_ROOT" == *" "* ]]; then
echo "[BUILD] ERROR: Project path contains spaces:"
echo " $PROJECT_ROOT"
echo ""
echo "Move/reclone this repo to a path without spaces, for example:"
echo " C:/dev/abysiuscodium"
echo ""
echo "From Git Bash:"
echo " mkdir -p /c/dev"
echo " cp -r \"$PROJECT_ROOT\" /c/dev/abysiuscodium"
echo " cd /c/dev/abysiuscodium"
echo ""
exit 1
fi
mkdir -p "${WORK_DIR}" "${RELEASES_DIR}"
if [[ $CLEAN -eq 1 ]]; then
echo "[BUILD] Cleaning work directory..."
rm -rf "${WORK_DIR:?}"/*
fi
# Enable long paths for the giant VS Code tree.
git config --global core.longpaths true || true
# Initialize fnm if available, then enforce Node 22.
if command -v fnm >/dev/null 2>&1; then
eval "$(fnm env --use-on-cd --shell bash)"
fnm use 22 >/dev/null 2>&1 || true
fi
NODE_VERSION="$(node -v 2>/dev/null || true)"
if [[ ! "$NODE_VERSION" =~ ^v22\. ]]; then
echo "[BUILD] ERROR: Node.js v22 is required."
echo "Current Node: ${NODE_VERSION:-not found}"
echo ""
echo "Fix with:"
echo ' eval "$(fnm env --use-on-cd --shell bash)"'
echo " fnm use 22"
echo ""
exit 1
fi
echo "[BUILD] Using Node: $(node -v)"
echo "[BUILD] Using npm: $(npm -v)"
ensure_jq() {
if command -v jq >/dev/null 2>&1; then
return
fi
echo "[BUILD] jq not found."
if command -v winget >/dev/null 2>&1; then
echo "[BUILD] Installing jq via winget..."
winget install --id jqlang.jq -e \
--accept-package-agreements \
--accept-source-agreements || true
hash -r || true
# winget often updates PATH but current Git Bash does not see it.
export PATH="$PATH:/c/Users/$USERNAME/AppData/Local/Microsoft/WinGet/Links"
export PATH="$PATH:/c/Program Files/jq"
if command -v jq >/dev/null 2>&1; then
echo "[BUILD] jq installed successfully."
return
fi
fi
echo "[BUILD] ERROR: jq is required."
echo "Install manually:"
echo " winget install jqlang.jq"
echo ""
echo "Then restart Git Bash."
exit 1
}
ensure_jq
VSCODIUM_DIR="${WORK_DIR}/vscodium"
echo "[BUILD] Setting up VSCodium source: ${VSCODIUM_REF}"
if [[ ! -d "${VSCODIUM_DIR}/.git" ]]; then
git clone https://github.com/VSCodium/vscodium.git "${VSCODIUM_DIR}"
fi
cd "${VSCODIUM_DIR}"
git fetch --all --tags
git checkout "${VSCODIUM_REF}"
if [[ $SKIP_EXT -eq 0 ]]; then
echo "[BUILD] Building Abysius AI extension..."
cd "${PROJECT_ROOT}/extensions/abysius-ai"
if [[ -f package-lock.json || -f npm-shrinkwrap.json ]]; then
npm ci
else
npm install
fi
npm run compile
npx vsce package --no-dependencies -o "${WORK_DIR}/abysius-ai.vsix"
echo "[BUILD] Abysius AI extension packaged:"
echo " ${WORK_DIR}/abysius-ai.vsix"
fi
if [[ $SKIP_EXT -eq 0 ]]; then
echo "[BUILD] Running license compliance check..."
cd "${PROJECT_ROOT}"
node "${BUILD_DIR}/check-licenses.js"
fi
cd "${VSCODIUM_DIR}"
echo "[BUILD] Applying Abysius branding..."
if [[ -f "${PROJECT_ROOT}/product.json" ]]; then
mkdir -p "${VSCODIUM_DIR}/custom"
cp "${PROJECT_ROOT}/product.json" "${VSCODIUM_DIR}/custom/product.json"
fi
echo "[BUILD] Running VSCodium build system for ${PLATFORM}-${ARCH}..."
export SHOULD_BUILD="yes"
export SHOULD_BUILD_REH="no"
export SHOULD_BUILD_REH_WEB="no"
export VSCODE_ARCH="${ARCH}"
export OS_NAME="${PLATFORM}"
export APP_NAME="${APP_NAME}"
export BINARY_NAME="${APP_NAME_SHORT}"
if [[ -x "./dev/build.sh" ]]; then
./dev/build.sh -o "${PLATFORM}" -a "${ARCH}"
elif [[ -x "./build.sh" ]]; then
./build.sh
else
echo "[BUILD] ERROR: Could not find VSCodium build script."
ls -la
exit 1
fi
echo "[BUILD] Collecting artifacts..."
rm -rf "${RELEASES_DIR:?}"/*
mkdir -p "${RELEASES_DIR}"
find "${VSCODIUM_DIR}" \
-type f \( \
-iname "*.exe" \
-o -iname "*.zip" \
-o -iname "*.tar.gz" \
-o -iname "*.deb" \
-o -iname "*.rpm" \
-o -iname "*.dmg" \
\) \
-not -path "*/node_modules/*" \
-not -path "*/.git/*" \
-exec cp {} "${RELEASES_DIR}/" \; 2>/dev/null || true
if [[ -f "${WORK_DIR}/abysius-ai.vsix" ]]; then
cp "${WORK_DIR}/abysius-ai.vsix" "${RELEASES_DIR}/"
fi
echo ""
echo "========================================"
echo " AbysiusCodium Build Finished"
echo "========================================"
echo ""
echo "Release artifacts available in:"
echo " ${RELEASES_DIR}/"
echo ""
ls -la "${RELEASES_DIR}/" 2>/dev/null || true
if ! find "${RELEASES_DIR}" -maxdepth 1 \
\( \
-iname "*codium*.exe" \
-o -iname "*codium*.zip" \
-o -iname "*codium*.tar.gz" \
-o -iname "*codium*.deb" \
-o -iname "*codium*.rpm" \
-o -iname "*codium*.dmg" \
-o -iname "Code.exe" \
\) | grep -q .; then
echo ""
echo "[BUILD] ERROR: No IDE artifact was found."
echo ""
echo "The extension/helper files may have built, but the actual IDE did not."
echo "Check the VSCodium build output above."
echo ""
exit 1
fi
echo ""
echo "[BUILD] Success: IDE artifact found."
echo ""