# syntax=docker/dockerfile:latest
# SPDX-FileCopyrightText: 2022 Nextcloud GmbH <https://nextcloud.com>
# SPDX-License-Identifier: AGPL-3.0-only
FROM alpine:3.23.4

RUN set -ex; \
    apk upgrade --no-cache -a; \
    apk add --no-cache tzdata clamav clamav-milter supervisor bash; \
    mkdir -p /tmp /var/lib/clamav /run/clamav /var/log/supervisord /var/run/supervisord; \
    chmod 777 -R /tmp /run/clamav /var/log/clamav /var/log/supervisord /var/run/supervisord; \
    chown -R 100:100 /var/lib/clamav; \
    sed -i "s|#\?MaxDirectoryRecursion.*|MaxDirectoryRecursion 30|g" /etc/clamav/clamd.conf; \
    sed -i "s|#\?MaxScanSize.*|MaxScanSize 2000M|g" /etc/clamav/clamd.conf; \
    sed -i "s|#\?MaxFileSize.*|MaxFileSize 2000M|g" /etc/clamav/clamd.conf; \
    sed -i "s|#\?PCREMaxFileSize.*|PCREMaxFileSize 2000M|g" /etc/clamav/clamd.conf; \
# StreamMaxLength must be synced with av_stream_max_length inside the Nextcloud files_antivirus plugin
    sed -i "s|#\?StreamMaxLength.*|StreamMaxLength 2000M|g" /etc/clamav/clamd.conf; \
# By default clamd keeps the old signature database in RAM while loading the new one,
# briefly doubling memory usage (~1 GB extra) during each freshclam update cycle.
# Setting ConcurrentDatabaseReload to "no" makes clamd unload the old database first,
# eliminating that transient peak and significantly reducing maximum RAM consumption.
    sed -i "s|#\?ConcurrentDatabaseReload.*|ConcurrentDatabaseReload no|g" /etc/clamav/clamd.conf; \
# The default thread pool is 10-12 threads, each reserving its own stack and scan buffers.
# The Nextcloud antivirus plugin sends one file at a time, so 2 threads are sufficient
# and avoids the idle per-thread memory overhead of the larger default pool.
    sed -i "s|#\?MaxThreads.*|MaxThreads 2|g" /etc/clamav/clamd.conf; \
    sed -i "s|#\?TCPSocket|TCPSocket|g" /etc/clamav/clamd.conf; \
    sed -i "s|^LocalSocket .*|LocalSocket /tmp/clamd.sock|g" /etc/clamav/clamd.conf; \
    sed -i "s|Example| |g" /etc/clamav/clamav-milter.conf; \
    sed -i "s|#\?MilterSocket inet:7357|MilterSocket inet:7357|g" /etc/clamav/clamav-milter.conf; \
    sed -i "s|#\?ClamdSocket unix:/run/clamav/clamd.sock|ClamdSocket unix:/tmp/clamd.sock|g" /etc/clamav/clamav-milter.conf; \
    sed -i "s|#\?OnInfected Quarantine|OnInfected Reject|g" /etc/clamav/clamav-milter.conf; \
    sed -i "s|#\?AddHeader Replace|AddHeader Add|g" /etc/clamav/clamav-milter.conf; \
    sed -i "s|#\?Foreground yes|Foreground yes|g" /etc/clamav/clamav-milter.conf

COPY --chmod=775 start.sh /start.sh
COPY --chmod=775 healthcheck.sh /healthcheck.sh
COPY --chmod=664 supervisord.conf /supervisord.conf

USER 100
RUN set -ex; \
    freshclam --foreground --stdout
VOLUME /var/lib/clamav
ENTRYPOINT ["/start.sh"]
CMD ["/usr/bin/supervisord", "-c", "/supervisord.conf"]
LABEL com.centurylinklabs.watchtower.enable="false" \
    wud.watch="false" \
    org.opencontainers.image.title="ClamAV for Nextcloud AIO" \
    org.opencontainers.image.description="ClamAV antivirus scanner for Nextcloud All-in-One" \
    org.opencontainers.image.url="https://github.com/nextcloud/all-in-one" \
    org.opencontainers.image.source="https://github.com/nextcloud/all-in-one" \
    org.opencontainers.image.vendor="Nextcloud" \
    org.opencontainers.image.documentation="https://github.com/nextcloud/all-in-one/blob/main/readme.md"
HEALTHCHECK --start-period=60s --retries=9 CMD /healthcheck.sh
