Dans un script, j'ai un tableau associatif comme:
declare -A VARS=( ["key1"]="value1" ["key2"]="value" )
Existe-t-il une seule commande pour transformer cela en une liste de paramètres sous la forme
--key1=value1 --key2=value2
sans avoir à réécrire manuellement
--key1="${VARS[key1]}" --key2="${VARS[key2]}"
le cas d'utilisation que j'avais en tête était de passer le tableau à un script comme une liste de paramètres, comme
my_script.sh $(to_param_list $VARS)
Pour développer le commentaire que j'ai fait sur la réponse de @Kusalananda, mon cas d'utilisation exact est le suivant: j'ai un script qui est utilisé pour construire un programme d'installation auto-extractible en utilisant make-make, et ce script reçoit certains paramètres qui doivent être séparés entre:
- paramètres pour le script lui-même
- paramètres pour l'installateur dans l'installateur auto-extractible
Les scripts construisent ensuite l'installateur comme ceci:
to_param_list installer_param_list installer_param_array
./makeself ./path/to/sourcedir ./path/to/created/installer "My installer" ./path/to/install/inside/package "${installer_param_list[@]}"
Cependant, j'ai testé le passage de paramètres avec un script d'installation très simple à l'intérieur du package:
while ! -z "$1" ; do
echo "$1"
shift
done
et en passant un tableau comme:
installer_param_array=( ["upgrade-from"]="19 .2.0" ["upgrade-to"]="19.3.0" )
donne cette sortie:
--upgrade-to=19.3.0
--upgrade-from=19
.2.0
la source
my_script.sh "$(declare -p thearray)$"
. Enmyscript.sh
vous le lisez avecsource /dev/stdin <<<"$1"
ensuite vous avezthearray
dans votre script. Vous pouvez avoir d'autres arguments à côté du tableau. Vous pouvez passer de nombreuses variables:my_script.sh "$(declare -p var1 var2 ...)"
dans ce seul argument.Réponses:
Avec une fonction d'assistance:
La commande finale dans le script ci-dessus s'étendrait à l'équivalent d'avoir écrit
La
to_param_list
fonction prend le nom d'une variable de tableau et le nom d'une variable de tableau associatif et les utilise pour créer deux variables de «référence de nom» dans la fonction (les références de nom ont été introduites dans labash
version 4.3). Celles-ci sont ensuite utilisées pour remplir la variable de tableau donnée avec les clés et les valeurs au format approprié à partir du tableau associatif.La boucle de la fonction itère sur
"${!inhash[@]}"
, qui est la liste des clés entre guillemets individuels dans votre tableau associatif.Une fois l'appel de fonction de retour, le script utilise le tableau pour appeler votre autre script ou commande.
Exécution de ce qui précède avec
le script afficherait
Cela montre que les options sont générées sans que le fractionnement de mot ou le remplacement de nom de fichier n'entrent en vigueur. Cela montre également que l'ordre des clés peut ne pas être conservé, car l'accès aux clés à partir d'un tableau associatif le fera dans un ordre assez aléatoire.
Vous ne pouvez pas vraiment utiliser une substitution de commande en toute sécurité ici car le résultat serait une seule chaîne. Si elle n'est pas entre guillemets, cette chaîne sera ensuite divisée en caractères d'espacement (par défaut), ce qui divisera également les clés et les valeurs de votre tableau associatif. L'interpréteur de commandes exécuterait également un remplacement de nom de fichier sur les mots résultants. La citation double de la substitution de commande n'aiderait pas car cela entraînerait l'appel de votre
my_script.sh
avec un seul argument.Concernant votre problème avec
makeself
:Le
makeself
script fait cela avec les arguments de votre script d'installation:Cela enregistre les arguments sous forme de chaîne
$SCRIPTARGS
(concaténés, séparés par des espaces). Celui-ci est ensuite inséré tel quel dans l'archive auto-extractible. Pour que les options soient correctement analysées lorsqu'elles sont réévaluées (ce qu'elles sont lors de l'exécution du programme d'installation), vous devrez fournir un ensemble supplémentaire de guillemets dans les valeurs des paramètres pour qu'elles soient correctement délimitées.Notez que ce n'est pas un bug dans mon code. C'est juste un effet secondaire de la
makeself
production de code shell basé sur des valeurs fournies par l'utilisateur.Idéalement, le
makeself
script devrait avoir écrit chacun des arguments fournis avec un ensemble supplémentaire de guillemets autour d'eux, mais ce n'est pas le cas, probablement parce qu'il est difficile de savoir quel effet cela peut avoir. Au lieu de cela, il laisse à l'utilisateur le soin de fournir ces devis supplémentaires.Relancer mon test d'en haut, mais maintenant avec
produit
Vous pouvez voir que ces chaînes, lorsqu'elles sont réévaluées par le shell, ne sont pas divisées en espaces.
De toute évidence, vous pouvez utiliser votre tableau associatif initial et ajouter à la place les guillemets dans la
to_param_list
fonction en changeantdans
L'une ou l'autre de ces modifications de votre code inclurait les guillemets simples dans les valeurs des options, donc une réévaluation des valeurs deviendrait nécessaire .
la source
"--$param=${inhash[$param]}"
ou dans"${list[@]}"
, ou le script qui reçoit les options fait quelque chose de mal en les analysant.