Как передать глобус скрипту оболочки через переменную окружения при передаче ShellCheck

Допустим, у меня есть сценарий оболочки, test.sh, который должен отражать некоторое количество значений. Я хотел бы иметь возможность передавать эти значения через переменную окружения с расширением glob:

$ ls
1.js  2.js  test.sh*

$ FOO="*.js" bash ./test.sh
1.js 2.js

Легко, ты говоришь! Просто пиши

#!/bin/bash
echo $FOO

и действительно, это работает. Но он не пропускает ShellCheck, который призывает нас к использованию неявного сглаживания / расширения ( SC2086). (И это справедливо; в исходном коде строка эха была cp $FOO $BARгде на самом деле мы не хотели расширяться $BAR; эта ошибка ловит ошибки.)

Итак, в стремлении сделать это более явным, я надеялся, что, возможно, будет работать следующее:

#!/bin/bash
array=( $FOO )
echo "${array[@]}"

но нет: мы в конечном итоге с SC2206.

Есть ли канонический способ сделать это, что находится в пределах того, что авторы ShellCheck считают лучшим опытом? (Не стесняйтесь использовать онлайн-чек на сайте www.shellcheck.net, чтобы проверить его.) Это совершенно неправильный подход? Кажется маловероятным, что авторы ShellCheck никогда не думали об этом случае использования...

1 ответ

Решение

В этом случае не существует безопасного обходного пути для предупреждений ShellCheck. Однако диагностика ShellCheck не является универсальной правдой. Как вы могли заметить, документация некоторых из его предупреждений включает в себя раздел " Исключения ". Для SC2206 это гласит:

Исключения:

Если вы уже позаботились (через настройки IFS а также set -f) чтобы разделение слов работало так, как вы хотите, вы можете игнорировать это предупреждение.

Теперь ShellCheck предоставляет директивы для игнорирования предупреждений в каждом конкретном случае:

Директивы Shellcheck позволяют выборочно игнорировать предупреждения и принимают форму комментариев в файлах:

hexToAscii() {
  # shellcheck disable=SC2059
  printf "\x$1"
}

Поддерживаемые директивы

  • disable отключить предупреждения:

    # shellcheck disable=code[,code...]
    statement_where_warning_should_be_disabled
    

    ...

Директивы вместо или сразу после Шебанга применяются ко всему сценарию. В противном случае они ограничиваются структурой, которая следует за ней (например, все ветви оператора case или целая функция).

Таким образом, вы можете подавить свое предупреждение следующим образом:

#!/usr/bin/env bash

# The following line is needed so that the shellcheck directive
# below doesn't have global effect
:

# shellcheck disable=SC2206
array=( $FOO )
echo "${array[@]}"
Другие вопросы по тегам