# =============================================================================
# Zonemaster Backend — multi-stage build from source
# Chain: LDNS → Engine → CLI → Backend
# =============================================================================

# ── Stage 1: Build LDNS ──────────────────────────────────────────────────────
FROM alpine:3.22 AS ldns-build

RUN apk add --no-cache \
    autoconf \
    automake \
    build-base \
    libidn2-dev \
    libtool \
    make \
    openssl-dev \
    perl-app-cpanminus \
    perl-dev \
    perl-devel-checklib \
    perl-extutils-depends \
    perl-extutils-pkgconfig \
    perl-lwp-protocol-https \
    perl-mime-base32 \
    perl-module-install \
    perl-test-differences \
    perl-test-fatal \
    perl-test-nowarnings \
 && cpanm --notest --no-wget --from=https://cpan.metacpan.org/ \
    Module::Install::XSUtil

COPY zonemaster-ldns/ /src/ldns/
RUN cpanm --notest --no-wget /src/ldns/

# ── Stage 2: LDNS runtime base ────────────────────────────────────────────────
FROM alpine:3.22 AS ldns

COPY --from=ldns-build \
    /usr/local/lib/perl5/site_perl/auto/Zonemaster \
    /usr/local/lib/perl5/site_perl/auto/Zonemaster
COPY --from=ldns-build \
    /usr/local/lib/perl5/site_perl/Zonemaster \
    /usr/local/lib/perl5/site_perl/Zonemaster

RUN apk add --no-cache libidn2 perl

# ── Stage 3: Build Engine ─────────────────────────────────────────────────────
FROM ldns AS engine-build

RUN apk add --no-cache \
    gcc \
    gettext \
    make \
    musl-dev \
    perl-dev \
    perl-app-cpanminus \
    perl-mailtools \
    perl-module-build-tiny \
    perl-class-accessor \
    perl-clone \
    perl-file-sharedir \
    perl-file-slurp \
    perl-io-socket-inet6 \
    perl-list-moreutils \
    perl-locale-msgfmt \
    perl-log-any \
    perl-lwp-protocol-https \
    perl-mail-spf \
    perl-module-install \
    perl-pod-coverage \
    perl-readonly \
    perl-sub-override \
    perl-test-differences \
    perl-test-exception \
    perl-test-fatal \
    perl-test-nowarnings \
    perl-test-pod \
    perl-text-csv \
    perl-yaml \
    perl-yaml-libyaml \
 && cpanm --no-wget --from=https://cpan.metacpan.org/ \
    Email::Valid \
    List::Compare \
    Locale::PO \
    Locale::TextDomain \
    Module::Find \
    Net::DNS \
    Net::IP::XS

COPY zonemaster-engine/ /src/engine/
RUN cpanm --notest --no-wget /src/engine/

# ── Stage 4: Engine runtime base ─────────────────────────────────────────────
FROM ldns AS engine

COPY --from=engine-build /usr/local/lib/perl5/site_perl /usr/local/lib/perl5/site_perl
COPY --from=engine-build /usr/local/share/perl5/site_perl /usr/local/share/perl5/site_perl

RUN apk add --no-cache \
    musl-locales \
    perl-class-accessor \
    perl-clone \
    perl-file-sharedir \
    perl-file-slurp \
    perl-io-socket-inet6 \
    perl-list-moreutils \
    perl-locale-msgfmt \
    perl-log-any \
    perl-mail-spf \
    perl-mailtools \
    perl-module-install \
    perl-net-ip \
    perl-readonly \
    perl-text-csv \
    perl-try-tiny \
    perl-yaml-libyaml

# ── Stage 5: Build CLI ────────────────────────────────────────────────────────
FROM engine AS cli-build

RUN apk add --no-cache \
    gettext \
    make \
    perl-app-cpanminus \
    perl-json-xs \
    perl-lwp-protocol-https \
    perl-mojolicious \
    perl-test-deep \
    perl-test-differences \
    perl-try-tiny \
 && cpanm --notest --no-wget --from=https://cpan.metacpan.org/ \
    JSON::Validator

COPY zonemaster-cli/ /src/cli/
RUN cpanm --notest --no-wget /src/cli/

# ── Stage 6: CLI runtime base ─────────────────────────────────────────────────
FROM engine AS cli

RUN apk add --no-cache perl-json-xs perl-try-tiny

COPY --from=cli-build /usr/local/bin/zonemaster-cli /usr/local/bin/zonemaster-cli
COPY --from=cli-build /usr/local/lib/perl5/site_perl /usr/local/lib/perl5/site_perl
COPY --from=cli-build /usr/local/share/perl5/site_perl /usr/local/share/perl5/site_perl

# ── Stage 7: Build Backend ────────────────────────────────────────────────────
FROM cli AS backend-build

RUN apk add --no-cache \
    make \
    curl \
    gcc \
    perl-dev \
    musl-dev \
    perl-app-cpanminus \
    jq \
    perl-class-method-modifiers \
    perl-config-inifiles \
    perl-dbd-sqlite \
    perl-dbi \
    perl-file-share \
    perl-file-slurp \
    perl-html-parser \
    perl-http-parser-xs \
    perl-mojolicious \
    perl-io-stringy \
    perl-log-any \
    perl-log-dispatch \
    perl-moose \
    perl-parallel-forkmanager \
    perl-plack \
    perl-role-tiny \
    perl-test-nowarnings \
    perl-test-differences \
    perl-test-exception \
    perl-try-tiny \
    perl-doc \
 && cpanm --notest --no-wget --from=https://cpan.metacpan.org/ \
    Net::Statsd

COPY zonemaster-backend/ /src/backend/
RUN cpanm --notest --no-wget /src/backend/

# ── Stage 8: Backend runtime (final image) ────────────────────────────────────
FROM cli AS backend

RUN apk add --no-cache \
    jq \
    perl-config-inifiles \
    perl-mojolicious \
    perl-moose \
    perl-dbi \
    perl-dbd-sqlite \
    perl-plack \
    perl-parallel-forkmanager

COPY --from=backend-build /usr/local/share/perl5 /usr/local/share/perl5
COPY --from=backend-build /usr/local/bin/ /usr/local/bin/
COPY --from=backend-build /usr/lib/perl5 /usr/lib/perl5

RUN addgroup -S zonemaster \
 && adduser -S zonemaster -G zonemaster

RUN SHARE=$(perl -MFile::ShareDir=dist_dir -E 'say dist_dir("Zonemaster-Backend")') \
 && install -v -m 755 -d /etc/zonemaster \
 && install -v -m 775 -g zonemaster -d /var/log/zonemaster \
 && install -v -m 640 -g zonemaster "$SHARE/backend_config.ini" /etc/zonemaster/

RUN install -v -m 755 -o zonemaster -g zonemaster -d /var/lib/zonemaster
USER zonemaster
RUN "$(perl -MFile::ShareDir -le 'print File::ShareDir::dist_dir("Zonemaster-Backend")')/create_db.pl"

USER root

# Install s6-overlay for process supervision (rpcapi + testagent)
ARG S6_OVERLAY_VERSION=3.2.1.0
ADD https://github.com/just-containers/s6-overlay/releases/download/v${S6_OVERLAY_VERSION}/s6-overlay-noarch.tar.xz /tmp
RUN tar -C / -Jxpf /tmp/s6-overlay-noarch.tar.xz
ADD https://github.com/just-containers/s6-overlay/releases/download/v${S6_OVERLAY_VERSION}/s6-overlay-x86_64.tar.xz /tmp
RUN tar -C / -Jxpf /tmp/s6-overlay-x86_64.tar.xz

COPY zonemaster-backend/zonemaster_launch /usr/local/bin/zonemaster_launch
RUN chmod +x /usr/local/bin/zonemaster_launch

# Register rpcapi service (JSON-RPC API on :5000)
RUN mkdir -p /etc/s6-overlay/s6-rc.d/rpcapi \
 && echo "longrun" > /etc/s6-overlay/s6-rc.d/rpcapi/type \
 && printf '#!/command/with-contenv sh\nexec zonemaster_launch rpcapi\n' \
    > /etc/s6-overlay/s6-rc.d/rpcapi/run \
 && chmod +x /etc/s6-overlay/s6-rc.d/rpcapi/run \
 && touch /etc/s6-overlay/s6-rc.d/user/contents.d/rpcapi

# Register testagent service (background test runner)
RUN mkdir -p /etc/s6-overlay/s6-rc.d/testagent \
 && echo "longrun" > /etc/s6-overlay/s6-rc.d/testagent/type \
 && printf '#!/command/with-contenv sh\nexec zonemaster_launch testagent\n' \
    > /etc/s6-overlay/s6-rc.d/testagent/run \
 && chmod +x /etc/s6-overlay/s6-rc.d/testagent/run \
 && touch /etc/s6-overlay/s6-rc.d/user/contents.d/testagent

EXPOSE 5000

ENTRYPOINT ["/init"]
