Some checks failed
CI/CD Pipeline / Manual Action Help (push) Has been skipped
CI/CD Pipeline / Start Dev Containers in Dokploy (push) Has been skipped
CI/CD Pipeline / Quality Gate (push) Failing after 2s
CI/CD Pipeline / Drop and Recreate Dev Database (push) Has been skipped
CI/CD Pipeline / Build and Push Images (push) Has been skipped
CI/CD Pipeline / Deploy Dev in Dokploy (push) Has been skipped
CI/CD Pipeline / Internal Notify (push) Successful in 1s
112 lines
3.2 KiB
Bash
Executable File
112 lines
3.2 KiB
Bash
Executable File
#!/usr/bin/env bash
|
|
|
|
set -euo pipefail
|
|
|
|
TARGET_VERSION="${1:-3.11}"
|
|
IFS="." read -r PYTHON_MAJOR PYTHON_MINOR _ <<< "${TARGET_VERSION}"
|
|
|
|
if [[ -n "${PYTHON_MINOR:-}" ]]; then
|
|
PYTHON_BIN="python${PYTHON_MAJOR}.${PYTHON_MINOR}"
|
|
else
|
|
PYTHON_BIN="python${PYTHON_MAJOR}"
|
|
fi
|
|
|
|
python_matches() {
|
|
local candidate="$1"
|
|
[[ -x "${candidate}" ]] || return 1
|
|
"${candidate}" - "${PYTHON_MAJOR}" "${PYTHON_MINOR:-}" <<'PY'
|
|
import sys
|
|
|
|
expected_major = int(sys.argv[1])
|
|
expected_minor = sys.argv[2]
|
|
if sys.version_info.major != expected_major:
|
|
raise SystemExit(1)
|
|
if expected_minor and sys.version_info.minor != int(expected_minor):
|
|
raise SystemExit(1)
|
|
PY
|
|
}
|
|
|
|
python_has_venv() {
|
|
local candidate="$1"
|
|
"${candidate}" -m venv --help >/dev/null 2>&1
|
|
}
|
|
|
|
print_if_usable() {
|
|
local candidate="$1"
|
|
case "${candidate}" in
|
|
"${PWD}/.venv/"*)
|
|
return 1
|
|
;;
|
|
esac
|
|
if python_matches "${candidate}" && python_has_venv "${candidate}"; then
|
|
printf '%s\n' "${candidate}"
|
|
exit 0
|
|
fi
|
|
}
|
|
|
|
if command -v "${PYTHON_BIN}" >/dev/null 2>&1; then
|
|
print_if_usable "$(command -v "${PYTHON_BIN}")"
|
|
fi
|
|
|
|
TOOLCACHE_DIR="${RUNNER_TOOL_CACHE:-/opt/hostedtoolcache}"
|
|
HOME_DIR="${HOME:-/root}"
|
|
|
|
shopt -s nullglob
|
|
# shellcheck disable=SC2140
|
|
for candidate in \
|
|
"${TOOLCACHE_DIR}"/Python/"${PYTHON_MAJOR}.${PYTHON_MINOR}"*/x64/bin/python \
|
|
"${TOOLCACHE_DIR}"/Python/"${PYTHON_MAJOR}.${PYTHON_MINOR}"*/x64/bin/python3 \
|
|
"${TOOLCACHE_DIR}"/uv-python/cpython-"${PYTHON_MAJOR}.${PYTHON_MINOR}"*/bin/python \
|
|
"${HOME_DIR}"/.local/share/uv/python/cpython-"${PYTHON_MAJOR}.${PYTHON_MINOR}"*/bin/python \
|
|
"${HOME_DIR}"/.cache/uv/python/cpython-"${PYTHON_MAJOR}.${PYTHON_MINOR}"*/bin/python; do
|
|
print_if_usable "${candidate}"
|
|
done
|
|
shopt -u nullglob
|
|
|
|
APT_RUNNER=()
|
|
if [[ "$(id -u)" -ne 0 ]]; then
|
|
APT_RUNNER=(sudo)
|
|
fi
|
|
|
|
export DEBIAN_FRONTEND=noninteractive
|
|
|
|
if "${APT_RUNNER[@]}" apt-get update >&2 \
|
|
&& "${APT_RUNNER[@]}" apt-get install -y "${PYTHON_BIN}" "${PYTHON_BIN}-venv" >&2; then
|
|
print_if_usable "$(command -v "${PYTHON_BIN}")"
|
|
fi
|
|
|
|
install_uv_standalone() {
|
|
if command -v uv >/dev/null 2>&1; then
|
|
command -v uv
|
|
return 0
|
|
fi
|
|
|
|
local uv_dir
|
|
uv_dir="$(mktemp -d)"
|
|
local install_url="https://astral.sh/uv/${UV_VERSION:-0.7.2}/install.sh"
|
|
if ! curl -LsSf "${install_url}" | env UV_INSTALL_DIR="${uv_dir}/bin" sh >&2; then
|
|
curl -LsSf "https://astral.sh/uv/install.sh" | env UV_INSTALL_DIR="${uv_dir}/bin" sh >&2
|
|
fi
|
|
printf '%s\n' "${uv_dir}/bin/uv"
|
|
}
|
|
|
|
UV_BIN="$(install_uv_standalone)"
|
|
UV_PYTHON_INSTALL_DIR="${TOOLCACHE_DIR:-${HOME_DIR}/.cache}/uv-python" \
|
|
"${UV_BIN}" python install "${TARGET_VERSION}" --no-progress >&2
|
|
|
|
UV_PYTHON_CANDIDATE="$(
|
|
UV_PYTHON_INSTALL_DIR="${TOOLCACHE_DIR:-${HOME_DIR}/.cache}/uv-python" \
|
|
"${UV_BIN}" python find "${TARGET_VERSION}" --managed-python
|
|
)"
|
|
print_if_usable "${UV_PYTHON_CANDIDATE}"
|
|
|
|
if "${APT_RUNNER[@]}" apt-get install -y software-properties-common >&2 \
|
|
&& "${APT_RUNNER[@]}" add-apt-repository -y ppa:deadsnakes/ppa >&2 \
|
|
&& "${APT_RUNNER[@]}" apt-get update >&2 \
|
|
&& "${APT_RUNNER[@]}" apt-get install -y "${PYTHON_BIN}" "${PYTHON_BIN}-venv" >&2; then
|
|
print_if_usable "$(command -v "${PYTHON_BIN}")"
|
|
fi
|
|
|
|
printf 'Unable to install a usable Python %s with venv support\n' "${TARGET_VERSION}" >&2
|
|
exit 1
|