FROM debian:testing

## Install additional Debian packages

# Configure APT and upgrade base image
# – add source packages (for Suitesparse)
# – add contrib section (for matlab-support) and non-free section (for x13as)
# – do not install recommends, to keep image minimal
# – do no keep downloaded packages, to keep image minimal (now the default for
#   apt but not for apt-get, see Debian bug #160743; and we prefer to use
#   apt-get since it is recommended for scripting)
# – run non-interactively and assume yes to all questions
# – update APT database
# – upgrade the packages of the base image
RUN sed -i \
    's/^Types: deb$/Types: deb deb-src/g;s/^Components: main$/Components: main contrib non-free/g' \
    /etc/apt/sources.list.d/debian.sources \
    && { echo 'APT::Install-Recommends "false";'; \
    echo 'APT::Keep-Downloaded-Packages "false";'; \
    echo 'APT::Get::Assume-Yes "true";'; } > /etc/apt/apt.conf \
    && apt-get update \
    && apt-get dist-upgrade

# Install packages needed by Dynare jobs
RUN apt-get install \
# Basic git support
    git \
    git-lfs \
# The Dynare build dependencies, to be kept in sync with README.md
# NB: we use libboost-graph-dev instead of libboost-dev, because of this meson bug:
# https://github.com/mesonbuild/meson/issues/15470
    gcc \
    g++ \
    gfortran \
    octave-dev \
    libboost-graph-dev \
    libslicot-dev \
    libslicot64-pic \
    libsuitesparse-dev \
    flex \
    libfl-dev \
    bison \
    meson \
    pkgconf \
    texlive \
    texlive-publishers \
    texlive-latex-extra \
    texlive-fonts-extra \
    texlive-science \
    texlive-plain-generic \
    lmodern \
    cm-super \
    python3-sphinx \
    python3-sphinxcontrib.bibtex \
    tex-gyre \
    latexmk \
    libjs-mathjax \
    x13as \
# For building the ParU MEX file in Linux build jobs
# - dpkg-dev is needed for the apt-get source command below which retrieves suitesparse source
# - libopenblas-dev is needed for the Octave ParU MEX
    dpkg-dev \
    libopenblas-dev \
# Old Dynare build dependencies, which can be dropped once all our branches (incl. enterprise stable)
# no longer need them
    autoconf \
    automake \
    libgsl-dev \
    libmatio-dev \
# For running the Dynare testsuite
# - xauth is needed by xwayland-run (but only indirectly recommended by it)
# - texlive-font-utils provides /usr/bin/repstopdf, needed by tests/gsa/ls2003.mod
#   and other .mod files that directly call pdflatex
# - ghostscript in turn is needed by repstopdf (and only recommended by texlive-font-utils)
# - libopenblas0, libqt6waylandclient6 and fonts-freefont-otf are needed by octave
    xwayland-run \
    xauth \
    texlive-font-utils \
    ghostscript \
    libopenblas0 \
    libqt6waylandclient6 \
    fonts-freefont-otf \
    octave-optim \
    octave-io \
    octave-control \
    octave-datatypes \
# For building the Dynare source package
    xz-utils \
# For building the Dynare Windows package, to be kept in sync with windows/install-packages.sh
    gcc-mingw-w64-ucrt64 \
    g++-mingw-w64-ucrt64 \
    gfortran-mingw-w64-ucrt64 \
    mingw-w64-tools \
    make \
    7zip \
    wget \
    zstd \
    nsis \
    cmake \
# Old dependencies of the Dynare Windows package, which can be dropped once all our branches
# (incl. enterprise stable) no longer need them
    gcc-mingw-w64-x86-64-posix \
    g++-mingw-w64-x86-64-posix \
    gfortran-mingw-w64-x86-64-posix \
    parallel \
# For testing the code formatting
# NB: we enforce a specific clang-format version, because there are some behavioural
# differences across versions. Meson uses the default clang-format binary (provided by the
# clang-format package) if present, otherwise it falls back to the most recent clang-format-NN
# binary.
    clang-format-19 \
# For the clang-tidy job
    clang-tidy \
# For the dynare-python CI
    python3-pip \
# For the Dynare website, to be kept in sync with .gitlab-ci.yml in the website repository
    jekyll \
    ruby-jekyll-sitemap \
    ruby-jekyll-archives \
    ruby-jekyll-include-cache \
    ruby-dev \
    ruby-jekyll-paginate \
    ruby-jekyll-feed \
    ruby-jekyll-gist \
    jq \
    pdf2svg \
    imagemagick

# MATLAB R2026a dependencies
# From https://github.com/mathworks-ref-arch/container-images/blob/main/matlab-deps/r2026a/debian13/base-dependencies.txt
RUN apt-get install \
    ca-certificates \
    ibverbs-providers \
    libasound2t64 \
    libatk-bridge2.0-0t64 \
    libatk1.0-0t64 \
    libatomic1 \
    libatspi2.0-0t64 \
    libc6 \
    libcairo-gobject2 \
    libcairo2 \
    libcap2 \
    libcrypt1 \
    libcups2t64 \
    libfontconfig1 \
    libfribidi0 \
    libgbm1 \
    libgdk-pixbuf-2.0-0 \
    libgl1 \
    libglib2.0-0t64 \
    libglx0 \
    libgstreamer-plugins-base1.0-0 \
    libgstreamer1.0-0 \
    libgtk-3-0t64 \
    libhidapi-libusb0 \
    libibverbs1 \
    libice6 \
    libmosquitto1 \
    libmosquittopp1 \
    libnspr4 \
    libnss3 \
    libnuma1 \
    libopengl0 \
    libpam0g \
    libpango-1.0-0 \
    libpangocairo-1.0-0 \
    libpangoft2-1.0-0 \
    libpixman-1-0 \
    libpsm2-2 \
    librdmacm1t64 \
    libsndfile1 \
    libtirpc3t64 \
    libucx0 \
    libudev1 \
    libuuid1 \
    libxcomposite1 \
    libxcursor1 \
    libxdamage1 \
    libxfixes3 \
    libxfont2 \
    libxft2 \
    libxinerama1 \
    libxrandr2 \
    libxt6t64 \
    libxtst6 \
    libxxf86vm1 \
    locales \
    locales-all \
    make \
    net-tools \
    procps \
    sudo \
    unzip \
    x11-xkb-utils \
    zlib1g \
    wget


## Create dedicated user
RUN useradd -m gitlab-runner


## Install MATLAB

# NB: it will be possible to use --chmod=+x in Debian forky (requires Dockerfile 1.14)
ADD --chmod=755 https://www.mathworks.com/mpm/glnxa64/mpm /tmp/

ARG MATLAB_PRODUCTS="MATLAB Optimization_Toolbox"

# Oldest version supported by Dynare 7
RUN /tmp/mpm install --release=R2020a --destination=/usr/local/MATLAB/R2020a \
    --products ${MATLAB_PRODUCTS}
COPY --chown=gitlab-runner:gitlab-runner license-R2020a.lic \
    /home/gitlab-runner/.matlab/R2020a_licenses/

# Version used by enterprise stable CI
RUN /tmp/mpm install --release=R2021b --destination=/usr/local/MATLAB/R2021b \
    --products ${MATLAB_PRODUCTS}
COPY --chown=gitlab-runner:gitlab-runner license-R2021b.lic \
    /home/gitlab-runner/.matlab/R2021b_licenses/

# Version used by enterprise unstable CI
RUN /tmp/mpm install --release=R2023b --destination=/usr/local/MATLAB/R2023b \
    --products ${MATLAB_PRODUCTS}
COPY --chown=gitlab-runner:gitlab-runner license-R2023b.lic \
    /home/gitlab-runner/.matlab/R2023b_licenses/

# Latest version
RUN /tmp/mpm install --release=R2026a --destination=/usr/local/MATLAB/R2026a \
    --products ${MATLAB_PRODUCTS}
COPY --chown=gitlab-runner:gitlab-runner license-R2026a.lic \
    /home/gitlab-runner/.matlab/R2026a_licenses/

# Remove embedded system libraries using the matlab-support package, and clean up
RUN { echo 'matlab-support matlab-support/matlab-install-glob string /usr/local/MATLAB/*'; \
    echo 'matlab-support matlab-support/rename-libs boolean true'; } | debconf-set-selections \
    && apt-get install matlab-support \
    && rm -f /tmp/mpm /tmp/mathworks_root.log


## Misc

# Run subsequent commands as gitlab-runner, and ensure that at runtime the
# image starts with that user as well
USER gitlab-runner
WORKDIR /home/gitlab-runner

# Source of suitesparse for ParU MEX file in Linux build jobs
RUN apt-get source suitesparse \
    && rm -f suitesparse_* \
    && mv suitesparse-* suitesparse

# MATLAB and Panua Pardiso binaries for Windows package
COPY --chown=gitlab-runner:gitlab-runner \
    matlab64-20231122.tar.xz \
    matlab64-20250618.tar.xz \
    panua-pardiso-20240630-win.zip \
    .

# Configure git identity for commits (needed for pkg_source job)
RUN git config --global user.email noreply@dynare.org \
    && git config --global user.name "Dynare CI"
