# syntax=docker/dockerfile:1

# ---------------------------------------------------------------------------
# Stage 1 — build. Dependencies are resolved in their own layer (cached until
# pom.xml changes) before the source is copied, so source-only edits rebuild fast.
# ---------------------------------------------------------------------------
FROM eclipse-temurin:21-jdk-alpine AS build
WORKDIR /workspace

# Dependency layer: only pom + wrapper, so it is cached independently of source.
COPY .mvn/ .mvn/
COPY mvnw pom.xml ./
RUN ./mvnw -B -ntp dependency:go-offline

# Source layer.
COPY config/ config/
COPY src/ src/
RUN ./mvnw -B -ntp clean package -DskipTests \
    && java -Djarmode=layertools -jar target/demo.jar extract --destination target/extracted

# ---------------------------------------------------------------------------
# Stage 2 — runtime. Small JRE image, non-root, layered-jar layout for fast
# rebuilds. curl is installed only for the container HEALTHCHECK.
# ---------------------------------------------------------------------------
FROM eclipse-temurin:21-jre-alpine AS runtime

RUN apk add --no-cache curl \
    && addgroup -S app && adduser -S -G app -H -u 10001 app

WORKDIR /app

# Ordered least- to most-frequently-changing for optimal layer caching.
COPY --from=build --chown=app:app /workspace/target/extracted/dependencies/ ./
COPY --from=build --chown=app:app /workspace/target/extracted/spring-boot-loader/ ./
COPY --from=build --chown=app:app /workspace/target/extracted/snapshot-dependencies/ ./
COPY --from=build --chown=app:app /workspace/target/extracted/application/ ./

USER app
EXPOSE 4455

# Container-aware heap sizing; fail fast on OOM instead of thrashing.
ENV JAVA_OPTS="-XX:MaxRAMPercentage=75.0 -XX:+ExitOnOutOfMemoryError"

# Scheme is overridable so prod (TLS) can point the check at https:// (Phase 7).
# curl -k tolerates the self-signed dev CA; dev uses plain http.
ENV HEALTHCHECK_URL="http://127.0.0.1:4455/actuator/health"
HEALTHCHECK --interval=30s --timeout=5s --start-period=45s --retries=3 \
    CMD curl -fsSk "${HEALTHCHECK_URL}" | grep -q '"status":"UP"' || exit 1

ENTRYPOINT ["sh", "-c", "exec java $JAVA_OPTS org.springframework.boot.loader.launch.JarLauncher"]

# OCI metadata. Values are supplied by the build (CI passes git sha + version).
ARG GIT_SHA=unknown
ARG VERSION=0.0.1-SNAPSHOT
ARG BUILD_DATE=unknown
LABEL org.opencontainers.image.title="demo" \
      org.opencontainers.image.description="Spring Boot API server (Item CRUD + auth), TLS on :4455" \
      org.opencontainers.image.version="${VERSION}" \
      org.opencontainers.image.revision="${GIT_SHA}" \
      org.opencontainers.image.created="${BUILD_DATE}" \
      org.opencontainers.image.source="https://github.com/OWNER/REPO" \
      org.opencontainers.image.licenses="Apache-2.0"
