🛠 ShellCheck как small helper
Салют,
Сегодня хочу с тобой посмотреть инструмент ShellCheck.
Это статический анализатор shell‑скриптов типа sh, bash, dash, ksh, который ищет небезопасные конструкции и не портируемый код.
Это CLI‑утилита (GPLv3), которая gарсит скрипты, cтроит AST и првоеряет правила, выводит типичные синтаксические ошибки в runtime, а также семантические.
Еще одна полезная фича - corner‑case.
Команды
# Выборка типа shell
shellcheck -s bash script.sh
shellcheck --shell=sh script.sh
# Проверка нескольких файлов
shellcheck scripts/*.sh
find . -type f -name '*.sh' -print0 | xargs -0 shellcheck
# Игнорирование
shellcheck -e SC2086,SC1090 script.sh
# Опциональные проверки
shellcheck -o avoid-nullary-conditions script.sh
# Сужение проверки
shellcheck --source-path=./lib:./scripts main.sh
# Управление ENV
export SHELLCHECK_OPTS='--shell=bash --exclude=SC2016 -o all'
shellcheck script.sh
Вывод
shellcheck -f tty script.sh
shellcheck -f gcc script.sh # файл:строка:колонка:msg
shellcheck -f json script.sh # JSON
shellcheck -f checkstyle script.sh # XML для CI
shellcheck -f sarif script.sh # SARIF
Пример бага почти как фичи
# Давай теперь чекнем почему он может помочь и что может быть неприятно.
# потеря состояния в циклах, где while выполняется в subshell, а count снаружи останется 0.
# ShellCheck подсветит while read как потенциальную проблему, что нам и важно
count=0
cat file | while read -r line; do
count=$((count + 1))
done
echo "$count"
CI/CD
name: shellcheck
on: [push, pull_request]
jobs:
lint-shell:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v4
- name: Install ShellCheck
run: sudo apt-get update && sudo apt-get install -y shellcheck
- name: Run ShellCheck
run: |
git ls-files '*.sh' | xargs shellcheck -s bash -o all -e SC1090
Итого:
• Этот хелпер помогает тебе его использовать как премерджер и контролировать разработчиков, что бы они могли избегать проблемные паттерны, которые повлияют на безопасность
• Тула поможет быть более уверенным, что при настройке правил - ты снизишь частично входной вектор атак и покроешь то, что обычно думается "да ладно, этого не будет"
• Глобально отключать только заведомо не уместные правила и использовать точечные shellcheck disable
• Использовать фиксированной версии, что бы не сломать билд при изменениях, а только выводить в отдельный лог реко по апгрейду
• Собирать список скриптов git ls-files '*.sh'
• Запускать с профилем -s , -o , -e , -P
• Использовать non‑zero exit code критерием падения
Сноска
• Shell — это оболочка, которая интерпретирует команды через системные вызовы позволяя управлять ядром и приложениями с помощью shebang
• Corner‑case - ситуация, когда система ведёт себя иначе, например, скрипт, который корректно работает с файлами, но падает, когда файлов нет, то есть имеет необработанный “пустой список файлов”.
#toolchain #sast #appsec #reco #term
