Sempre que você tiver que especificar uma lista de nomes de caminho ou nomes de caminho com nome de arquivo globs, ou apenas uma lista que você pretende passar por cima e / ou usar como lista de argumentos para algum comando, use uma matriz.
Se você não usar uma matriz, mas uma string, você não poderá processar coisas com espaços (porque você usa espaços como o delimitador na string). Isso também dificulta o loop do conteúdo da string, já que você terá que invocar a divisão de palavras (não citando a expansão da variável). Mas isso também fará com que a globalização de nomes de arquivo aconteça, a menos que você desative explicitamente isso com set -f
.
Na maioria dos shells, mesmo em /bin/sh
, use uma matriz. Em sh
, use a matriz de parâmetros posicionais ( $@
).
Para bash
, use uma matriz de strings entre aspas, como
excludes=( '/home/*/.cache/*'
'/var/cache/*'
'/var/tmp/*'
'/var/lib/lxcfs/cgroup/*' )
Então,
rsync_opts=( --verbose --archive )
for excl in "${excludes[@]}"; do
rsync_opts+=( --exclude="$excl" )
done
Mais tarde,
rsync "${rsync_opts[@]}" source/ target
Observe que a cotação é importante em todas as expansões de variáveis acima. A expansão "${array[@]}"
(assim como "$@"
abaixo) resulta em uma lista de elementos citados individualmente da matriz em questão (mas apenas se forem citados em duplicado!).
Para qualquer /bin/sh
shell:
set -- '/home/*/.cache/*' \
'/var/cache/*' \
'/var/tmp/*' \
'/var/lib/lxcfs/cgroup/*'
for excl do
set -- "$@" --exclude="$excl"
shift
done
set -- --verbose --archive "$@"
rsync "$@" source/ target