# syntax=docker/dockerfile:1.6
#
# Multi-stage, multi-arch build for vpp-maglev container images.
#
# Produces two runtime images from a single Alpine-based builder:
#   --target maglevd   -> git.ipng.ch/ipng/vpp-maglevd:latest
#   --target frontend  -> git.ipng.ch/ipng/vpp-maglevd-frontend:latest
#
# The builder stage runs on the host's native arch ($BUILDPLATFORM) and
# Go cross-compiles to the image's target arch ($TARGETARCH), so a
# single `docker buildx build --platform linux/amd64,linux/arm64`
# produces a proper multi-arch manifest without a qemu-emulated
# builder. Both BUILDPLATFORM and TARGETARCH are populated
# automatically by buildx.
#
# Both images are driven by docker-compose.yaml at the repo root; see
# README.md and .env.example.

# =============================================================================
# Builder — compiles all four binaries against golang:alpine.
# =============================================================================
FROM --platform=$BUILDPLATFORM golang:1.25-alpine AS builder

# TARGETARCH is supplied by buildx (amd64, arm64, ...). Declared here
# so the make invocation below can reference it.
ARG TARGETARCH

# make drives the Go build; nodejs/npm are needed for the SolidJS SPA
# that maglevd-frontend embeds at link time via //go:embed; git is used
# by the Makefile's `git rev-parse --short HEAD` to stamp the commit
# hash into the binary via -ldflags, and golang:alpine doesn't ship it.
RUN apk add --no-cache make nodejs npm git

WORKDIR /src

# Cache Go modules first so code-only rebuilds skip the download.
COPY go.mod go.sum ./
RUN go mod download

COPY . .

# The protoc-generated files are checked in, but docker COPY resets
# their mtimes so make may think they need regenerating. Touch them
# to ensure they are newer than the proto file and skip the rule.
RUN touch internal/grpcapi/maglev.pb.go internal/grpcapi/maglev_grpc.pb.go

# build-amd64 / build-arm64 both set GOOS=linux GOARCH=<arch> and emit
# into build/<arch>/, so the runtime stages below can COPY straight
# out of build/$TARGETARCH/. CGO_ENABLED=0 is exported by the Makefile.
RUN make build-$TARGETARCH

# =============================================================================
# Runtime: maglevd (health-checker daemon)
# =============================================================================
FROM alpine:3 AS maglevd
ARG TARGETARCH

# ca-certificates — HTTPS health checks need a trust store.
# iproute2       — `ip netns` helpers, useful for debugging netns-scoped probes.
RUN apk add --no-cache ca-certificates iproute2

COPY --from=builder /src/build/$TARGETARCH/maglevd /usr/sbin/maglevd

# gRPC control plane (9090) and Prometheus /metrics (9091). The actual
# listen addresses are set by MAGLEV_GRPC_ADDR / MAGLEV_METRICS_ADDR.
EXPOSE 9090 9091

ENTRYPOINT ["/usr/sbin/maglevd"]

# =============================================================================
# Runtime: maglevd-frontend (read-only dashboard + optional /admin/)
# =============================================================================
FROM alpine:3 AS frontend
ARG TARGETARCH

RUN apk add --no-cache ca-certificates

COPY --from=builder /src/build/$TARGETARCH/maglevd-frontend /usr/sbin/maglevd-frontend

EXPOSE 8080

ENTRYPOINT ["/usr/sbin/maglevd-frontend"]
