diff --git a/Dockerfiles/ubuntu-24.04.dockerfile b/Dockerfiles/ubuntu-24.04.dockerfile index 749ccdb..d6b7229 100644 --- a/Dockerfiles/ubuntu-24.04.dockerfile +++ b/Dockerfiles/ubuntu-24.04.dockerfile @@ -53,7 +53,7 @@ ENV VIRTUAL_ENV=/opt/venv RUN python3 -m venv $VIRTUAL_ENV ENV PATH="$VIRTUAL_ENV/bin:$PATH" RUN python3 -m pip install --upgrade pip setuptools wheel \ - && python3 -m pip install gnureadline boto3 pyyaml pytz minio requests clingo \ + && python3 -m pip install gnureadline boto3 pyyaml pytz minio requests \ && rm -rf ~/.cache # Install AWS CLI v2 (used improve performance of `spack buildcache update-index`). @@ -78,6 +78,11 @@ RUN AWSCLI_ZIP="awscli-exe-linux-$(uname -m).zip" \ && rm -rf /tmp/awscliv2.zip /tmp/awscliv2.zip.sig /tmp/aws "$GNUPGHOME" \ && aws --version +# Spack's optimized clingo (faster than the PyPI wheel); SPACK_COMMIT is v1.2.2. +ARG SPACK_COMMIT=3e19345b6e12f5ff1b874f4059622fc6a1fd804a +COPY scripts/bootstrap-clingo.sh /tmp/bootstrap-clingo.sh +RUN /tmp/bootstrap-clingo.sh "${SPACK_COMMIT}" && rm /tmp/bootstrap-clingo.sh + CMD ["/bin/bash"] ENV NVIDIA_VISIBLE_DEVICES=all \ diff --git a/scripts/bootstrap-clingo.sh b/scripts/bootstrap-clingo.sh new file mode 100755 index 0000000..fcbbe1e --- /dev/null +++ b/scripts/bootstrap-clingo.sh @@ -0,0 +1,46 @@ +#!/bin/sh +# Install Spack's optimized clingo and make it importable by python3. +# Usage: bootstrap-clingo.sh [bootstrap-root] +set -eu + +SPACK_COMMIT="${1:?usage: bootstrap-clingo.sh [bootstrap-root]}" +ROOT_ARG="${2:-/opt/spack-bootstrap}" + +# Spack skips bootstrapping if python3 can already import clingo. +if CLINGO_FILE=$(python3 -c 'import clingo; print(clingo.__file__)' 2>/dev/null); then + echo "error: python3 already imports clingo from $CLINGO_FILE; remove it first" >&2 + exit 1 +fi + +# Spack would reuse a clingo already in the store instead of SPACK_COMMIT's. +if [ -e "$ROOT_ARG/store" ]; then + echo "error: $ROOT_ARG/store already exists; use an empty bootstrap root" >&2 + exit 1 +fi + +# Absolute path, since it ends up in the .pth. +BOOTSTRAP_ROOT=$(mkdir -p "$ROOT_ARG" && CDPATH= cd "$ROOT_ARG" && pwd -P) +# site, not sysconfig: Debian's sysconfig purelib isn't on sys.path before Python 3.10. +SITE_DIR=$(python3 -c 'import site; print(site.getsitepackages()[0])') +SPACK_DIR="$(mktemp -d)" +trap 'rm -rf "$SPACK_DIR"' EXIT + +# Throwaway Spack; the commit only picks which clingo build is installed. +git init -q "$SPACK_DIR" +git -C "$SPACK_DIR" fetch -q --depth 1 https://github.com/spack/spack.git "$SPACK_COMMIT" +git -C "$SPACK_DIR" checkout -q FETCH_HEAD +export SPACK_USER_CONFIG_PATH="$SPACK_DIR/.user" SPACK_USER_CACHE_PATH="$SPACK_DIR/.user" +"$SPACK_DIR/bin/spack" bootstrap root --scope site "$BOOTSTRAP_ROOT" +"$SPACK_DIR/bin/spack" bootstrap disable --scope site spack-install +"$SPACK_DIR/bin/spack" bootstrap now + +# The store started empty, so any match is the clingo just installed. +PY_TAG=$(python3 -c 'import sys; print("cpython-%d%d" % sys.version_info[:2])') +CLINGO_SO=$(find "$BOOTSTRAP_ROOT/store" -name "clingo.${PY_TAG}-*.so") +echo "clingo builds matching ${PY_TAG}: ${CLINGO_SO:-none}" +test -n "$CLINGO_SO" + +mkdir -p "$SITE_DIR" +dirname "$CLINGO_SO" > "$SITE_DIR/spack-clingo.pth" + +python3 -c 'import clingo; print("clingo", clingo.__version__, "from", clingo.__file__)'