Você não usar eval
! Há um grande risco de introdução de execução arbitrária de código.
BashFAQ-50 - Estou tentando colocar um comando em uma variável, mas os casos complexos sempre falham.
Coloque-o em uma matriz e expanda todas as palavras com aspas duplas "${arr[@]}"
para não permitir que IFS
as palavras sejam separadas devido à Divisão de Palavras .
cmdArgs=()
cmdArgs=('date' '+%H:%M:%S')
e veja o conteúdo da matriz interna. O declare -p
permite que você veja o conteúdo do array dentro de cada parâmetro de comando em índices separados. Se um desses argumentos contiver espaços, aspas internas ao adicionar ao array evitarão que ele seja dividido devido à divisão de palavras.
declare -p cmdArgs
declare -a cmdArgs='([0]="date" [1]="+%H:%M:%S")'
e execute os comandos como
"${cmdArgs[@]}"
23:15:18
(ou) usar uma bash
função para executar o comando,
cmd() {
date '+%H:%M:%S'
}
e chamar a função apenas
cmd
POSIX sh
não tem matrizes, então o mais próximo que você pode chegar é construir uma lista de elementos nos parâmetros posicionais. Esta é uma sh
maneira POSIX de executar um programa de e-mail
# POSIX sh
# Usage: sendto subject address [address ...]
sendto() {
subject=$1
shift
first=1
for addr; do
if [ "$first" = 1 ]; then set --; first=0; fi
set -- "$@" --recipient="$addr"
done
if [ "$first" = 1 ]; then
echo "usage: sendto subject address [address ...]"
return 1
fi
MailTool --subject="$subject" "$@"
}
Observe que essa abordagem só pode lidar com comandos simples, sem redirecionamentos. Ele não pode lidar com redirecionamentos, pipelines, loops for / while, instruções if, etc.
Outro caso de uso comum é ao executar curl
com vários campos de cabeçalho e carga útil. Você sempre pode definir args como abaixo e invocar curl
no conteúdo da matriz expandida
curlArgs=('-H' "keyheader: value" '-H' "2ndkeyheader: 2ndvalue")
curl "${curlArgs[@]}"
Outro exemplo,
payload='{}'
hostURL='http://google.com'
authToken='someToken'
authHeader='Authorization:Bearer "'"$authToken"'"'
agora que as variáveis estão definidas, use uma matriz para armazenar seus argumentos de comando
curlCMD=(-X POST "$hostURL" --data "$payload" -H "Content-Type:application/json" -H "$authHeader")
e agora faça uma expansão adequada entre aspas
curl "${curlCMD[@]}"