Skip to content

Use template "Check Shell" workflow (Task) #214

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 8 commits into from
Jul 30, 2021
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
54 changes: 49 additions & 5 deletions .editorconfig
Original file line number Diff line number Diff line change
@@ -1,16 +1,60 @@
# http://editorconfig.org

root = true
# Source: https://github.com/arduino/tooling-project-assets/blob/main/workflow-templates/assets/general/.editorconfig
# See: https://editorconfig.org/
# The formatting style defined in this file is the official standardized style to be used in all Arduino Tooling
# projects and should not be modified.
# Note: indent style for each file type is defined even when it matches the universal config in order to make it clear
# that this type has an official style.

[*]
charset = utf-8
end_of_line = lf
indent_size = 2
indent_style = space
insert_final_newline = true
trim_trailing_whitespace = true

[*.go]
[*.{adoc,asc,asciidoc}]
indent_size = 2
indent_style = space

[*.{bash,sh}]
indent_size = 2
indent_style = space

[*.{c,cc,cp,cpp,cxx,h,hh,hpp,hxx,ii,inl,ino,ixx,pde,tpl,tpp,txx}]
indent_size = 2
indent_style = space

[*.{go,mod}]
indent_style = tab

[*.java]
indent_size = 2
indent_style = space

[*.{js,jsx,json,jsonc,json5,ts,tsx}]
indent_size = 2
indent_style = space

[*.{md,mdx,mkdn,mdown,markdown}]
indent_size = unset
indent_style = space

[*.proto]
indent_size = 2
indent_style = space

[*.py]
indent_size = 4
indent_style = space

[*.{yml,yaml}]
[*.svg]
indent_size = 2
indent_style = space

[*.{yaml,yml}]
indent_size = 2
indent_style = space

[.gitmodules]
indent_style = tab
6 changes: 0 additions & 6 deletions .github/workflows/check-formatting.yml
Original file line number Diff line number Diff line change
Expand Up @@ -34,12 +34,6 @@ jobs:
repo-token: ${{ secrets.GITHUB_TOKEN }}
version: 3.x

- name: Check shell script formatting
# https://github.com/mvdan/sh
run: |
docker run --volume "$GITHUB_WORKSPACE/libraries/spell-check":/mnt --workdir /mnt mvdan/shfmt:latest -w .
git diff --color --exit-code

- name: Check documentation formatting
run: task docs:check-formatting

Expand Down
147 changes: 147 additions & 0 deletions .github/workflows/check-shell-task.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,147 @@
# Source: https://github.com/arduino/tooling-project-assets/blob/main/workflow-templates/check-shell-task.md
name: Check Shell Scripts

# See: https://docs.github.com/en/actions/reference/events-that-trigger-workflows
on:
push:
paths:
- ".github/workflows/check-shell-task.ya?ml"
- "Taskfile.ya?ml"
- "**/.editorconfig"
- "**.bash"
- "**.sh"
pull_request:
paths:
- ".github/workflows/check-shell-task.ya?ml"
- "Taskfile.ya?ml"
- "**/.editorconfig"
- "**.bash"
- "**.sh"
schedule:
# Run every Tuesday at 8 AM UTC to catch breakage caused by tool changes.
- cron: "0 8 * * TUE"
workflow_dispatch:
repository_dispatch:

jobs:
lint:
name: ${{ matrix.configuration.name }}
runs-on: ubuntu-latest

env:
# See: https://github.com/koalaman/shellcheck/releases/latest
SHELLCHECK_RELEASE_ASSET_SUFFIX: .linux.x86_64.tar.xz

strategy:
fail-fast: false

matrix:
configuration:
- name: Generate problem matcher output
# ShellCheck's "gcc" output format is required for annotated diffs, but inferior for humans reading the log.
format: gcc
# The other matrix job is used to set the result, so this job is configured to always pass.
continue-on-error: true
- name: ShellCheck
# ShellCheck's "tty" output format is most suitable for humans reading the log.
format: tty
continue-on-error: false

steps:
- name: Set environment variables
run: |
# See: https://docs.github.com/en/actions/reference/workflow-commands-for-github-actions#setting-an-environment-variable
echo "INSTALL_PATH=${{ runner.temp }}/shellcheck" >> "$GITHUB_ENV"

- name: Checkout repository
uses: actions/checkout@v2

- name: Install Task
uses: arduino/setup-task@v1
with:
repo-token: ${{ secrets.GITHUB_TOKEN }}
version: 3.x

- name: Download latest ShellCheck release binary package
id: download
uses: MrOctopus/[email protected]
with:
repository: koalaman/shellcheck
excludes: prerelease, draft
asset: ${{ env.SHELLCHECK_RELEASE_ASSET_SUFFIX }}
target: ${{ env.INSTALL_PATH }}

- name: Install ShellCheck
run: |
cd "${{ env.INSTALL_PATH }}"
tar --extract --file="${{ steps.download.outputs.name }}"
EXTRACTION_FOLDER="$(basename "${{ steps.download.outputs.name }}" "${{ env.SHELLCHECK_RELEASE_ASSET_SUFFIX }}")"
# Add installation to PATH:
# See: https://docs.github.com/en/actions/reference/workflow-commands-for-github-actions#adding-a-system-path
echo "${{ env.INSTALL_PATH }}/$EXTRACTION_FOLDER" >> "$GITHUB_PATH"

- name: Run ShellCheck
uses: liskin/gh-problem-matcher-wrap@v1
continue-on-error: ${{ matrix.configuration.continue-on-error }}
with:
linters: gcc
run: task --silent shell:check SHELLCHECK_FORMAT=${{ matrix.configuration.format }}

formatting:
runs-on: ubuntu-latest

steps:
- name: Set environment variables
run: |
# See: https://docs.github.com/en/actions/reference/workflow-commands-for-github-actions#setting-an-environment-variable
echo "SHFMT_INSTALL_PATH=${{ runner.temp }}/shfmt" >> "$GITHUB_ENV"

- name: Checkout repository
uses: actions/checkout@v2

- name: Install Task
uses: arduino/setup-task@v1
with:
repo-token: ${{ secrets.GITHUB_TOKEN }}
version: 3.x

- name: Download shfmt
id: download
uses: MrOctopus/[email protected]
with:
repository: mvdan/sh
excludes: prerelease, draft
asset: _linux_amd64
target: ${{ env.SHFMT_INSTALL_PATH }}

- name: Install shfmt
run: |
# Executable permissions of release assets are lost
chmod +x "${{ env.SHFMT_INSTALL_PATH }}/${{ steps.download.outputs.name }}"
# Standardize binary name
mv "${{ env.SHFMT_INSTALL_PATH }}/${{ steps.download.outputs.name }}" "${{ env.SHFMT_INSTALL_PATH }}/shfmt"
# Add installation to PATH:
# See: https://docs.github.com/en/actions/reference/workflow-commands-for-github-actions#adding-a-system-path
echo "${{ env.SHFMT_INSTALL_PATH }}" >> "$GITHUB_PATH"

- name: Format shell scripts
run: task --silent shell:format

- name: Check formatting
run: git diff --color --exit-code

executable:
runs-on: ubuntu-latest

steps:
- name: Checkout repository
uses: actions/checkout@v2

- name: Install Task
uses: arduino/setup-task@v1
with:
repo-token: ${{ secrets.GITHUB_TOKEN }}
version: 3.x

- name: Check for non-executable scripts
run: task --silent shell:check-mode
28 changes: 0 additions & 28 deletions .github/workflows/lint-shell.yml

This file was deleted.

1 change: 1 addition & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,7 @@
[![Docs Status](https://github.com/arduino/arduino-lint/workflows/Publish%20documentation/badge.svg)](https://github.com/arduino/arduino-lint/actions?workflow=Publish+documentation)
[![Codecov](https://codecov.io/gh/arduino/arduino-lint/branch/main/graph/badge.svg?token=nprqPQMbdh)](https://codecov.io/gh/arduino/arduino-lint)
[![Check General Formatting status](https://github.com/arduino/arduino-lint/actions/workflows/check-general-formatting-task.yml/badge.svg)](https://github.com/arduino/arduino-lint/actions/workflows/check-general-formatting-task.yml)
[![Check Shell Scripts status](https://github.com/arduino/arduino-lint/actions/workflows/check-shell-task.yml/badge.svg)](https://github.com/arduino/arduino-lint/actions/workflows/check-shell-task.yml)
[![Check Certificates status](https://github.com/arduino/arduino-lint/actions/workflows/check-certificates.yml/badge.svg)](https://github.com/arduino/arduino-lint/actions/workflows/check-certificates.yml)

**Arduino Lint** is a command line tool that checks for common problems in [Arduino](https://www.arduino.cc/) projects:
Expand Down
76 changes: 63 additions & 13 deletions Taskfile.yml
Original file line number Diff line number Diff line change
Expand Up @@ -46,6 +46,7 @@ tasks:
- task: config:check
- task: general:check-formatting
- task: check-spelling
- task: shell:check-mode

lint:
desc: Lint all files
Expand Down Expand Up @@ -266,24 +267,73 @@ tasks:
cmds:
- npx {{ .PRETTIER }} --write "**/*.md"

shell:lint:
desc: Lint shell scripts
# Source: https://github.com/arduino/tooling-project-assets/blob/main/workflow-templates/assets/check-shell-task/Taskfile.yml
shell:check:
desc: Check for problems with shell scripts
cmds:
# https://github.com/koalaman/shellcheck
- |
shopt -s globstar # Needed to check all scripts recursively.
shellcheck ./**/*.sh

shell:check-formatting:
desc: Format shell scripts
if ! which shellcheck &>/dev/null; then
echo "shellcheck not installed or not in PATH. Please install: https://github.com/koalaman/shellcheck#installing"
exit 1
fi
- |
# There is something odd about shellcheck that causes the task to always exit on the first fail, despite any
# measures that would prevent this with any other command. So it's necessary to call shellcheck only once with
# the list of script paths as an argument. This could lead to exceeding the maximum command length on Windows if
# the repository contained a large number of scripts, but it's unlikely to happen in reality.
shellcheck \
--format={{default "tty" .SHELLCHECK_FORMAT}} \
$(
# The odd method for escaping . in the regex is required for windows compatibility because mvdan.cc/sh gives
# \ characters special treatment on Windows in an attempt to support them as path separators.
find . \
-path ".git" -prune -or \
\( \
-regextype posix-extended \
-regex '.*[.](bash|sh)' -and \
-type f \
\)
)

# Source: https://github.com/arduino/tooling-project-assets/blob/main/workflow-templates/assets/check-shell-task/Taskfile.yml
shell:format:
desc: Format shell script files
cmds:
# https://github.com/mvdan/sh#shfmt
- shfmt -d .
- |
if ! which shfmt &>/dev/null; then
echo "shfmt not installed or not in PATH. Please install: https://github.com/mvdan/sh#shfmt"
exit 1
fi
- shfmt -w .

shell:format:
desc: Format shell scripts
# Source: https://github.com/arduino/tooling-project-assets/blob/main/workflow-templates/assets/check-shell-task/Taskfile.yml
shell:check-mode:
desc: Check for non-executable shell scripts
cmds:
- shfmt -l -w .
- |
EXIT_STATUS=0
while read -r nonExecutableScriptPath; do
# The while loop always runs once, even if no file was found
if [[ "$nonExecutableScriptPath" == "" ]]; then
continue
fi

echo "::error file=${nonExecutableScriptPath}::non-executable script file: $nonExecutableScriptPath";
EXIT_STATUS=1
done <<<"$(
# The odd approach to escaping `.` in the regex is required for windows compatibility because mvdan.cc/sh
# gives `\` characters special treatment on Windows in an attempt to support them as path separators.
find . \
-path ".git" -prune -or \
\( \
-regextype posix-extended \
-regex '.*[.](bash|sh)' -and \
-type f -and \
-not -executable \
-print \
\)
)"
exit $EXIT_STATUS

config:check:
desc: Lint and check formatting of configuration files
Expand Down
Loading