diff --git a/4.1-rc/alpine3.23/Dockerfile b/4.1-rc/alpine3.23/Dockerfile new file mode 100644 index 000000000..dedf2a010 --- /dev/null +++ b/4.1-rc/alpine3.23/Dockerfile @@ -0,0 +1,148 @@ +# +# NOTE: THIS DOCKERFILE IS GENERATED VIA "apply-templates.sh" +# +# PLEASE DO NOT EDIT IT DIRECTLY. +# + +FROM alpine:3.23 + +# skip installing gem documentation with `gem install`/`gem update` +RUN set -eux; \ + mkdir -p /usr/local/etc; \ + echo 'gem: --no-document' >> /usr/local/etc/gemrc + +ENV LANG C.UTF-8 + +# https://www.ruby-lang.org/en/news/2026/10/12/ruby-4-1-0-preview1-released/ +ENV RUBY_VERSION 4.1.0-preview1 +ENV RUBY_DOWNLOAD_URL https://cache.ruby-lang.org/pub/ruby/4.1/ruby-4.1.0-preview1.tar.xz +ENV RUBY_DOWNLOAD_SHA256 b81f20bf2bc72aa360785eb77ffa0c9f15343ac7316637fbf347500fc3e2e3a8 + +# some of ruby's build scripts are written in ruby +# we purge system ruby later to make sure our final image uses what we just built +RUN set -eux; \ + \ + apk add --no-cache --virtual .ruby-builddeps \ + autoconf \ + bzip2 \ + bzip2-dev \ + ca-certificates \ + coreutils \ + dpkg-dev dpkg \ + g++ \ + gcc \ + gdbm-dev \ + glib-dev \ + gmp-dev \ + libc-dev \ + libffi-dev \ + libxml2-dev \ + libxslt-dev \ + linux-headers \ + make \ + ncurses-dev \ + openssl \ + openssl-dev \ + patch \ + procps \ + yaml-dev \ + zlib-dev \ + ruby \ + tar \ + xz \ + yaml-dev \ + zlib-dev \ + ; \ + \ + rustArch=; \ + apkArch="$(apk --print-arch)"; \ + case "$apkArch" in \ + 'x86_64') rustArch='x86_64-unknown-linux-musl'; rustupUrl='https://static.rust-lang.org/rustup/archive/1.28.2/x86_64-unknown-linux-musl/rustup-init'; rustupSha256='e6599a1c7be58a2d8eaca66a80e0dc006d87bbcf780a58b7343d6e14c1605cb2' ;; \ + 'aarch64') rustArch='aarch64-unknown-linux-musl'; rustupUrl='https://static.rust-lang.org/rustup/archive/1.28.2/aarch64-unknown-linux-musl/rustup-init'; rustupSha256='a97c8f56d7462908695348dd8c71ea6740c138ce303715793a690503a94fc9a9' ;; \ + esac; \ + \ + if [ -n "$rustArch" ]; then \ + mkdir -p /tmp/rust; \ + \ + wget -O /tmp/rust/rustup-init "$rustupUrl"; \ + echo "$rustupSha256 */tmp/rust/rustup-init" | sha256sum --check --strict; \ + chmod +x /tmp/rust/rustup-init; \ + \ + export RUSTUP_HOME='/tmp/rust/rustup' CARGO_HOME='/tmp/rust/cargo'; \ + export PATH="$CARGO_HOME/bin:$PATH"; \ + /tmp/rust/rustup-init -y --no-modify-path --profile minimal --default-toolchain '1.91.1' --default-host "$rustArch"; \ + \ + rustc --version; \ + cargo --version; \ + fi; \ + \ + wget -O ruby.tar.xz "$RUBY_DOWNLOAD_URL"; \ + echo "$RUBY_DOWNLOAD_SHA256 *ruby.tar.xz" | sha256sum --check --strict; \ + \ + mkdir -p /usr/src/ruby; \ + tar -xJf ruby.tar.xz -C /usr/src/ruby --strip-components=1; \ + rm ruby.tar.xz; \ + \ + cd /usr/src/ruby; \ + \ +# https://github.com/docker-library/ruby/issues/196 +# https://bugs.ruby-lang.org/issues/14387#note-13 (patch source) +# https://bugs.ruby-lang.org/issues/14387#note-16 ("Therefore ncopa's patch looks good for me in general." -- only breaks glibc which doesn't matter here) + wget -O 'thread-stack-fix.patch' 'https://bugs.ruby-lang.org/attachments/download/7081/0001-thread_pthread.c-make-get_main_stack-portable-on-lin.patch'; \ + echo '3ab628a51d92fdf0d2b5835e93564857aea73e0c1de00313864a94a6255cb645 *thread-stack-fix.patch' | sha256sum --check --strict; \ + patch -p1 -i thread-stack-fix.patch; \ + rm thread-stack-fix.patch; \ + \ + autoconf; \ + gnuArch="$(dpkg-architecture --query DEB_BUILD_GNU_TYPE)"; \ +# full RELRO: "-z now" disables lazy binding so the loader can map the GOT read-only at startup +# https://github.com/docker-library/ruby/pull/529 +# https://salsa.debian.org/ruby-team/ruby/-/blob/8a55ab83e2c1783d80d0117fecbda533ac75f3e3/debian/rules#L63-67 (Debian's "hardening=+bindnow" produces the same flags) + export LDFLAGS='-Wl,-z,relro -Wl,-z,now'; \ + ./configure \ + --build="$gnuArch" \ + --disable-install-doc \ + --enable-shared \ + ${rustArch:+--enable-yjit} \ + ${rustArch:+--enable-zjit} \ + ; \ + make -j "$(nproc)"; \ + make install; \ + \ + rm -rf /tmp/rust; \ + runDeps="$( \ + scanelf --needed --nobanner --format '%n#p' --recursive /usr/local \ + | tr ',' '\n' \ + | sort -u \ + | awk 'system("[ -e /usr/local/lib/" $1 " ]") == 0 { next } { print "so:" $1 }' \ + )"; \ + apk add --no-network --virtual .ruby-rundeps $runDeps; \ + apk del --no-network .ruby-builddeps; \ + \ + cd /; \ + rm -r /usr/src/ruby; \ +# verify we have no "ruby" packages installed + if \ + apk --no-network list --installed \ + | grep -v '^[.]ruby-' \ + | grep -i ruby \ + ; then \ + exit 1; \ + fi; \ + [ "$(command -v ruby)" = '/usr/local/bin/ruby' ]; \ +# rough smoke test + ruby --version; \ + gem --version; \ + bundle --version + +# don't create ".bundle" in all our apps +ENV GEM_HOME /usr/local/bundle +ENV BUNDLE_SILENCE_ROOT_WARNING=1 \ + BUNDLE_APP_CONFIG="$GEM_HOME" +ENV PATH $GEM_HOME/bin:$PATH +RUN set -eux; \ + mkdir "$GEM_HOME"; \ +# adjust permissions of GEM_HOME for running "gem install" as an arbitrary user + chmod 1777 "$GEM_HOME" + +CMD [ "irb" ] diff --git a/4.1-rc/alpine3.24/Dockerfile b/4.1-rc/alpine3.24/Dockerfile new file mode 100644 index 000000000..90768f228 --- /dev/null +++ b/4.1-rc/alpine3.24/Dockerfile @@ -0,0 +1,148 @@ +# +# NOTE: THIS DOCKERFILE IS GENERATED VIA "apply-templates.sh" +# +# PLEASE DO NOT EDIT IT DIRECTLY. +# + +FROM alpine:3.24 + +# skip installing gem documentation with `gem install`/`gem update` +RUN set -eux; \ + mkdir -p /usr/local/etc; \ + echo 'gem: --no-document' >> /usr/local/etc/gemrc + +ENV LANG C.UTF-8 + +# https://www.ruby-lang.org/en/news/2026/10/12/ruby-4-1-0-preview1-released/ +ENV RUBY_VERSION 4.1.0-preview1 +ENV RUBY_DOWNLOAD_URL https://cache.ruby-lang.org/pub/ruby/4.1/ruby-4.1.0-preview1.tar.xz +ENV RUBY_DOWNLOAD_SHA256 b81f20bf2bc72aa360785eb77ffa0c9f15343ac7316637fbf347500fc3e2e3a8 + +# some of ruby's build scripts are written in ruby +# we purge system ruby later to make sure our final image uses what we just built +RUN set -eux; \ + \ + apk add --no-cache --virtual .ruby-builddeps \ + autoconf \ + bzip2 \ + bzip2-dev \ + ca-certificates \ + coreutils \ + dpkg-dev dpkg \ + g++ \ + gcc \ + gdbm-dev \ + glib-dev \ + gmp-dev \ + libc-dev \ + libffi-dev \ + libxml2-dev \ + libxslt-dev \ + linux-headers \ + make \ + ncurses-dev \ + openssl \ + openssl-dev \ + patch \ + procps \ + yaml-dev \ + zlib-dev \ + ruby \ + tar \ + xz \ + yaml-dev \ + zlib-dev \ + ; \ + \ + rustArch=; \ + apkArch="$(apk --print-arch)"; \ + case "$apkArch" in \ + 'x86_64') rustArch='x86_64-unknown-linux-musl'; rustupUrl='https://static.rust-lang.org/rustup/archive/1.28.2/x86_64-unknown-linux-musl/rustup-init'; rustupSha256='e6599a1c7be58a2d8eaca66a80e0dc006d87bbcf780a58b7343d6e14c1605cb2' ;; \ + 'aarch64') rustArch='aarch64-unknown-linux-musl'; rustupUrl='https://static.rust-lang.org/rustup/archive/1.28.2/aarch64-unknown-linux-musl/rustup-init'; rustupSha256='a97c8f56d7462908695348dd8c71ea6740c138ce303715793a690503a94fc9a9' ;; \ + esac; \ + \ + if [ -n "$rustArch" ]; then \ + mkdir -p /tmp/rust; \ + \ + wget -O /tmp/rust/rustup-init "$rustupUrl"; \ + echo "$rustupSha256 */tmp/rust/rustup-init" | sha256sum --check --strict; \ + chmod +x /tmp/rust/rustup-init; \ + \ + export RUSTUP_HOME='/tmp/rust/rustup' CARGO_HOME='/tmp/rust/cargo'; \ + export PATH="$CARGO_HOME/bin:$PATH"; \ + /tmp/rust/rustup-init -y --no-modify-path --profile minimal --default-toolchain '1.91.1' --default-host "$rustArch"; \ + \ + rustc --version; \ + cargo --version; \ + fi; \ + \ + wget -O ruby.tar.xz "$RUBY_DOWNLOAD_URL"; \ + echo "$RUBY_DOWNLOAD_SHA256 *ruby.tar.xz" | sha256sum --check --strict; \ + \ + mkdir -p /usr/src/ruby; \ + tar -xJf ruby.tar.xz -C /usr/src/ruby --strip-components=1; \ + rm ruby.tar.xz; \ + \ + cd /usr/src/ruby; \ + \ +# https://github.com/docker-library/ruby/issues/196 +# https://bugs.ruby-lang.org/issues/14387#note-13 (patch source) +# https://bugs.ruby-lang.org/issues/14387#note-16 ("Therefore ncopa's patch looks good for me in general." -- only breaks glibc which doesn't matter here) + wget -O 'thread-stack-fix.patch' 'https://bugs.ruby-lang.org/attachments/download/7081/0001-thread_pthread.c-make-get_main_stack-portable-on-lin.patch'; \ + echo '3ab628a51d92fdf0d2b5835e93564857aea73e0c1de00313864a94a6255cb645 *thread-stack-fix.patch' | sha256sum --check --strict; \ + patch -p1 -i thread-stack-fix.patch; \ + rm thread-stack-fix.patch; \ + \ + autoconf; \ + gnuArch="$(dpkg-architecture --query DEB_BUILD_GNU_TYPE)"; \ +# full RELRO: "-z now" disables lazy binding so the loader can map the GOT read-only at startup +# https://github.com/docker-library/ruby/pull/529 +# https://salsa.debian.org/ruby-team/ruby/-/blob/8a55ab83e2c1783d80d0117fecbda533ac75f3e3/debian/rules#L63-67 (Debian's "hardening=+bindnow" produces the same flags) + export LDFLAGS='-Wl,-z,relro -Wl,-z,now'; \ + ./configure \ + --build="$gnuArch" \ + --disable-install-doc \ + --enable-shared \ + ${rustArch:+--enable-yjit} \ + ${rustArch:+--enable-zjit} \ + ; \ + make -j "$(nproc)"; \ + make install; \ + \ + rm -rf /tmp/rust; \ + runDeps="$( \ + scanelf --needed --nobanner --format '%n#p' --recursive /usr/local \ + | tr ',' '\n' \ + | sort -u \ + | awk 'system("[ -e /usr/local/lib/" $1 " ]") == 0 { next } { print "so:" $1 }' \ + )"; \ + apk add --no-network --virtual .ruby-rundeps $runDeps; \ + apk del --no-network .ruby-builddeps; \ + \ + cd /; \ + rm -r /usr/src/ruby; \ +# verify we have no "ruby" packages installed + if \ + apk --no-network list --installed \ + | grep -v '^[.]ruby-' \ + | grep -i ruby \ + ; then \ + exit 1; \ + fi; \ + [ "$(command -v ruby)" = '/usr/local/bin/ruby' ]; \ +# rough smoke test + ruby --version; \ + gem --version; \ + bundle --version + +# don't create ".bundle" in all our apps +ENV GEM_HOME /usr/local/bundle +ENV BUNDLE_SILENCE_ROOT_WARNING=1 \ + BUNDLE_APP_CONFIG="$GEM_HOME" +ENV PATH $GEM_HOME/bin:$PATH +RUN set -eux; \ + mkdir "$GEM_HOME"; \ +# adjust permissions of GEM_HOME for running "gem install" as an arbitrary user + chmod 1777 "$GEM_HOME" + +CMD [ "irb" ] diff --git a/4.1-rc/bookworm/Dockerfile b/4.1-rc/bookworm/Dockerfile new file mode 100644 index 000000000..942b4017b --- /dev/null +++ b/4.1-rc/bookworm/Dockerfile @@ -0,0 +1,115 @@ +# +# NOTE: THIS DOCKERFILE IS GENERATED VIA "apply-templates.sh" +# +# PLEASE DO NOT EDIT IT DIRECTLY. +# + +FROM buildpack-deps:bookworm + +# skip installing gem documentation with `gem install`/`gem update` +RUN set -eux; \ + mkdir -p /usr/local/etc; \ + echo 'gem: --no-document' >> /usr/local/etc/gemrc + +ENV LANG C.UTF-8 + +# https://www.ruby-lang.org/en/news/2026/10/12/ruby-4-1-0-preview1-released/ +ENV RUBY_VERSION 4.1.0-preview1 +ENV RUBY_DOWNLOAD_URL https://cache.ruby-lang.org/pub/ruby/4.1/ruby-4.1.0-preview1.tar.xz +ENV RUBY_DOWNLOAD_SHA256 b81f20bf2bc72aa360785eb77ffa0c9f15343ac7316637fbf347500fc3e2e3a8 + +# some of ruby's build scripts are written in ruby +# we purge system ruby later to make sure our final image uses what we just built +RUN set -eux; \ + \ + savedAptMark="$(apt-mark showmanual)"; \ + apt-get update; \ + apt-get install -y --no-install-recommends \ + dpkg-dev \ + libgdbm-dev \ + ruby \ + ; \ + \ + rustArch=; \ + dpkgArch="$(dpkg --print-architecture)"; \ + case "$dpkgArch" in \ + 'amd64') rustArch='x86_64-unknown-linux-gnu'; rustupUrl='https://static.rust-lang.org/rustup/archive/1.28.2/x86_64-unknown-linux-gnu/rustup-init'; rustupSha256='20a06e644b0d9bd2fbdbfd52d42540bdde820ea7df86e92e533c073da0cdd43c' ;; \ + 'arm64') rustArch='aarch64-unknown-linux-gnu'; rustupUrl='https://static.rust-lang.org/rustup/archive/1.28.2/aarch64-unknown-linux-gnu/rustup-init'; rustupSha256='e3853c5a252fca15252d07cb23a1bdd9377a8c6f3efa01531109281ae47f841c' ;; \ + esac; \ + \ + if [ -n "$rustArch" ]; then \ + mkdir -p /tmp/rust; \ + \ + wget -O /tmp/rust/rustup-init "$rustupUrl"; \ + echo "$rustupSha256 */tmp/rust/rustup-init" | sha256sum --check --strict; \ + chmod +x /tmp/rust/rustup-init; \ + \ + export RUSTUP_HOME='/tmp/rust/rustup' CARGO_HOME='/tmp/rust/cargo'; \ + export PATH="$CARGO_HOME/bin:$PATH"; \ + /tmp/rust/rustup-init -y --no-modify-path --profile minimal --default-toolchain '1.91.1' --default-host "$rustArch"; \ + \ + rustc --version; \ + cargo --version; \ + fi; \ + \ + wget -O ruby.tar.xz "$RUBY_DOWNLOAD_URL"; \ + echo "$RUBY_DOWNLOAD_SHA256 *ruby.tar.xz" | sha256sum --check --strict; \ + \ + mkdir -p /usr/src/ruby; \ + tar -xJf ruby.tar.xz -C /usr/src/ruby --strip-components=1; \ + rm ruby.tar.xz; \ + \ + cd /usr/src/ruby; \ + \ + autoconf; \ + gnuArch="$(dpkg-architecture --query DEB_BUILD_GNU_TYPE)"; \ +# full RELRO: "-z now" disables lazy binding so the loader can map the GOT read-only at startup +# https://github.com/docker-library/ruby/pull/529 +# https://salsa.debian.org/ruby-team/ruby/-/blob/8a55ab83e2c1783d80d0117fecbda533ac75f3e3/debian/rules#L63-67 (Debian's "hardening=+bindnow" produces the same flags) + export LDFLAGS='-Wl,-z,relro -Wl,-z,now'; \ + ./configure \ + --build="$gnuArch" \ + --disable-install-doc \ + --enable-shared \ + ${rustArch:+--enable-yjit} \ + ${rustArch:+--enable-zjit} \ + ; \ + make -j "$(nproc)"; \ + make install; \ + \ + rm -rf /tmp/rust; \ + apt-mark auto '.*' > /dev/null; \ + apt-mark manual $savedAptMark > /dev/null; \ + find /usr/local -type f -executable -not \( -name '*tkinter*' \) -exec ldd '{}' ';' \ + | awk '/=>/ { so = $(NF-1); if (index(so, "/usr/local/") == 1) { next }; gsub("^/(usr/)?", "", so); printf "*%s\n", so }' \ + | sort -u \ + | xargs -r dpkg-query --search \ +# https://manpages.debian.org/bookworm/dpkg/dpkg-query.1.en.html#S (we ignore diversions and it'll be really unusual for more than one package to provide any given .so file) + | awk 'sub(":$", "", $1) { print $1 }' \ + | sort -u \ + | xargs -r apt-mark manual \ + ; \ + apt-get purge -y --auto-remove -o APT::AutoRemove::RecommendsImportant=false; \ + rm -rf /var/lib/apt/lists/*; \ + \ + cd /; \ + rm -r /usr/src/ruby; \ +# verify we have no "ruby" packages installed + if dpkg -l | grep -i ruby; then exit 1; fi; \ + [ "$(command -v ruby)" = '/usr/local/bin/ruby' ]; \ +# rough smoke test + ruby --version; \ + gem --version; \ + bundle --version + +# don't create ".bundle" in all our apps +ENV GEM_HOME /usr/local/bundle +ENV BUNDLE_SILENCE_ROOT_WARNING=1 \ + BUNDLE_APP_CONFIG="$GEM_HOME" +ENV PATH $GEM_HOME/bin:$PATH +RUN set -eux; \ + mkdir "$GEM_HOME"; \ +# adjust permissions of GEM_HOME for running "gem install" as an arbitrary user + chmod 1777 "$GEM_HOME" + +CMD [ "irb" ] diff --git a/4.1-rc/slim-bookworm/Dockerfile b/4.1-rc/slim-bookworm/Dockerfile new file mode 100644 index 000000000..1e4c6091b --- /dev/null +++ b/4.1-rc/slim-bookworm/Dockerfile @@ -0,0 +1,140 @@ +# +# NOTE: THIS DOCKERFILE IS GENERATED VIA "apply-templates.sh" +# +# PLEASE DO NOT EDIT IT DIRECTLY. +# + +FROM debian:bookworm-slim + +RUN set -eux; \ + apt-get update; \ + apt-get install -y --no-install-recommends \ + ca-certificates \ + ; \ + rm -rf /var/lib/apt/lists/* + +# skip installing gem documentation with `gem install`/`gem update` +RUN set -eux; \ + mkdir -p /usr/local/etc; \ + echo 'gem: --no-document' >> /usr/local/etc/gemrc + +ENV LANG C.UTF-8 + +# https://www.ruby-lang.org/en/news/2026/10/12/ruby-4-1-0-preview1-released/ +ENV RUBY_VERSION 4.1.0-preview1 +ENV RUBY_DOWNLOAD_URL https://cache.ruby-lang.org/pub/ruby/4.1/ruby-4.1.0-preview1.tar.xz +ENV RUBY_DOWNLOAD_SHA256 b81f20bf2bc72aa360785eb77ffa0c9f15343ac7316637fbf347500fc3e2e3a8 + +# some of ruby's build scripts are written in ruby +# we purge system ruby later to make sure our final image uses what we just built +RUN set -eux; \ + \ + savedAptMark="$(apt-mark showmanual)"; \ + apt-get update; \ + apt-get install -y --no-install-recommends \ + dpkg-dev \ + libgdbm-dev \ + ruby \ + autoconf \ + bzip2 \ + g++ \ + gcc \ + libbz2-dev \ + libffi-dev \ + libgdbm-compat-dev \ + libglib2.0-dev \ + libgmp-dev \ + libncurses-dev \ + libssl-dev \ + libxml2-dev \ + libxslt-dev \ + libyaml-dev \ + make \ + wget \ + xz-utils \ + zlib1g-dev \ + ; \ + \ + rustArch=; \ + dpkgArch="$(dpkg --print-architecture)"; \ + case "$dpkgArch" in \ + 'amd64') rustArch='x86_64-unknown-linux-gnu'; rustupUrl='https://static.rust-lang.org/rustup/archive/1.28.2/x86_64-unknown-linux-gnu/rustup-init'; rustupSha256='20a06e644b0d9bd2fbdbfd52d42540bdde820ea7df86e92e533c073da0cdd43c' ;; \ + 'arm64') rustArch='aarch64-unknown-linux-gnu'; rustupUrl='https://static.rust-lang.org/rustup/archive/1.28.2/aarch64-unknown-linux-gnu/rustup-init'; rustupSha256='e3853c5a252fca15252d07cb23a1bdd9377a8c6f3efa01531109281ae47f841c' ;; \ + esac; \ + \ + if [ -n "$rustArch" ]; then \ + mkdir -p /tmp/rust; \ + \ + wget -O /tmp/rust/rustup-init "$rustupUrl"; \ + echo "$rustupSha256 */tmp/rust/rustup-init" | sha256sum --check --strict; \ + chmod +x /tmp/rust/rustup-init; \ + \ + export RUSTUP_HOME='/tmp/rust/rustup' CARGO_HOME='/tmp/rust/cargo'; \ + export PATH="$CARGO_HOME/bin:$PATH"; \ + /tmp/rust/rustup-init -y --no-modify-path --profile minimal --default-toolchain '1.91.1' --default-host "$rustArch"; \ + \ + rustc --version; \ + cargo --version; \ + fi; \ + \ + wget -O ruby.tar.xz "$RUBY_DOWNLOAD_URL"; \ + echo "$RUBY_DOWNLOAD_SHA256 *ruby.tar.xz" | sha256sum --check --strict; \ + \ + mkdir -p /usr/src/ruby; \ + tar -xJf ruby.tar.xz -C /usr/src/ruby --strip-components=1; \ + rm ruby.tar.xz; \ + \ + cd /usr/src/ruby; \ + \ + autoconf; \ + gnuArch="$(dpkg-architecture --query DEB_BUILD_GNU_TYPE)"; \ +# full RELRO: "-z now" disables lazy binding so the loader can map the GOT read-only at startup +# https://github.com/docker-library/ruby/pull/529 +# https://salsa.debian.org/ruby-team/ruby/-/blob/8a55ab83e2c1783d80d0117fecbda533ac75f3e3/debian/rules#L63-67 (Debian's "hardening=+bindnow" produces the same flags) + export LDFLAGS='-Wl,-z,relro -Wl,-z,now'; \ + ./configure \ + --build="$gnuArch" \ + --disable-install-doc \ + --enable-shared \ + ${rustArch:+--enable-yjit} \ + ${rustArch:+--enable-zjit} \ + ; \ + make -j "$(nproc)"; \ + make install; \ + \ + rm -rf /tmp/rust; \ + apt-mark auto '.*' > /dev/null; \ + apt-mark manual $savedAptMark > /dev/null; \ + find /usr/local -type f -executable -not \( -name '*tkinter*' \) -exec ldd '{}' ';' \ + | awk '/=>/ { so = $(NF-1); if (index(so, "/usr/local/") == 1) { next }; gsub("^/(usr/)?", "", so); printf "*%s\n", so }' \ + | sort -u \ + | xargs -r dpkg-query --search \ +# https://manpages.debian.org/bookworm/dpkg/dpkg-query.1.en.html#S (we ignore diversions and it'll be really unusual for more than one package to provide any given .so file) + | awk 'sub(":$", "", $1) { print $1 }' \ + | sort -u \ + | xargs -r apt-mark manual \ + ; \ + apt-get purge -y --auto-remove -o APT::AutoRemove::RecommendsImportant=false; \ + rm -rf /var/lib/apt/lists/*; \ + \ + cd /; \ + rm -r /usr/src/ruby; \ +# verify we have no "ruby" packages installed + if dpkg -l | grep -i ruby; then exit 1; fi; \ + [ "$(command -v ruby)" = '/usr/local/bin/ruby' ]; \ +# rough smoke test + ruby --version; \ + gem --version; \ + bundle --version + +# don't create ".bundle" in all our apps +ENV GEM_HOME /usr/local/bundle +ENV BUNDLE_SILENCE_ROOT_WARNING=1 \ + BUNDLE_APP_CONFIG="$GEM_HOME" +ENV PATH $GEM_HOME/bin:$PATH +RUN set -eux; \ + mkdir "$GEM_HOME"; \ +# adjust permissions of GEM_HOME for running "gem install" as an arbitrary user + chmod 1777 "$GEM_HOME" + +CMD [ "irb" ] diff --git a/4.1-rc/slim-trixie/Dockerfile b/4.1-rc/slim-trixie/Dockerfile new file mode 100644 index 000000000..14ee84d9e --- /dev/null +++ b/4.1-rc/slim-trixie/Dockerfile @@ -0,0 +1,140 @@ +# +# NOTE: THIS DOCKERFILE IS GENERATED VIA "apply-templates.sh" +# +# PLEASE DO NOT EDIT IT DIRECTLY. +# + +FROM debian:trixie-slim + +RUN set -eux; \ + apt-get update; \ + apt-get install -y --no-install-recommends \ + ca-certificates \ + ; \ + apt-get dist-clean + +# skip installing gem documentation with `gem install`/`gem update` +RUN set -eux; \ + mkdir -p /usr/local/etc; \ + echo 'gem: --no-document' >> /usr/local/etc/gemrc + +ENV LANG C.UTF-8 + +# https://www.ruby-lang.org/en/news/2026/10/12/ruby-4-1-0-preview1-released/ +ENV RUBY_VERSION 4.1.0-preview1 +ENV RUBY_DOWNLOAD_URL https://cache.ruby-lang.org/pub/ruby/4.1/ruby-4.1.0-preview1.tar.xz +ENV RUBY_DOWNLOAD_SHA256 b81f20bf2bc72aa360785eb77ffa0c9f15343ac7316637fbf347500fc3e2e3a8 + +# some of ruby's build scripts are written in ruby +# we purge system ruby later to make sure our final image uses what we just built +RUN set -eux; \ + \ + savedAptMark="$(apt-mark showmanual)"; \ + apt-get update; \ + apt-get install -y --no-install-recommends \ + dpkg-dev \ + libgdbm-dev \ + ruby \ + autoconf \ + bzip2 \ + g++ \ + gcc \ + libbz2-dev \ + libffi-dev \ + libgdbm-compat-dev \ + libglib2.0-dev \ + libgmp-dev \ + libncurses-dev \ + libssl-dev \ + libxml2-dev \ + libxslt-dev \ + libyaml-dev \ + make \ + wget \ + xz-utils \ + zlib1g-dev \ + ; \ + \ + rustArch=; \ + dpkgArch="$(dpkg --print-architecture)"; \ + case "$dpkgArch" in \ + 'amd64') rustArch='x86_64-unknown-linux-gnu'; rustupUrl='https://static.rust-lang.org/rustup/archive/1.28.2/x86_64-unknown-linux-gnu/rustup-init'; rustupSha256='20a06e644b0d9bd2fbdbfd52d42540bdde820ea7df86e92e533c073da0cdd43c' ;; \ + 'arm64') rustArch='aarch64-unknown-linux-gnu'; rustupUrl='https://static.rust-lang.org/rustup/archive/1.28.2/aarch64-unknown-linux-gnu/rustup-init'; rustupSha256='e3853c5a252fca15252d07cb23a1bdd9377a8c6f3efa01531109281ae47f841c' ;; \ + esac; \ + \ + if [ -n "$rustArch" ]; then \ + mkdir -p /tmp/rust; \ + \ + wget -O /tmp/rust/rustup-init "$rustupUrl"; \ + echo "$rustupSha256 */tmp/rust/rustup-init" | sha256sum --check --strict; \ + chmod +x /tmp/rust/rustup-init; \ + \ + export RUSTUP_HOME='/tmp/rust/rustup' CARGO_HOME='/tmp/rust/cargo'; \ + export PATH="$CARGO_HOME/bin:$PATH"; \ + /tmp/rust/rustup-init -y --no-modify-path --profile minimal --default-toolchain '1.91.1' --default-host "$rustArch"; \ + \ + rustc --version; \ + cargo --version; \ + fi; \ + \ + wget -O ruby.tar.xz "$RUBY_DOWNLOAD_URL"; \ + echo "$RUBY_DOWNLOAD_SHA256 *ruby.tar.xz" | sha256sum --check --strict; \ + \ + mkdir -p /usr/src/ruby; \ + tar -xJf ruby.tar.xz -C /usr/src/ruby --strip-components=1; \ + rm ruby.tar.xz; \ + \ + cd /usr/src/ruby; \ + \ + autoconf; \ + gnuArch="$(dpkg-architecture --query DEB_BUILD_GNU_TYPE)"; \ +# full RELRO: "-z now" disables lazy binding so the loader can map the GOT read-only at startup +# https://github.com/docker-library/ruby/pull/529 +# https://salsa.debian.org/ruby-team/ruby/-/blob/8a55ab83e2c1783d80d0117fecbda533ac75f3e3/debian/rules#L63-67 (Debian's "hardening=+bindnow" produces the same flags) + export LDFLAGS='-Wl,-z,relro -Wl,-z,now'; \ + ./configure \ + --build="$gnuArch" \ + --disable-install-doc \ + --enable-shared \ + ${rustArch:+--enable-yjit} \ + ${rustArch:+--enable-zjit} \ + ; \ + make -j "$(nproc)"; \ + make install; \ + \ + rm -rf /tmp/rust; \ + apt-mark auto '.*' > /dev/null; \ + apt-mark manual $savedAptMark > /dev/null; \ + find /usr/local -type f -executable -not \( -name '*tkinter*' \) -exec ldd '{}' ';' \ + | awk '/=>/ { so = $(NF-1); if (index(so, "/usr/local/") == 1) { next }; gsub("^/(usr/)?", "", so); printf "*%s\n", so }' \ + | sort -u \ + | xargs -r dpkg-query --search \ +# https://manpages.debian.org/bookworm/dpkg/dpkg-query.1.en.html#S (we ignore diversions and it'll be really unusual for more than one package to provide any given .so file) + | awk 'sub(":$", "", $1) { print $1 }' \ + | sort -u \ + | xargs -r apt-mark manual \ + ; \ + apt-get purge -y --auto-remove -o APT::AutoRemove::RecommendsImportant=false; \ + apt-get dist-clean; \ + \ + cd /; \ + rm -r /usr/src/ruby; \ +# verify we have no "ruby" packages installed + if dpkg -l | grep -i ruby; then exit 1; fi; \ + [ "$(command -v ruby)" = '/usr/local/bin/ruby' ]; \ +# rough smoke test + ruby --version; \ + gem --version; \ + bundle --version + +# don't create ".bundle" in all our apps +ENV GEM_HOME /usr/local/bundle +ENV BUNDLE_SILENCE_ROOT_WARNING=1 \ + BUNDLE_APP_CONFIG="$GEM_HOME" +ENV PATH $GEM_HOME/bin:$PATH +RUN set -eux; \ + mkdir "$GEM_HOME"; \ +# adjust permissions of GEM_HOME for running "gem install" as an arbitrary user + chmod 1777 "$GEM_HOME" + +CMD [ "irb" ] diff --git a/4.1-rc/trixie/Dockerfile b/4.1-rc/trixie/Dockerfile new file mode 100644 index 000000000..6bad32da8 --- /dev/null +++ b/4.1-rc/trixie/Dockerfile @@ -0,0 +1,115 @@ +# +# NOTE: THIS DOCKERFILE IS GENERATED VIA "apply-templates.sh" +# +# PLEASE DO NOT EDIT IT DIRECTLY. +# + +FROM buildpack-deps:trixie + +# skip installing gem documentation with `gem install`/`gem update` +RUN set -eux; \ + mkdir -p /usr/local/etc; \ + echo 'gem: --no-document' >> /usr/local/etc/gemrc + +ENV LANG C.UTF-8 + +# https://www.ruby-lang.org/en/news/2026/10/12/ruby-4-1-0-preview1-released/ +ENV RUBY_VERSION 4.1.0-preview1 +ENV RUBY_DOWNLOAD_URL https://cache.ruby-lang.org/pub/ruby/4.1/ruby-4.1.0-preview1.tar.xz +ENV RUBY_DOWNLOAD_SHA256 b81f20bf2bc72aa360785eb77ffa0c9f15343ac7316637fbf347500fc3e2e3a8 + +# some of ruby's build scripts are written in ruby +# we purge system ruby later to make sure our final image uses what we just built +RUN set -eux; \ + \ + savedAptMark="$(apt-mark showmanual)"; \ + apt-get update; \ + apt-get install -y --no-install-recommends \ + dpkg-dev \ + libgdbm-dev \ + ruby \ + ; \ + \ + rustArch=; \ + dpkgArch="$(dpkg --print-architecture)"; \ + case "$dpkgArch" in \ + 'amd64') rustArch='x86_64-unknown-linux-gnu'; rustupUrl='https://static.rust-lang.org/rustup/archive/1.28.2/x86_64-unknown-linux-gnu/rustup-init'; rustupSha256='20a06e644b0d9bd2fbdbfd52d42540bdde820ea7df86e92e533c073da0cdd43c' ;; \ + 'arm64') rustArch='aarch64-unknown-linux-gnu'; rustupUrl='https://static.rust-lang.org/rustup/archive/1.28.2/aarch64-unknown-linux-gnu/rustup-init'; rustupSha256='e3853c5a252fca15252d07cb23a1bdd9377a8c6f3efa01531109281ae47f841c' ;; \ + esac; \ + \ + if [ -n "$rustArch" ]; then \ + mkdir -p /tmp/rust; \ + \ + wget -O /tmp/rust/rustup-init "$rustupUrl"; \ + echo "$rustupSha256 */tmp/rust/rustup-init" | sha256sum --check --strict; \ + chmod +x /tmp/rust/rustup-init; \ + \ + export RUSTUP_HOME='/tmp/rust/rustup' CARGO_HOME='/tmp/rust/cargo'; \ + export PATH="$CARGO_HOME/bin:$PATH"; \ + /tmp/rust/rustup-init -y --no-modify-path --profile minimal --default-toolchain '1.91.1' --default-host "$rustArch"; \ + \ + rustc --version; \ + cargo --version; \ + fi; \ + \ + wget -O ruby.tar.xz "$RUBY_DOWNLOAD_URL"; \ + echo "$RUBY_DOWNLOAD_SHA256 *ruby.tar.xz" | sha256sum --check --strict; \ + \ + mkdir -p /usr/src/ruby; \ + tar -xJf ruby.tar.xz -C /usr/src/ruby --strip-components=1; \ + rm ruby.tar.xz; \ + \ + cd /usr/src/ruby; \ + \ + autoconf; \ + gnuArch="$(dpkg-architecture --query DEB_BUILD_GNU_TYPE)"; \ +# full RELRO: "-z now" disables lazy binding so the loader can map the GOT read-only at startup +# https://github.com/docker-library/ruby/pull/529 +# https://salsa.debian.org/ruby-team/ruby/-/blob/8a55ab83e2c1783d80d0117fecbda533ac75f3e3/debian/rules#L63-67 (Debian's "hardening=+bindnow" produces the same flags) + export LDFLAGS='-Wl,-z,relro -Wl,-z,now'; \ + ./configure \ + --build="$gnuArch" \ + --disable-install-doc \ + --enable-shared \ + ${rustArch:+--enable-yjit} \ + ${rustArch:+--enable-zjit} \ + ; \ + make -j "$(nproc)"; \ + make install; \ + \ + rm -rf /tmp/rust; \ + apt-mark auto '.*' > /dev/null; \ + apt-mark manual $savedAptMark > /dev/null; \ + find /usr/local -type f -executable -not \( -name '*tkinter*' \) -exec ldd '{}' ';' \ + | awk '/=>/ { so = $(NF-1); if (index(so, "/usr/local/") == 1) { next }; gsub("^/(usr/)?", "", so); printf "*%s\n", so }' \ + | sort -u \ + | xargs -r dpkg-query --search \ +# https://manpages.debian.org/bookworm/dpkg/dpkg-query.1.en.html#S (we ignore diversions and it'll be really unusual for more than one package to provide any given .so file) + | awk 'sub(":$", "", $1) { print $1 }' \ + | sort -u \ + | xargs -r apt-mark manual \ + ; \ + apt-get purge -y --auto-remove -o APT::AutoRemove::RecommendsImportant=false; \ + apt-get dist-clean; \ + \ + cd /; \ + rm -r /usr/src/ruby; \ +# verify we have no "ruby" packages installed + if dpkg -l | grep -i ruby; then exit 1; fi; \ + [ "$(command -v ruby)" = '/usr/local/bin/ruby' ]; \ +# rough smoke test + ruby --version; \ + gem --version; \ + bundle --version + +# don't create ".bundle" in all our apps +ENV GEM_HOME /usr/local/bundle +ENV BUNDLE_SILENCE_ROOT_WARNING=1 \ + BUNDLE_APP_CONFIG="$GEM_HOME" +ENV PATH $GEM_HOME/bin:$PATH +RUN set -eux; \ + mkdir "$GEM_HOME"; \ +# adjust permissions of GEM_HOME for running "gem install" as an arbitrary user + chmod 1777 "$GEM_HOME" + +CMD [ "irb" ] diff --git a/versions.json b/versions.json index 6d870dc03..e54b2d910 100644 --- a/versions.json +++ b/versions.json @@ -208,5 +208,82 @@ }, "version": "1.28.2" } + }, + "4.1": null, + "4.1-rc": { + "version": "4.1.0-preview1", + "date": "2026-10-12", + "post": "/en/news/2026/10/12/ruby-4-1-0-preview1-released/", + "tag": "v4.1.0-preview1", + "stats": { + "files_changed": 6116, + "insertions": 311387, + "deletions": 219997 + }, + "url": { + "gz": "https://cache.ruby-lang.org/pub/ruby/4.1/ruby-4.1.0-preview1.tar.gz", + "zip": "https://cache.ruby-lang.org/pub/ruby/4.1/ruby-4.1.0-preview1.zip", + "xz": "https://cache.ruby-lang.org/pub/ruby/4.1/ruby-4.1.0-preview1.tar.xz" + }, + "size": { + "gz": 26550186, + "zip": 32429495, + "xz": 20218640 + }, + "sha1": { + "gz": "4f04a63c2e65945a4f4f7a6d1372783b60e68c5a", + "zip": "199cf5247f7fc55ff225b3fe6928a39a522000d0", + "xz": "3e6c6919bbdb178fd7d6210e3e960889094fac3c" + }, + "sha256": { + "gz": "fb530bb88e90de3ae91c1310a27ae090e6bd989b8726de50ef12a890a85b88ef", + "zip": "2f1ea85203801c24e64ddf02fc2600f582a2544ef8c84d198111e56b0873b125", + "xz": "b81f20bf2bc72aa360785eb77ffa0c9f15343ac7316637fbf347500fc3e2e3a8" + }, + "sha512": { + "gz": "f5628830685d0ce4ffb26294089c31c452e2e5a0bdcc6a5e0c670f335e52fb33eaaea7df3b834778db1fdde89cd2656d94743f6efa672c3bff6e89d64d5b7539", + "zip": "fd32a7b544ec73f0e642202531170bf8fa4454b2c7ff069748b2bf8e530fc8ae4124572e570c4c56606cc90aeeb723d35cab152978b28ee36b4bb06c798529df", + "xz": "b58bc71a8734ceb38c9c301e0201ecd28559c97a3b93caa1d49e07ff34d51565b0b6ed98f05be41868cc09513784bd3e8b5340574fec37116a4ffcb218d396e4" + }, + "variants": [ + "trixie", + "slim-trixie", + "bookworm", + "slim-bookworm", + "alpine3.24", + "alpine3.23" + ], + "rust": { + "version": "1.91.1" + }, + "rustup": { + "arches": { + "amd64": { + "glibc": { + "arch": "x86_64-unknown-linux-gnu", + "sha256": "20a06e644b0d9bd2fbdbfd52d42540bdde820ea7df86e92e533c073da0cdd43c", + "url": "https://static.rust-lang.org/rustup/archive/1.28.2/x86_64-unknown-linux-gnu/rustup-init" + }, + "musl": { + "arch": "x86_64-unknown-linux-musl", + "sha256": "e6599a1c7be58a2d8eaca66a80e0dc006d87bbcf780a58b7343d6e14c1605cb2", + "url": "https://static.rust-lang.org/rustup/archive/1.28.2/x86_64-unknown-linux-musl/rustup-init" + } + }, + "arm64v8": { + "glibc": { + "arch": "aarch64-unknown-linux-gnu", + "sha256": "e3853c5a252fca15252d07cb23a1bdd9377a8c6f3efa01531109281ae47f841c", + "url": "https://static.rust-lang.org/rustup/archive/1.28.2/aarch64-unknown-linux-gnu/rustup-init" + }, + "musl": { + "arch": "aarch64-unknown-linux-musl", + "sha256": "a97c8f56d7462908695348dd8c71ea6740c138ce303715793a690503a94fc9a9", + "url": "https://static.rust-lang.org/rustup/archive/1.28.2/aarch64-unknown-linux-musl/rustup-init" + } + } + }, + "version": "1.28.2" + } } }