De temps en temps, je rédige un script bash et il me semble qu'il existe plusieurs façons de définir une variable:
key=value
env key=value
export key=value
Lorsque vous êtes dans un script ou une seule commande (par exemple, je vais souvent chaîner une variable avec un lanceur Wine pour définir le préfixe Wine correct), celles-ci semblent être complètement interchangeables, mais ce ne peut certainement pas être le cas.
Quelle est la différence entre ces trois méthodes et pouvez-vous me donner un exemple du moment où je souhaiterais spécifiquement utiliser chacune d'elles?
Relativement liée à Quelle est la différence entre `VAR = ...` et `export VAR = ...`? mais je veux savoir comment cela env
s'inscrit aussi, et quelques exemples montrant les avantages de chacun seraient bien aussi :)
export key=value
c'est une syntaxe étendue et ne doit pas être utilisé dans des scripts portables (c'est-à-dire#! /bin/sh
).Réponses:
Considérons un exemple spécifique. La
grep
commande utilise une variable d'environnement appeléeGREP_OPTIONS
pour définir les options par défaut.Maintenant. Étant donné que le fichier
test.txt
contient les lignes suivantes:l'exécution de la commande
grep one test.txt
retourneraSi vous exécutez grep avec l’
-v
option, elle renverra les lignes qui ne correspondent pas, ainsi le résultat seraNous allons maintenant essayer de définir l’option avec une variable environnementale.
Les variables d'environnement définies sans
export
ne seront pas héritées de l'environnement des commandes que vous appelez.Le résultat:
De toute évidence, l'option
-v
n'a pas été transmise àgrep
.Vous souhaitez utiliser ce formulaire lorsque vous définissez une variable à utiliser uniquement par le shell, par exemple si
for i in * ; do
vous ne souhaitez pas exporter$i
.Cependant, la variable est transmise à l’environnement de cette ligne de commande, vous pouvez donc effectuer cette opération.
qui retournera le prévu
Vous utilisez ce formulaire pour modifier temporairement l'environnement de cette instance particulière du programme lancé.
L'exportation d'une variable entraîne l'héritage de la variable:
revient maintenant
C’est le moyen le plus courant de définir des variables pour l’utilisation de processus lancés ultérieurement dans un shell.
Tout a été fait à Bash.
export
est un bash intégré;VAR=whatever
est la syntaxe bash.env
d'autre part, est un programme en soi. Quandenv
est appelé, les choses suivantes se produisent:env
est exécutée comme un nouveau processusenv
modifie l'environnement, etenv
processus est remplacé par lecommand
processus.Exemple:
Cette commande lancera deux nouveaux processus: (i) env et (ii) grep (en réalité, le deuxième processus remplacera le premier). Du point de vue du
grep
processus, le résultat est identique à l’exécutionCependant, vous pouvez utiliser cet idiome si vous êtes en dehors de bash ou si vous ne souhaitez pas lancer un autre shell (par exemple, lorsque vous utilisez la
exec()
famille de fonctions plutôt que l'system()
appel).Note complémentaire sur
#!/usr/bin/env
C'est aussi pourquoi l'idiome
#!/usr/bin/env interpreter
est utilisé plutôt que#!/usr/bin/interpreter
.env
ne nécessite pas un chemin d'accès complet à un programme, car il utilise laexecvp()
fonction qui parcourt laPATH
variable, comme le fait un shell, puis se remplace par la commande exécutée. Ainsi, il peut être utilisé pour savoir où un interprète (comme perl ou python) "se repose" sur le chemin.Cela signifie également qu'en modifiant le chemin actuel, vous pouvez influencer quelle variante python sera appelée. Cela rend possible ce qui suit:
au lieu de lancer Calibre, se traduira par
la source
env
proviennent toutes les variables ? Je veux dire quand vous ouvrez un nouveau shell, vous avez toujours quelques variables. Donc, certains programmes doivent les avoirexport
, non?set var=blah
?