diff --git a/.githooks/pre-commit b/.githooks/pre-commit index 5387bd9f3..b29cef04d 100755 --- a/.githooks/pre-commit +++ b/.githooks/pre-commit @@ -11,17 +11,6 @@ set -euo pipefail # we need to resolve it before we can make path relative to this script's file. . "$(dirname "$(readlink -f "${BASH_SOURCE[0]}")")/../scripts/lib.sh" -function command_exists() { - bin_name=$(basename "$1") - - if command -v "$1" &> /dev/null; then - return 0 - fi - - warn "$bin_name CLI was not found. Ignoring it..." - return 1 -} - files=$(git diff --cached --name-only --diff-filter=ACMR | sed 's| |\\ |g') if [[ -z "$files" ]]; then @@ -29,26 +18,19 @@ if [[ -z "$files" ]]; then exit 0 fi -if command_exists typos; then - echo "$files" | step xargs typos -fi +echo "$files" | step xargs typos -if command_exists npx; then - echo "$files" | step xargs npx prettier --ignore-unknown --write -fi +./scripts/shellcheck.sh -if command_exists cargo; then - # `rustfmt` doesn't ignore non-rust files automatically - rust_files=$(echo "$files" | { grep -E '\.rs$' || true; }) +echo "$files" | step xargs npx prettier --ignore-unknown --write - if [[ -n "$rust_files" ]]; then - echo "$rust_files" | step xargs cargo fmt --manifest-path native/Cargo.toml -- - fi +# `rustfmt` doesn't ignore non-rust files automatically +rust_files=$(echo "$files" | { grep -E '\.rs$' || true; }) +if [[ -n "$rust_files" ]]; then + echo "$rust_files" | step xargs cargo fmt --manifest-path native/Cargo.toml -- fi -if command_exists mix; then - echo "$files" | step xargs mix format -fi +echo "$files" | step xargs mix format # Add the modified/prettified files to staging echo "$files" | step xargs git add diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml index 99402ba14..aba462a7a 100644 --- a/.github/workflows/ci.yml +++ b/.github/workflows/ci.yml @@ -41,6 +41,14 @@ jobs: - uses: actions/checkout@v5 - uses: crate-ci/typos@master + shellcheck: + name: Shellcheck + runs-on: ubuntu-latest + steps: + - uses: actions/checkout@v5 + - run: ./scripts/install/shellcheck.sh + - run: ./scripts/shellcheck.sh + cargo: name: Rust Linting and Unit Tests runs-on: ubuntu-latest diff --git a/docker/app/purge-cache b/docker/app/purge-cache index f16ae4775..5cd1608a6 100755 --- a/docker/app/purge-cache +++ b/docker/app/purge-cache @@ -1,4 +1,5 @@ #!/usr/bin/env sh +# shellcheck disable=SC2034 # Run your custom purge command here. # diff --git a/docker/app/run-test b/docker/app/run-test index f845890f1..ccd69995a 100755 --- a/docker/app/run-test +++ b/docker/app/run-test @@ -11,10 +11,10 @@ mix format --check-formatted # Sleep to allow OpenSearch to finish initializing # if it's not done doing whatever it does yet -echo -n "Waiting for OpenSearch" +printf "Waiting for OpenSearch" until wget -qO - opensearch:9200; do - echo -n "." + printf "." sleep 2 done diff --git a/post-receive b/post-receive deleted file mode 100755 index c224455e5..000000000 --- a/post-receive +++ /dev/null @@ -1,48 +0,0 @@ -#!/usr/bin/env bash - -# Set up environment -source ~/bin/philomena-env - -read oldrev newrev ref -echo "Updating $oldrev -> $newrev ($ref)" - -# Clear variable set to '.' so git commands don't complain -unset GIT_DIR - -cd ~/philomena - -die() { - echo "$*" 1>&2 - exit 1 -} - -if git diff --name-only $oldrev $newrev | grep -Ee "^mix.(exs|lock)"; then - echo "Fetching deps" - mix deps.get || die "mix failed to update" -fi - -# Compile assets -if git diff --name-only $oldrev $newrev | grep "^assets/"; then - echo "Compiling assets" - npm install --prefix ./assets || die "assets install failed" - npm run deploy --prefix ./assets - mix phx.digest || die "assets compile failed" -fi - -echo "Building release" -mix release --overwrite || die "failed to generate release" - -# Run migrations -if git diff --name-only $oldrev $newrev | grep "^priv/repo/migrations"; then - echo "Running database migrations" - _build/prod/rel/philomena/bin/philomena eval "Philomena.Release.migrate()" || die "ecto.migrate failed" -fi - -# Include a task to restart your running appserver instances here. -# -# In general, you should have many app instances configured on different -# ports using the PORT environment variable, so as to allow you to roll -# releases and deploy new code with no visible downtime. -# -# You can use a reverse proxy like haproxy or nginx to load balance between -# different server instances automatically. diff --git a/scripts/install/shellcheck.sh b/scripts/install/shellcheck.sh new file mode 100755 index 000000000..395f7c19f --- /dev/null +++ b/scripts/install/shellcheck.sh @@ -0,0 +1,10 @@ +#!/usr/bin/env bash + +set -euo pipefail + +. "$(dirname "${BASH_SOURCE[0]}")/../lib.sh" + +version=0.11.0 + +fetch https://github.com/koalaman/shellcheck/releases/download/v$version/shellcheck-v$version.linux.x86_64.tar.xz \ + | step tar -xJf - -C /usr/local/bin --strip-components=1 shellcheck-v$version/shellcheck diff --git a/scripts/lib.sh b/scripts/lib.sh index 1ab0d4800..c78192d2e 100644 --- a/scripts/lib.sh +++ b/scripts/lib.sh @@ -80,3 +80,15 @@ function colorize_command { # and we use bash >= v5. If this ever becomes a problem, you know the why. echo -e "\033[1;32m${program}\033[0m ${args[*]}" } + +# `curl` wrapper with better defaults for non-interactive scripts +function fetch { + step curl \ + --fail \ + --silent \ + --show-error \ + --location \ + --retry 5 \ + --retry-all-errors \ + "$@" +} diff --git a/scripts/shellcheck.sh b/scripts/shellcheck.sh new file mode 100755 index 000000000..022d11aa5 --- /dev/null +++ b/scripts/shellcheck.sh @@ -0,0 +1,23 @@ +#!/usr/bin/env bash +# +# This script runs shellcheck on all shell scripts in the repository. +# It exists because shellcheck doesn't attempt to automatically discover +# shell scripts and requires specifying the file paths explicitly. +# +# This is somewhat understandable, because not all shell scripts use +# obvious file extensions like `.sh`. So, we discover such files by +# checking if they have one of the expected shebang lines at the beginning. + +set -euo pipefail + +. "$(dirname "${BASH_SOURCE[0]}")/lib.sh" + +function shell_script_files { + git ls-files "*.sh" + git grep --files-with-matches '^#!/usr/bin/env bash' + git grep --files-with-matches '^#!/usr/bin/env sh' +} + +mapfile -t files < <(shell_script_files "$@" | sort -u) + +step shellcheck --source-path SCRIPTDIR "${files[@]}"