#!/usr/bin/env bash set -euo pipefail SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)" readonly SCRIPT_DIR PSYSH_ROOT="$(cd "${SCRIPT_DIR}/.." && pwd)" readonly PSYSH_ROOT readonly DEFAULT_PROJECTS_TIER1=("laravel-tinker" "laravel-web-tinker") readonly DEFAULT_PROJECTS_ALL=("laravel-tinker" "laravel-web-tinker" "drush" "codeception" "magerun2" "cakephp-repl" "composer-repl-lib" "bdf-prime-shell") readonly OVERRIDE_VERSION="${DOWNSTREAM_PSYSH_VERSION:-0.12.99}" usage() { cat <<'USAGE' Usage: scripts/test-downstream scripts/test-downstream tier1 scripts/test-downstream all scripts/test-downstream --list Project IDs: laravel-tinker laravel-web-tinker drush codeception magerun2 cakephp-repl composer-repl-lib bdf-prime-shell USAGE } list_projects() { printf '%s\n' "${DEFAULT_PROJECTS_ALL[@]}" } retry() { local -r attempts="$1" shift local try=1 until "$@"; do if [[ "${try}" -ge "${attempts}" ]]; then echo " FAILED after ${attempts} attempts: $*" >&2 return 1 fi try=$((try + 1)) echo " Retrying (${try}/${attempts}): $*" >&2 sleep 2 done } version_lt() { [[ "$(printf '%s\n%s\n' "$1" "$2" | sort -V | head -n 1)" != "$2" ]] } resolve_project() { case "$1" in laravel-tinker) repo="laravel/tinker" ref="2.x" test_command="vendor/bin/phpunit" min_php="7.2" ;; laravel-web-tinker) repo="spatie/laravel-web-tinker" ref="main" test_command="composer test" min_php="8.2" ;; drush) repo="drush-ops/drush" ref="14.x" test_command="composer unit" min_php="8.3" ;; codeception) repo="Codeception/Codeception" ref="main" test_command="./codecept run unit" min_php="8.2" ;; magerun2) repo="netz98/n98-magerun2" ref="develop" test_command="vendor/bin/phpunit" min_php="8.0" ;; cakephp-repl) repo="cakephp/repl" ref="master" test_command="vendor/bin/phpunit" min_php="7.2" ;; composer-repl-lib) repo="ramsey/composer-repl-lib" ref="main" test_command="vendor/bin/phpunit" min_php="8.1" ;; bdf-prime-shell) repo="b2pweb/bdf-prime-shell" ref="master" test_command="vendor/bin/phpunit" min_php="7.1" ;; *) echo "Unknown project ID: $1" >&2 return 1 ;; esac } run_one_project() { local -r project="$1" local repo ref test_command min_php resolve_project "${project}" local -r current_php="$(php -r 'echo PHP_MAJOR_VERSION.".".PHP_MINOR_VERSION;')" if version_lt "${current_php}" "${min_php}"; then echo echo "==> ${project}" echo " repo: ${repo} (${ref})" echo " test: ${test_command}" echo " skipped: requires PHP >= ${min_php}, current PHP is ${current_php}" return 0 fi local -r psysh_path="${PSYSH_PATH:-${PSYSH_ROOT}}" local -r tmp_dir="$(mktemp -d)" local -r work_dir="${tmp_dir}/${project}" local -r repo_config_json="{\"type\":\"path\",\"url\":\"${psysh_path}\",\"options\":{\"symlink\":true,\"versions\":{\"psy/psysh\":\"${OVERRIDE_VERSION}\"}}}" echo echo "==> ${project}" echo " repo: ${repo} (${ref})" echo " test: ${test_command}" ( if [[ "${DOWNSTREAM_KEEP_TMP:-0}" == "1" ]]; then echo " temp dir preserved: ${tmp_dir}" else # shellcheck disable=SC2064 trap "rm -rf '${tmp_dir}'" EXIT fi retry 3 git clone --depth 1 --branch "${ref}" "https://github.com/${repo}.git" "${work_dir}" cd "${work_dir}" export COMPOSER_CACHE_DIR="${COMPOSER_CACHE_DIR:-${tmp_dir}/composer-cache}" mkdir -p "${COMPOSER_CACHE_DIR}" composer config repositories.psysh "${repo_config_json}" if [[ -f composer.lock ]]; then retry 3 composer update psy/psysh --with-all-dependencies --no-interaction --no-progress else retry 3 composer update --no-interaction --no-progress fi ${test_command} ) } main() { local -a projects=() if [[ $# -ne 1 ]]; then usage exit 1 fi case "$1" in --list) list_projects return ;; tier1) projects=("${DEFAULT_PROJECTS_TIER1[@]}") ;; all) projects=("${DEFAULT_PROJECTS_ALL[@]}") ;; -h|--help) usage return ;; *) projects=("$1") ;; esac for project in "${projects[@]}"; do run_one_project "${project}" done } main "$@"