Может ли массив bash использоваться вместо eval set – «$ params»?

Я рассматриваю библиотеку optparse для синтаксического анализа параметров bash , в частности, этот бит в сгенерированном коде:

 params="" while [ $# -ne 0 ]; do param="$1" shift case "$param" in --my-long-flag) params="$params -m";; --another-flag) params="$params -a";; "-?"|--help) usage exit 0;; *) if [[ "$param" == --* ]]; then echo -e "Unrecognized long option: $param" usage exit 1 fi params="$params \"$param\"";; ##### THIS LINE esac done eval set -- "$params" ##### AND THIS LINE # then a typical while getopts loop 

Будет ли реальная причина использовать здесь eval ? Вклад в eval кажется, надлежащим образом дезинфицирован. Но не будет ли он работать одинаково:

 params=() # ... --my-long-flag) params+=("-m");; --another-flag) params+=("-a");; # ... params+=("$param");; # ... set -- "${params[@]}" 

Это кажется мне более чистым.

На самом деле, не разрешат ли эти параметры анализировать непосредственно из массива params (даже не используя set ), используя while getopts "ma" option "${params[@]}"; do вместо того, чтобы использовать while getopts "ma" option; do while getopts "ma" option; do ?

Вопрос: « Должен ли использоваться массив bash вместо eval set -« $ params »?», И ответ да! ,

В вашем сценарии вход в eval явно не подвергается надлежащей дезинфекции. Пытаться

  yourscript '`xterm`' 

и вы увидите, что xterm запущен, даже если обратные ссылки правильно указаны одиночными кавычками. (Сравнить с

  echo '`xterm`' 

который не запускает xterm.)

Исправить ошибку, когда keepting eval очень сложно. Даже изменение линии

  params="$params \"$param\"";; 

в

  params="$params '$param'";; 

не помогло бы: теперь

  yourscript '`xterm`' 

больше не запускается xterm, но

  yourscript \'' `xterm` '\' 

все еще делает.