#!/bin/bash

# Build fully static MUSL binary for nsigner using Alpine Docker

set -euo pipefail

SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)"
BUILD_DIR="$SCRIPT_DIR/build"
DOCKERFILE="$SCRIPT_DIR/Dockerfile.alpine-musl"

TARGET_ARCH=""

while [[ $# -gt 0 ]]; do
    case "$1" in
        --arch)
            if [[ -z "${2:-}" ]]; then
                echo "ERROR: --arch requires a value"
                echo "Usage: $0 [--arch <x86_64|arm64|armv7>]"
                exit 1
            fi
            case "$2" in
                x86_64|arm64|armv7)
                    TARGET_ARCH="$2"
                    ;;
                *)
                    echo "ERROR: Unsupported architecture '$2'"
                    echo "Supported values: x86_64, arm64, armv7"
                    exit 1
                    ;;
            esac
            shift 2
            ;;
        *)
            echo "ERROR: Unknown argument '$1'"
            echo "Usage: $0 [--arch <x86_64|arm64|armv7>]"
            exit 1
            ;;
    esac
done

if ! command -v docker >/dev/null 2>&1; then
    echo "ERROR: Docker is not installed or not in PATH"
    exit 1
fi

if ! docker info >/dev/null 2>&1; then
    echo "ERROR: Docker daemon is not running or user lacks permissions"
    exit 1
fi

HOST_UNAME="$(uname -m)"
case "$HOST_UNAME" in
    x86_64)
        HOST_ARCH="x86_64"
        ;;
    aarch64|arm64)
        HOST_ARCH="arm64"
        ;;
    armv7l|armv7)
        HOST_ARCH="armv7"
        ;;
    *)
        HOST_ARCH="x86_64"
        ;;
esac

ARCH="${TARGET_ARCH:-$HOST_ARCH}"

case "$ARCH" in
    x86_64)
        PLATFORM="linux/amd64"
        OUTPUT_NAME="nsigner_static_x86_64"
        ;;
    arm64)
        PLATFORM="linux/arm64"
        OUTPUT_NAME="nsigner_static_arm64"
        ;;
    armv7)
        PLATFORM="linux/arm/v7"
        OUTPUT_NAME="nsigner_static_armv7"
        ;;
    *)
        echo "ERROR: Unsupported target architecture '$ARCH'"
        exit 1
        ;;
esac

mkdir -p "$BUILD_DIR"

IMAGE_TAG="nsigner-static-builder:${ARCH}"
CONTAINER_NAME=""
cleanup() {
    if [[ -n "$CONTAINER_NAME" ]]; then
        docker rm -f "$CONTAINER_NAME" >/dev/null 2>&1 || true
    fi
}
trap cleanup EXIT

echo "=========================================="
echo "nsigner static build"
echo "=========================================="
echo "Project root: $SCRIPT_DIR"
echo "Dockerfile:   $DOCKERFILE"
echo "Platform:     $PLATFORM"
echo "Output:       $BUILD_DIR/$OUTPUT_NAME"
echo ""

if [ "$ARCH" != "$HOST_ARCH" ]; then
    echo "[0/3] Preparing buildx + QEMU for cross-architecture build"
    if ! docker buildx inspect >/dev/null 2>&1; then
        echo "ERROR: docker buildx is not available"
        exit 1
    fi
    docker run --privileged --rm tonistiigi/binfmt --install all >/dev/null

    if ! docker buildx inspect nsigner-builder >/dev/null 2>&1; then
        docker buildx create --name nsigner-builder --driver docker-container --use >/dev/null
    else
        docker buildx use nsigner-builder >/dev/null
    fi
    docker buildx inspect --bootstrap >/dev/null
fi

echo "[1/3] Building builder stage from project root context"
docker buildx build \
    --platform "$PLATFORM" \
    --target builder \
    -f "$DOCKERFILE" \
    -t "$IMAGE_TAG" \
    --load \
    "$SCRIPT_DIR"

echo "[2/3] Extracting static binary"
CONTAINER_NAME="$(docker create "$IMAGE_TAG")"
docker cp "$CONTAINER_NAME:/build/nsigner_static" "$BUILD_DIR/$OUTPUT_NAME"
chmod +x "$BUILD_DIR/$OUTPUT_NAME"
strip "$BUILD_DIR/$OUTPUT_NAME" >/dev/null 2>&1 || true

echo "[3/3] Verifying static binary"
file "$BUILD_DIR/$OUTPUT_NAME"

LDD_OUTPUT="$(ldd "$BUILD_DIR/$OUTPUT_NAME" 2>&1 || true)"
echo "$LDD_OUTPUT"
if echo "$LDD_OUTPUT" | grep -Eq "not a dynamic executable|statically linked"; then
    echo "Static check: PASS"
else
    echo "Static check: WARNING (verify manually)"
fi

echo ""
echo "Build complete: $BUILD_DIR/$OUTPUT_NAME"
