# ---- Stage 0: Compile lcgamboa QEMU as Linux .so (full ESP32 GPIO emulation) ----
FROM ubuntu:22.04 AS qemu-builder

RUN apt-get update && apt-get install -y --no-install-recommends \
    git python3 python3-pip python3-setuptools \
    ninja-build pkg-config flex bison \
    gcc g++ make ca-certificates \
    libglib2.0-dev libgcrypt20-dev libslirp-dev \
    libpixman-1-dev libfdt-dev \
    && rm -rf /var/lib/apt/lists/*

# QEMU 8.x requires meson >= 1.0
RUN pip3 install meson

# Clone lcgamboa fork (picsimlab-esp32 branch adds GPIO/ADC/UART/RMT C callback API)
RUN git clone --depth=1 --branch picsimlab-esp32 \
    https://github.com/lcgamboa/qemu /qemu-lcgamboa

WORKDIR /qemu-lcgamboa

# Build libqemu-xtensa.so (ESP32/S3) and libqemu-riscv32.so (ESP32-C3).
# The script: configures with --extra-cflags=-fPIC, builds normally, then
# re-links without softmmu_main.c.o and with -shared.
RUN bash build_libqemu-esp32.sh


# ---- Stage 1: Build frontend and wokwi-libs ----
FROM node:20 AS frontend-builder

WORKDIR /app

# Clone wokwi-libs fresh from upstream to avoid stale submodule pointers.
# git is pre-installed in the node:20 Debian image.
RUN git clone --depth=1 https://github.com/wokwi/avr8js.git wokwi-libs/avr8js \
 && git clone --depth=1 https://github.com/wokwi/rp2040js.git wokwi-libs/rp2040js \
 && git clone --depth=1 https://github.com/wokwi/wokwi-elements.git wokwi-libs/wokwi-elements \
 && git clone --depth=1 https://github.com/wokwi/wokwi-boards.git wokwi-libs/wokwi-boards

# Build avr8js
WORKDIR /app/wokwi-libs/avr8js
RUN npm install && npm run build --if-present

# Build rp2040js (may have no build script on some commits)
WORKDIR /app/wokwi-libs/rp2040js
RUN npm install && npm run build --if-present

# Build wokwi-elements
WORKDIR /app/wokwi-libs/wokwi-elements
RUN npm install && npm run build --if-present

# Build frontend
# components-metadata.json is already committed; skip generate:metadata
# (it requires wokwi-elements/src which isn't needed at runtime)
WORKDIR /app
COPY frontend/ frontend/
WORKDIR /app/frontend
RUN npm install && npm run build:docker


# ---- Stage 2: Final Production Image ----
FROM python:3.12-slim

# Install system dependencies, nginx, and QEMU .so runtime libraries
RUN apt-get update && apt-get install -y --no-install-recommends \
    curl \
    ca-certificates \
    nginx \
    libglib2.0-0 \
    libgcrypt20 \
    libslirp0 \
    libpixman-1-0 \
    libfdt1 \
    && apt-get clean \
    && rm -rf /var/lib/apt/lists/*

# Install arduino-cli into /usr/local/bin directly (avoids touching /bin)
RUN curl -fsSL https://raw.githubusercontent.com/arduino/arduino-cli/master/install.sh \
    | BINDIR=/usr/local/bin sh

# Only install arduino-cli binary here. Core installation (arduino:avr,
# rp2040:rp2040, esp32:esp32) is done at first boot by entrypoint.sh
# and persisted in the mounted /root/.arduino15 volume.
# This keeps the image small (~500MB vs ~2.5GB) and builds fast.

WORKDIR /app

# Data directory for persistent SQLite database (mounted as a volume at runtime)
RUN mkdir -p /app/data

# Install Python backend dependencies
COPY backend/requirements.txt .
RUN pip install --no-cache-dir -r requirements.txt

# Copy backend application code
COPY backend/app/ ./app/

# Setup Nginx configuration
COPY deploy/nginx.conf /etc/nginx/conf.d/default.conf

# Copy built frontend assets from builder stage
COPY --from=frontend-builder /app/frontend/dist /usr/share/nginx/html

# Copy and configure entrypoint script
COPY deploy/entrypoint.sh /app/entrypoint.sh
RUN chmod +x /app/entrypoint.sh

# ── ESP32 emulation: lcgamboa QEMU .so + ROM binaries ────────────────────────
# libqemu-xtensa.so    → ESP32 / ESP32-S3 (Xtensa LX6/LX7)
# libqemu-riscv32.so   → ESP32-C3 (RISC-V RV32IMC)
# esp32-v3-rom*.bin    → boot/app ROM images required by esp32-picsimlab machine
# esp32c3-rom.bin      → ROM image required by esp32c3-picsimlab machine
# NOTE: ROM files must live in the same directory as the .so (worker passes -L
#       to QEMU pointing at os.path.dirname(lib_path))
RUN mkdir -p /app/lib
COPY --from=qemu-builder /qemu-lcgamboa/build/libqemu-xtensa.so /app/lib/
COPY --from=qemu-builder /qemu-lcgamboa/build/libqemu-riscv32.so /app/lib/
COPY --from=qemu-builder /qemu-lcgamboa/pc-bios/esp32-v3-rom.bin /app/lib/
COPY --from=qemu-builder /qemu-lcgamboa/pc-bios/esp32-v3-rom-app.bin /app/lib/
COPY --from=qemu-builder /qemu-lcgamboa/pc-bios/esp32c3-rom.bin /app/lib/

# Activate ESP32 emulation
# QEMU_ESP32_LIB    → Xtensa library (ESP32, ESP32-S3)
# QEMU_RISCV32_LIB  → RISC-V library (ESP32-C3 and variants)
ENV QEMU_ESP32_LIB=/app/lib/libqemu-xtensa.so
ENV QEMU_RISCV32_LIB=/app/lib/libqemu-riscv32.so

EXPOSE 80

CMD ["/app/entrypoint.sh"]
