Skip to content

Commit 00a3088

Browse files
DEV: separate builders
slim image by building nginx and imagemagick separately build jhead from source with no dependencies remove optipng, and pngcrush as these are disabled workers in discourse image_optim separate out discourse_web and discourse_release for no database web-only images. minimize layers by merging RUN commands prefer `&&\;` over `;\` for failing early on failing commands
1 parent 785fda3 commit 00a3088

File tree

4 files changed

+108
-89
lines changed

4 files changed

+108
-89
lines changed

image/base/Dockerfile

Lines changed: 97 additions & 84 deletions
Original file line numberDiff line numberDiff line change
@@ -2,34 +2,60 @@
22
# VERSION: release
33

44
ARG DEBIAN_RELEASE=bookworm
5+
FROM discourse/ruby:3.3.4-${DEBIAN_RELEASE}-slim AS builder
6+
ADD install-imagemagick /tmp/install-imagemagick
7+
# From https://nginx.org/en/pgp_keys.html
8+
ADD nginx_public_keys.key /tmp/nginx_public_keys.key
9+
ADD install-nginx /tmp/install-nginx
10+
RUN apt update && \
11+
DEBIAN_FRONTEND=noninteractive apt-get -y install wget \
12+
autoconf build-essential \
13+
git \
14+
cmake \
15+
gnupg \
16+
libpcre3-dev \
17+
libbrotli-dev
18+
RUN /tmp/install-imagemagick
19+
RUN gpg --import /tmp/nginx_public_keys.key &&\
20+
rm /tmp/nginx_public_keys.key &&\
21+
/tmp/install-nginx
22+
23+
ADD thpoff.c /src/thpoff.c
24+
RUN gcc -o /usr/local/sbin/thpoff /src/thpoff.c && rm /src/thpoff.c
25+
526
FROM discourse/ruby:3.3.4-${DEBIAN_RELEASE}-slim AS discourse_dependencies
627

728
ARG DEBIAN_RELEASE
829
ENV PG_MAJOR=13 \
930
RUBY_ALLOCATOR=/usr/lib/libjemalloc.so \
1031
LEFTHOOK=0 \
11-
DEBIAN_RELEASE=${DEBIAN_RELEASE}
32+
DEBIAN_RELEASE=${DEBIAN_RELEASE} \
33+
LC_ALL=en_US.UTF-8 \
34+
LANG=en_US.UTF-8 \
35+
LANGUAGE=en_US.UTF-8
1236

1337
#LABEL maintainer="Sam Saffron \"https://twitter.com/samsaffron\""
1438

39+
ADD install-oxipng install-jemalloc /tmp/
40+
1541
# Ensures that the gid and uid of the following users are consistent to avoid permission issues on directories in the
1642
# mounted volumes.
17-
RUN groupadd --gid 104 postgres &&\
18-
useradd --uid 101 --gid 104 --home /var/lib/postgresql --shell /bin/bash -c "PostgreSQL administrator,,," postgres &&\
19-
groupadd --gid 106 redis &&\
20-
useradd --uid 103 --gid 106 --home /var/lib/redis --shell /usr/sbin/nologin redis &&\
21-
groupadd --gid 1000 discourse &&\
22-
useradd --uid 1000 --gid 1000 -m --shell /bin/bash discourse
23-
24-
RUN echo 2.0.`date +%Y%m%d` > /VERSION
25-
RUN echo "deb http://deb.debian.org/debian ${DEBIAN_RELEASE}-backports main" > "/etc/apt/sources.list.d/${DEBIAN_RELEASE}-backports.list"
26-
2743
RUN --mount=type=cache,target=/var/cache/apt,sharing=locked \
2844
--mount=type=cache,target=/var/cache/debconf,sharing=locked \
2945
--mount=type=cache,target=/var/lib/apt,sharing=locked \
3046
--mount=type=tmpfs,target=/var/log \
31-
echo "debconf debconf/frontend select Teletype" | debconf-set-selections; \
32-
apt-get -y update && DEBIAN_FRONTEND=noninteractive apt-get -y install gnupg sudo curl fping locales \
47+
--mount=type=tmpfs,target=/root/.npm \
48+
groupadd --gid 104 postgres &&\
49+
useradd --uid 101 --gid 104 --home /var/lib/postgresql --shell /bin/bash -c "PostgreSQL administrator,,," postgres &&\
50+
groupadd --gid 106 redis &&\
51+
useradd --uid 103 --gid 106 --home /var/lib/redis --shell /usr/sbin/nologin redis &&\
52+
groupadd --gid 1000 discourse &&\
53+
useradd --uid 1000 --gid 1000 -m --shell /bin/bash discourse &&\
54+
# add version
55+
echo 2.0.`date +%Y%m%d` > /VERSION &&\
56+
echo "deb http://deb.debian.org/debian ${DEBIAN_RELEASE}-backports main" > "/etc/apt/sources.list.d/${DEBIAN_RELEASE}-backports.list" &&\
57+
echo "debconf debconf/frontend select Teletype" | debconf-set-selections &&\
58+
apt-get -y update && DEBIAN_FRONTEND=noninteractive apt-get -y install gnupg sudo curl fping locales \
3359
ca-certificates rsync \
3460
cmake g++ pkg-config patch \
3561
libxslt-dev libcurl4-openssl-dev \
@@ -38,94 +64,72 @@ RUN --mount=type=cache,target=/var/cache/apt,sharing=locked \
3864
libxml2-dev gawk parallel \
3965
libreadline-dev anacron wget \
4066
psmisc whois brotli libunwind-dev \
41-
libtcmalloc-minimal4 cmake \
42-
pngcrush pngquant ripgrep poppler-utils; \
67+
libtcmalloc-minimal4 \
68+
pngquant ripgrep poppler-utils \
69+
# imagemagick runtime dependencies
70+
libheif1 libjbig0 libtiff6 libpng16-16 libfontconfig1 \
71+
libwebpdemux2 libwebpmux3 libxext6 librsvg2-2 libgomp1 \
72+
# nginx runtime dependencies
73+
nginx-common &&\
4374
# install these without recommends to avoid pulling in e.g.
4475
# X11 libraries, mailutils
45-
DEBIAN_FRONTEND=noninteractive apt-get -y install --no-install-recommends git rsyslog logrotate cron ssh-client less; \
76+
DEBIAN_FRONTEND=noninteractive apt-get -y install --no-install-recommends git rsyslog logrotate cron ssh-client less &&\
4677
# postgres packages
4778
install -d /usr/share/postgresql-common/pgdg &&\
4879
curl -o /usr/share/postgresql-common/pgdg/apt.postgresql.org.asc --fail https://www.postgresql.org/media/keys/ACCC4CF8.asc &&\
49-
echo "deb [signed-by=/usr/share/postgresql-common/pgdg/apt.postgresql.org.asc] https://apt.postgresql.org/pub/repos/apt ${DEBIAN_RELEASE}-pgdg main" > /etc/apt/sources.list.d/pgdg.list; \
80+
echo "deb [signed-by=/usr/share/postgresql-common/pgdg/apt.postgresql.org.asc] https://apt.postgresql.org/pub/repos/apt ${DEBIAN_RELEASE}-pgdg main" > /etc/apt/sources.list.d/pgdg.list &&\
5081
# yarn packages
51-
curl -sS https://dl.yarnpkg.com/debian/pubkey.gpg | apt-key add -; \
52-
echo "deb https://dl.yarnpkg.com/debian/ stable main" > /etc/apt/sources.list.d/yarn.list; \
82+
curl -sS https://dl.yarnpkg.com/debian/pubkey.gpg | apt-key add - &&\
83+
echo "deb https://dl.yarnpkg.com/debian/ stable main" > /etc/apt/sources.list.d/yarn.list &&\
5384
# node packages
54-
curl --silent --location https://deb.nodesource.com/setup_18.x | sudo bash -; \
85+
curl --silent --location https://deb.nodesource.com/setup_18.x | sudo bash - &&\
5586
# setup anacron, rsyslog, initctl
56-
sed -i -e 's/start -q anacron/anacron -s/' /etc/cron.d/anacron; \
57-
sed -i.bak 's/$ModLoad imklog/#$ModLoad imklog/' /etc/rsyslog.conf; \
58-
sed -i.bak 's/module(load="imklog")/#module(load="imklog")/' /etc/rsyslog.conf; \
59-
dpkg-divert --local --rename --add /sbin/initctl; \
60-
sh -c "test -f /sbin/initctl || ln -s /bin/true /sbin/initctl"; \
87+
sed -i -e 's/start -q anacron/anacron -s/' /etc/cron.d/anacron &&\
88+
sed -i.bak 's/$ModLoad imklog/#$ModLoad imklog/' /etc/rsyslog.conf &&\
89+
sed -i.bak 's/module(load="imklog")/#module(load="imklog")/' /etc/rsyslog.conf &&\
90+
dpkg-divert --local --rename --add /sbin/initctl &&\
91+
sh -c "test -f /sbin/initctl || ln -s /bin/true /sbin/initctl" &&\
6192
apt-get -y update && DEBIAN_FRONTEND=noninteractive apt-get -y install runit socat \
6293
libpq-dev postgresql-client \
63-
postgresql-${PG_MAJOR} postgresql-contrib-${PG_MAJOR} postgresql-${PG_MAJOR}-pgvector \
6494
nodejs yarn &&\
65-
mkdir -p /etc/runit/1.d
66-
67-
ENV LC_ALL=en_US.UTF-8
68-
ENV LANG=en_US.UTF-8
69-
ENV LANGUAGE=en_US.UTF-8
70-
RUN sed -i "s/^# $LANG/$LANG/" /etc/locale.gen; \
71-
locale-gen
72-
73-
RUN --mount=type=tmpfs,target=/root/.npm \
74-
npm install -g terser uglify-js pnpm
75-
76-
ADD install-imagemagick /tmp/install-imagemagick
77-
RUN --mount=type=cache,target=/var/cache/apt,sharing=locked \
78-
--mount=type=cache,target=/var/cache/debconf,sharing=locked \
79-
--mount=type=cache,target=/var/lib/apt,sharing=locked \
80-
/tmp/install-imagemagick
81-
82-
ADD install-jemalloc /tmp/install-jemalloc
83-
RUN /tmp/install-jemalloc
84-
85-
# From https://nginx.org/en/pgp_keys.html
86-
ADD nginx_public_keys.key /tmp/nginx_public_keys.key
87-
ADD install-nginx /tmp/install-nginx
88-
89-
RUN --mount=type=cache,target=/var/cache/apt,sharing=locked \
90-
--mount=type=cache,target=/var/cache/debconf,sharing=locked \
91-
--mount=type=cache,target=/var/lib/apt,sharing=locked \
92-
gpg --import /tmp/nginx_public_keys.key &&\
93-
rm /tmp/nginx_public_keys.key &&\
94-
/tmp/install-nginx
95-
96-
ADD install-redis /tmp/install-redis
97-
RUN /tmp/install-redis
95+
mkdir -p /etc/runit/1.d &&\
96+
sed -i "s/^# $LANG/$LANG/" /etc/locale.gen && locale-gen &&\
97+
npm install -g terser uglify-js pnpm &&\
98+
/tmp/install-oxipng &&\
99+
/tmp/install-jemalloc
98100

99-
ADD install-oxipng /tmp/install-oxipng
100-
RUN --mount=type=cache,target=/var/cache/apt,sharing=locked \
101-
--mount=type=cache,target=/var/cache/debconf,sharing=locked \
102-
--mount=type=cache,target=/var/lib/apt,sharing=locked \
103-
/tmp/install-oxipng
104-
105-
RUN echo 'gem: --no-document' >> /usr/local/etc/gemrc &&\
106-
gem update --system
107-
108-
RUN gem install pups --force &&\
109-
mkdir -p /pups/bin/ &&\
110-
ln -s /usr/local/bin/pups /pups/bin/pups
101+
# Copy binary and configuration files for magick
102+
COPY --from=builder /usr/local/bin/magick /usr/local/bin/magick
103+
COPY --from=builder /usr/local/etc/ImageMagick-7 /usr/local/etc/ImageMagick-7
104+
COPY --from=builder /usr/sbin/nginx /usr/sbin/nginx
111105

112106
# This tool allows us to disable huge page support for our current process
113107
# since the flag is preserved through forks and execs it can be used on any
114108
# process
115-
ADD thpoff.c /src/thpoff.c
116-
RUN gcc -o /usr/local/sbin/thpoff /src/thpoff.c && rm /src/thpoff.c
117-
118-
# clean up for docker squash
119-
RUN rm -fr /usr/local/share/doc &&\
120-
rm -fr /usr/local/share/ri &&\
121-
rm -fr /var/lib/apt/lists/* &&\
122-
rm -fr /root/.gem &&\
123-
rm -fr /root/.npm &&\
124-
rm -fr /tmp/*
125-
109+
COPY --from=builder /usr/local/sbin/thpoff /usr/local/sbin/thpoff
110+
111+
# Create symlinks to imagemagick tools
112+
RUN ln -s /usr/local/bin/magick /usr/local/bin/animate &&\
113+
ln -s /usr/local/bin/magick /usr/local/bin/compare &&\
114+
ln -s /usr/local/bin/magick /usr/local/bin/composite &&\
115+
ln -s /usr/local/bin/magick /usr/local/bin/conjure &&\
116+
ln -s /usr/local/bin/magick /usr/local/bin/convert &&\
117+
ln -s /usr/local/bin/magick /usr/local/bin/display &&\
118+
ln -s /usr/local/bin/magick /usr/local/bin/identify &&\
119+
ln -s /usr/local/bin/magick /usr/local/bin/import &&\
120+
ln -s /usr/local/bin/magick /usr/local/bin/magick-script &&\
121+
ln -s /usr/local/bin/magick /usr/local/bin/mogrify &&\
122+
ln -s /usr/local/bin/magick /usr/local/bin/montage &&\
123+
ln -s /usr/local/bin/magick /usr/local/bin/stream &&\
124+
test $(magick -version | grep -o -e png -e tiff -e jpeg -e freetype -e heic -e webp | wc -l) -eq 6 &&\
125+
echo 'gem: --no-document' >> /usr/local/etc/gemrc &&\
126+
gem update --system &&\
127+
gem install pups --force &&\
128+
mkdir -p /pups/bin/ &&\
129+
ln -s /usr/local/bin/pups /pups/bin/pups &&\
126130
# this is required for aarch64 which uses buildx
127131
# see https://github.com/docker/buildx/issues/150
128-
RUN rm -f /etc/service
132+
rm -f /etc/service
129133

130134
COPY etc/ /etc
131135
COPY sbin/ /sbin
@@ -138,7 +142,7 @@ RUN install -dm 0755 -o discourse -g discourse /var/www/discourse &&\
138142
sudo -u discourse git clone --branch $DISCOURSE_BRANCH --filter=tree:0 https://github.com/discourse/discourse.git /var/www/discourse &&\
139143
gem install bundler --conservative -v $(awk '/BUNDLED WITH/ { getline; gsub(/ /,""); print $0 }' /var/www/discourse/Gemfile.lock)
140144

141-
FROM discourse_slim AS discourse_release
145+
FROM discourse_slim AS discourse_web
142146
ENV RAILS_ENV=production
143147

144148
RUN cd /var/www/discourse &&\
@@ -151,3 +155,12 @@ RUN cd /var/www/discourse &&\
151155

152156
RUN cd /var/www/discourse &&\
153157
sudo -u discourse /bin/bash -c 'if [ -f yarn.lock ]; then yarn install --frozen-lockfile && yarn cache clean; else pnpm install --frozen-lockfile; fi'
158+
159+
FROM discourse_web AS discourse_release
160+
ADD install-redis /tmp/install-redis
161+
RUN --mount=type=cache,target=/var/cache/apt,sharing=locked \
162+
--mount=type=cache,target=/var/cache/debconf,sharing=locked \
163+
--mount=type=cache,target=/var/lib/apt,sharing=locked \
164+
--mount=type=tmpfs,target=/var/log \
165+
apt-get -y update && DEBIAN_FRONTEND=noninteractive apt-get -y install postgresql-${PG_MAJOR} postgresql-contrib-${PG_MAJOR} postgresql-${PG_MAJOR}-pgvector &&\
166+
/tmp/install-redis

image/base/install-imagemagick

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -42,6 +42,8 @@ tar zxf $WDIR/ImageMagick.tar.gz -C $WDIR
4242
cd $IMDIR
4343
PKG_CONF_LIBDIR=$PREFIX/lib LDFLAGS=-L$PREFIX/lib CFLAGS='-O2 -I$PREFIX/include' ./configure \
4444
--prefix=$PREFIX \
45+
--disable-shared \
46+
--enable-delegate-build \
4547
--enable-static \
4648
--enable-bounds-checking \
4749
--enable-hdri \

image/base/install-jemalloc

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -16,7 +16,7 @@ if uname -m | grep -qi 'aarch64'; then
1616
sha256sum jemalloc-5.3.0.tar.bz2
1717
echo "2db82d1e7119df3e71b7640219b6dfe84789bc0537983c3b7ac4f7189aecfeaa jemalloc-5.3.0.tar.bz2" | sha256sum -c
1818
tar --strip-components=1 -xjf jemalloc-5.3.0.tar.bz2
19-
./configure --prefix=/usr --with-lg-page=16 && make build_lib -j"$(nproc)" && make install_lib
19+
./configure --prefix=/usr --with-lg-page=16 && make build_lib -j"$(nproc)" && make install_lib_shared
2020
cd / && rm -rf /jemalloc-new
2121
else
2222
# jemalloc stable
@@ -27,7 +27,7 @@ else
2727
sha256sum jemalloc-3.6.0.tar.bz2
2828
echo "e16c2159dd3c81ca2dc3b5c9ef0d43e1f2f45b04548f42db12e7c12d7bdf84fe jemalloc-3.6.0.tar.bz2" | sha256sum -c
2929
tar --strip-components=1 -xjf jemalloc-3.6.0.tar.bz2
30-
./configure --prefix=/usr $EXTRA_CONF && make -j"$(nproc)" && make install
30+
./configure --prefix=/usr $EXTRA_CONF && make -j"$(nproc)" && make install_lib_shared
3131
cd / && rm -rf /jemalloc-stable
3232

3333
# jemalloc new
@@ -38,6 +38,6 @@ else
3838
sha256sum jemalloc-5.3.0.tar.bz2
3939
echo "2db82d1e7119df3e71b7640219b6dfe84789bc0537983c3b7ac4f7189aecfeaa jemalloc-5.3.0.tar.bz2" | sha256sum -c
4040
tar --strip-components=1 -xjf jemalloc-5.3.0.tar.bz2
41-
./configure --prefix=/usr --with-install-suffix=5.3.0 && make build_lib -j"$(nproc)" && make install_lib
41+
./configure --prefix=/usr --with-install-suffix=5.3.0 && make build_lib -j"$(nproc)" && make install_lib_shared
4242
cd / && rm -rf /jemalloc-new
4343
fi

image/base/install-oxipng

Lines changed: 6 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -12,7 +12,11 @@ case "${dpkgArch##*-}" in
1212
esac
1313

1414
# Install other deps
15-
apt -y -q install advancecomp jhead jpegoptim libjpeg-turbo-progs optipng
15+
apt -y -q install advancecomp jpegoptim libjpeg-turbo-progs
16+
17+
git clone --depth 1 --branch "3.08" https://github.com/Matthias-Wandel/jhead.git /tmp/jhead
18+
cd /tmp/jhead && make && cp /tmp/jhead/jhead /usr/local/bin/jhead
19+
cd / && rm -rf /tmp/jhead
1620

1721
mkdir /oxipng-install
1822
cd /oxipng-install
@@ -22,4 +26,4 @@ sha256sum ${OXIPNG_FILE}
2226
echo "${OXIPNG_HASH} ${OXIPNG_FILE}" | sha256sum -c
2327
tar --strip-components=1 -xzf $OXIPNG_FILE
2428
cp -v ./oxipng /usr/local/bin
25-
cd / && rm -fr /oxipng-install
29+
cd / && rm -fr /oxipng-install

0 commit comments

Comments
 (0)