Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 2 additions & 0 deletions .devcontainer/post_create_command.sh
Original file line number Diff line number Diff line change
Expand Up @@ -3,3 +3,5 @@ npm install -g @devcontainers/cli
pre-commit install

scripts/create_builder.sh

sudo apt-get update && sudo apt-get install -y shellcheck
5 changes: 5 additions & 0 deletions .pre-commit-config.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -15,3 +15,8 @@ repos:
hooks:
- id: yamlfmt
args: [--mapping, '2', --offset, '2', --sequence, '4']

- repo: https://github.com/jumanjihouse/pre-commit-hooks
rev: 38980559e3a605691d6579f96222c30778e5a69e # 3.0.0
hooks:
- id: shellcheck
12 changes: 12 additions & 0 deletions .shellcheckrc
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
external-sources=true

# Enable all checks as long as it works
# This might create surprises when updating shellcheck and it adds new checks.
# If this becomes annoying we have seletively enable checks
enable=all

# required checks, no reason not to fix them except difficulty and fear to break code
disable=SC2046

# optional checks, fixes might not be easy and better not break the code
disable=SC2292,SC2154,SC2312
12 changes: 6 additions & 6 deletions scripts/build.sh
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
#!/usr/bin/env bash
set -euxo pipefail

if [[ "$#" -lt 1 || "$1" != "--arm64" && "$1" != "--amd64" ]]; then
if [[ "$#" -lt 1 || "${1}" != "--arm64" && "${1}" != "--amd64" ]]; then
echo "Error: First parameter must be --arm64 or --amd64."
exit 1
fi
Expand All @@ -11,11 +11,11 @@ if [ "$#" -lt 2 ]; then
exit 1
fi

ARCH_OPTION="$1"
ARCH_OPTION="${1}"
shift

ARCH="amd64"
if [[ "$ARCH_OPTION" == "--arm64" ]]; then
if [[ "${ARCH_OPTION}" == "--arm64" ]]; then
ARCH="arm64"
fi

Expand All @@ -24,7 +24,7 @@ for LABEL in "$@"; do
LABELS+=("${LABEL}")
done

echo "Building all labels (${LABELS[@]}) for architecture: ${ARCH}"
echo "Building all labels (" "${LABELS[@]}" ") for architecture: ${ARCH}"

# Prepare image names with tags (each tag includes a label and the architecture)
IMAGES=()
Expand All @@ -37,8 +37,8 @@ DEVCONTAINER_CALL="devcontainer build --workspace-folder src/s-core-devcontainer

# Append image names to the build command
for IMAGE in "${IMAGES[@]}"; do
DEVCONTAINER_CALL+=" $IMAGE"
DEVCONTAINER_CALL+=" ${IMAGE}"
done

# Execute the build for the specific architecture
eval "$DEVCONTAINER_CALL --platform linux/${ARCH}"
eval "${DEVCONTAINER_CALL} --platform linux/${ARCH}"
6 changes: 4 additions & 2 deletions scripts/create_builder.sh
Original file line number Diff line number Diff line change
Expand Up @@ -8,14 +8,14 @@ check_proxy_config() {

# Check if HTTP_PROXY is set in environment but not in builder
if [ -n "${HTTP_PROXY:-}" ]; then
if ! echo "$builder_info" | grep -q "HTTP_PROXY=${HTTP_PROXY}"; then
if ! echo "${builder_info}" | grep -q "HTTP_PROXY=${HTTP_PROXY}"; then
return 1
fi
fi

# Check if HTTPS_PROXY is set in environment but not in builder
if [ -n "${HTTPS_PROXY:-}" ]; then
if ! echo "$builder_info" | grep -q "HTTPS_PROXY=${HTTPS_PROXY}"; then
if ! echo "${builder_info}" | grep -q "HTTPS_PROXY=${HTTPS_PROXY}"; then
return 1
fi
fi
Expand All @@ -25,6 +25,8 @@ check_proxy_config() {

# Check if builder exists and has correct proxy configuration
if docker buildx inspect multiarch &>/dev/null; then
# shellcheck disable=SC2310
# it is an optional rule, enabled via --enable all
if ! check_proxy_config; then
echo "Builder 'multiarch' exists but has incorrect proxy configuration. Recreating..."
docker buildx rm multiarch
Expand Down
4 changes: 2 additions & 2 deletions scripts/merge.sh
Original file line number Diff line number Diff line change
Expand Up @@ -23,13 +23,13 @@ done

# Create and push the merged multiarch manifest for each tag; each tag combines all architecture-specific tags into one tag
for LABEL in "${LABELS[@]}"; do
echo "Merging all architectures (${ARCHITECTURES[@]}) into single tag: ${LABEL}"
echo "Merging all architectures (" "${ARCHITECTURES[@]}" ") into single tag: ${LABEL}"

MANIFEST_MERGE_CALL="docker buildx imagetools create -t ghcr.io/eclipse-score/devcontainer:${LABEL}"

for ARCH in "${ARCHITECTURES[@]}"; do
MANIFEST_MERGE_CALL+=" ghcr.io/eclipse-score/devcontainer:${LABEL}-${ARCH}"
done

eval "$MANIFEST_MERGE_CALL"
eval "${MANIFEST_MERGE_CALL}"
done
12 changes: 6 additions & 6 deletions scripts/publish.sh
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
#!/usr/bin/env bash
set -euxo pipefail

if [[ "$#" -lt 1 || "$1" != "--arm64" && "$1" != "--amd64" ]]; then
if [[ "$#" -lt 1 || "${1}" != "--arm64" && "${1}" != "--amd64" ]]; then
echo "Error: First parameter must be --arm64 or --amd64."
exit 1
fi
Expand All @@ -11,11 +11,11 @@ if [ "$#" -lt 2 ]; then
exit 1
fi

ARCH_OPTION="$1"
ARCH_OPTION="${1}"
shift

ARCH="amd64"
if [[ "$ARCH_OPTION" == "--arm64" ]]; then
if [[ "${ARCH_OPTION}" == "--arm64" ]]; then
ARCH="arm64"
fi

Expand All @@ -24,7 +24,7 @@ for LABEL in "$@"; do
LABELS+=("${LABEL}")
done

echo "Building all tags (${LABELS[@]}) for architecture: ${ARCH}"
echo "Building all tags (" "${LABELS[@]}" ") for architecture: ${ARCH}"
# Prepare image names with tags (each tag includes a label and an architecture)
IMAGES=()
for LABEL in "${LABELS[@]}"; do
Expand All @@ -36,8 +36,8 @@ DEVCONTAINER_CALL="devcontainer build --push --workspace-folder src/s-core-devco

# Append image names to the build command
for IMAGE in "${IMAGES[@]}"; do
DEVCONTAINER_CALL+=" $IMAGE"
DEVCONTAINER_CALL+=" ${IMAGE}"
done

# Execute the build and push all tags for the specific architecture
eval "$DEVCONTAINER_CALL --platform linux/${ARCH}"
eval "${DEVCONTAINER_CALL} --platform linux/${ARCH}"
1 change: 0 additions & 1 deletion src/s-core-devcontainer/.devcontainer/Dockerfile
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,5 @@ LABEL dev.containers.features="common"

# Unset proxy variables for all login shells
COPY unset-proxy.sh /etc/profile.d/unset-proxy.sh
RUN chmod +x /etc/profile.d/unset-proxy.sh
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

intentional change?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

yes, because due to the added shebang shellcheck also enforces that the script is executable, which it was not before
image

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

anyway I discovered the script is actually never executed and hence we have #71


RUN userdel -f -r ubuntu
10 changes: 6 additions & 4 deletions src/s-core-devcontainer/.devcontainer/bazel-feature/install.sh
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,8 @@ COPY_TARGET="${FEATURES_DIR}/$(basename "${SCRIPT_DIR%%_*}")"
cp -R "${SCRIPT_DIR}" "${COPY_TARGET}"
rm -f "${COPY_TARGET}/devcontainer-features.env" "${COPY_TARGET}/devcontainer-features-install.sh"

# shellcheck disable=SC2034
# used by apt-get only inside this script
DEBIAN_FRONTEND=noninteractive

# Read tool versions + metadata into environment variables
Expand All @@ -34,7 +36,7 @@ if [ "${ARCHITECTURE}" = "arm64" ]; then
SHA256SUM="${bazelisk_arm64_sha256}"
fi
curl -L "https://github.com/bazelbuild/bazelisk/releases/download/v${bazelisk_version}/bazelisk-${BAZELISK_VARIANT}.deb" -o /tmp/bazelisk.deb
echo "${SHA256SUM} /tmp/bazelisk.deb" | sha256sum -c - || exit -1
echo "${SHA256SUM} /tmp/bazelisk.deb" | sha256sum -c - || exit 1
apt-get install -y --no-install-recommends --fix-broken /tmp/bazelisk.deb
rm /tmp/bazelisk.deb

Expand All @@ -60,7 +62,7 @@ if [ "${ARCHITECTURE}" = "arm64" ]; then
SHA256SUM="${buildifier_arm64_sha256}"
fi
curl -L "https://github.com/bazelbuild/buildtools/releases/download/v${buildifier_version}/buildifier-linux-${BUILDIFIER_VARIANT}" -o /usr/local/bin/buildifier
echo "${SHA256SUM} /usr/local/bin/buildifier" | sha256sum -c - || exit -1
echo "${SHA256SUM} /usr/local/bin/buildifier" | sha256sum -c - || exit 1
chmod +x /usr/local/bin/buildifier

# Starlark Language Server, directly from GitHub (apparently no APT repository available)
Expand All @@ -71,7 +73,7 @@ if [ "${ARCHITECTURE}" = "arm64" ]; then
SHA256SUM="${starpls_arm64_sha256}"
fi
curl -L "https://github.com/withered-magic/starpls/releases/download/v${starpls_version}/starpls-linux-${STARPLS_VARIANT}" -o /usr/local/bin/starpls
echo "${SHA256SUM} /usr/local/bin/starpls" | sha256sum -c - || exit -1
echo "${SHA256SUM} /usr/local/bin/starpls" | sha256sum -c - || exit 1
chmod +x /usr/local/bin/starpls

# Code completion for C++ code of Bazel projects
Expand All @@ -83,7 +85,7 @@ SHA256SUM="${bazel_compile_commands_amd64_sha256}"
if [ "${ARCHITECTURE}" = "arm64" ]; then
SHA256SUM="${bazel_compile_commands_arm64_sha256}"
fi
echo "${SHA256SUM} /tmp/bazel-compile-commands.deb" | sha256sum -c - || exit -1
echo "${SHA256SUM} /tmp/bazel-compile-commands.deb" | sha256sum -c - || exit 1
apt-get install -y --no-install-recommends --fix-broken /tmp/bazel-compile-commands.deb
rm /tmp/bazel-compile-commands.deb

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -3,17 +3,19 @@ set -eo pipefail

. /devcontainer/features/bazel/bazel_setup.sh || true

if [ -f .bazelversion ] && [ "$(cat .bazelversion)" != "$INSTALLED_BAZEL_VERSION" ]; then
if [ -f .bazelversion ] && [ "$(cat .bazelversion)" != "${INSTALLED_BAZEL_VERSION}" ]; then
# Pre-install the matching Bazel version, setup the bash command completion
USE_BAZEL_VERSION=$(cat .bazelversion)

min_bazel_version_for_bash_option="8.4.0"
bash=""
if [ "$(printf '%s\n' "$min_bazel_version_for_bash_option" "$USE_BAZEL_VERSION" | sort -V | head -n1)" = "$min_bazel_version_for_bash_option" ]; then
if [ "$(printf '%s\n' "${min_bazel_version_for_bash_option}" "${USE_BAZEL_VERSION}" | sort -V | head -n1)" = "${min_bazel_version_for_bash_option}" ]; then
bash="bash"
fi

# shellcheck disable=SC2248
# without quotes is intentional: $bash might be empty and then an empty string is passed to the command, which will fail
bazel help completion ${bash} > /tmp/bazel-complete.bash
sudo mv /tmp/bazel-complete.bash /etc/bash_completion.d/bazel-complete.bash
echo "INSTALLED_BAZEL_VERSION=$USE_BAZEL_VERSION" | sudo tee /devcontainer/features/bazel/bazel_setup.sh
echo "INSTALLED_BAZEL_VERSION=${USE_BAZEL_VERSION}" | sudo tee /devcontainer/features/bazel/bazel_setup.sh
fi
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@ PRE_COMMIT_CONFIG_FILE=".pre-commit-config.yaml"
if [[ -f "${PRE_COMMIT_CONFIG_FILE}" ]]
then
echo "Pre-commit configuration found (${PRE_COMMIT_CONFIG_FILE})"
$PIPX_BIN_DIR/pre-commit install
"${PIPX_BIN_DIR}/pre-commit" install
else
echo "No pre-commit configuration found (${PRE_COMMIT_CONFIG_FILE})"
echo "Skipping pre-commit hook's installation"
Expand Down
16 changes: 10 additions & 6 deletions src/s-core-devcontainer/.devcontainer/s-core-local/install.sh
Original file line number Diff line number Diff line change
Expand Up @@ -10,13 +10,13 @@ COPY_TARGET="${FEATURES_DIR}/$(basename "${SCRIPT_DIR%%_*}")"
cp -R "${SCRIPT_DIR}" "${COPY_TARGET}"
rm -f "${COPY_TARGET}/devcontainer-features.env" "${COPY_TARGET}/devcontainer-features-install.sh"

# shellcheck disable=SC2034
# used by apt-get only inside this script
DEBIAN_FRONTEND=noninteractive

# Read tool versions + metadata into environment variables
. /devcontainer/features/s-core-local/versions.sh /devcontainer/features/s-core-local/versions.yaml

ARCHITECTURE=$(dpkg --print-architecture)

apt-get update

# Unminimize the image to include standard packages like man pages
Expand All @@ -27,6 +27,9 @@ apt-get install -y man-db manpages manpages-dev manpages-posix manpages-posix-de
# Container build dependencies are not pinned, since they are removed anyway after container creation.
apt-get install apt-transport-https -y

# static code anylysis for shell scripts
apt-get install -y shellcheck="${shellcheck_version}*"

# GraphViz
# The Ubuntu Noble package of GraphViz
apt-get install -y graphviz="${graphviz_version}*"
Expand All @@ -40,16 +43,17 @@ apt-get install -y git-lfs
apt-get install -y gh

# Python, via APT
apt-get install -y python${python_version} python3-pip python3-venv
apt-get install -y "python${python_version}" python3-pip python3-venv
# The following packages correspond to the list of packages installed by the
# devcontainer feature "python" (cf. https://github.com/devcontainers/features/tree/main/src/python )
apt-get install -y flake8 python3-autopep8 black python3-yapf mypy pydocstyle pycodestyle bandit pipenv virtualenv python3-pytest pylint

# OpenJDK 21, via APT
# Set JAVA_HOME environment variable system-wide, since some tools rely on it (e.g., Bazel's rules_java)
apt-get install -y ca-certificates-java openjdk-21-jdk-headless="${openjdk_21_version}*"
export JAVA_HOME="$(dirname $(dirname $(realpath $(which javac))))"
echo "export JAVA_HOME=\"$(dirname $(dirname $(realpath $(which javac))))\"" > /etc/profile.d/java_home.sh
JAVA_HOME="$(dirname $(dirname $(realpath $(command -v javac))))"
export JAVA_HOME
echo -e "JAVA_HOME=${JAVA_HOME}\nexport JAVA_HOME" > /etc/profile.d/java_home.sh

# qemu-system-arm
apt-get install -y --no-install-recommends --fix-broken qemu-system-arm="${qemu_system_arm_version}*"
Expand All @@ -60,7 +64,7 @@ apt-get install -y sshpass="${sshpass_version}*"
# additional developer tools
apt-get install -y gdb="${gdb_version}*"

apt-get install -y valgrind=1:${valgrind_version}*
apt-get install -y valgrind="1:${valgrind_version}*"

# Bash completion for rust tooling
rustup completions bash rustup >> /etc/bash_completion.d/rustup.bash
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -5,9 +5,11 @@ set -euo pipefail
. /devcontainer/features/s-core-local/versions.sh /devcontainer/features/s-core-local/versions.yaml

# pre-commit, it is available via $PATH in login shells, but not in non-login shells
check "validate pre-commit is working and has the correct version" bash -c "$PIPX_BIN_DIR/pre-commit --version | grep '4.5.1'"
check "validate pre-commit is working and has the correct version" bash -c "${PIPX_BIN_DIR}/pre-commit --version | grep '4.5.1'"

# Common tooling
check "validate shellcheck is working and has the correct version" bash -c "shellcheck --version | grep '${shellcheck_version}'"

# For an unknown reason, dot -V reports on Ubuntu Noble a version 2.43.0, while the package has a different version.
# Hence, we have to work around that.
check "validate graphviz is working" bash -c "dot -V"
Expand All @@ -32,7 +34,7 @@ check "validate pylint is working" bash -c "pylint --version"

# OpenJDK
check "validate java is working and has the correct version" bash -c "java -version 2>&1 | grep '${openjdk_21_version}'"
check "validate JAVA_HOME is set correctly" bash -c 'echo $JAVA_HOME | xargs readlink -f | grep "java-21-openjdk"'
check "validate JAVA_HOME is set correctly" bash -c "echo ${JAVA_HOME} | xargs readlink -f | grep \"java-21-openjdk\""

# additional developer tools
check "validate gdb is working and has the correct version" bash -c "gdb --version | grep '${gdb_version}'"
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -12,12 +12,12 @@ fi
# if /tmp/yq does not exist, download yq
if [ ! -f /tmp/yq ]; then
curl -L "https://github.com/mikefarah/yq/releases/download/${VERSION}/yq_linux_${ARCHITECTURE}" -o /tmp/yq
echo "${SHA256_FIELD} /tmp/yq" | sha256sum -c - || exit -1
echo "${SHA256_FIELD} /tmp/yq" | sha256sum -c - || exit 1
chmod +x /tmp/yq
fi

# Read tool versions and metadata into environment variables
export $(/tmp/yq eval '.. | select((tag == "!!map" or tag == "!!seq") | not) | (path | join("_")) + "=" + .' $1 | awk '!/=$/{print }' | xargs)
export $(/tmp/yq eval '.. | select((tag == "!!map" or tag == "!!seq") | not) | (path | join("_")) + "=" + .' "$1" | awk '!/=$/{print }' | xargs)

# Clean up
rm -f /tmp/yq
trap 'rm -f /tmp/yq' EXIT
Original file line number Diff line number Diff line change
Expand Up @@ -29,5 +29,8 @@ gh:
openjdk_21:
version: 21.0.10

shellcheck:
version: 0.9.0

valgrind:
version: 3.22.0
3 changes: 2 additions & 1 deletion src/s-core-devcontainer/.devcontainer/unset-proxy.sh
100644 → 100755
Original file line number Diff line number Diff line change
@@ -1,7 +1,8 @@
#!/bin/bash
# /etc/profile.d/unset-proxy.sh
# Unset proxy variables for all login shells if they are empty
for var in HTTP_PROXY HTTPS_PROXY http_proxy https_proxy NO_PROXY no_proxy; do
if [ -z "${!var}" ]; then
unset $var
unset "${var}"
fi
done
3 changes: 0 additions & 3 deletions src/s-core-devcontainer/test-project/test.sh
Original file line number Diff line number Diff line change
@@ -1,9 +1,6 @@
#!/bin/bash
set -euo pipefail

SCRIPT_PATH=$(readlink -f "$0")
SCRIPT_DIR=$(dirname -- "${SCRIPT_PATH}")

source "test-utils.sh" vscode

# C++ tooling
Expand Down