Comment déterminez-vous si les variables shell sont exportées ou non?

13

Avec la famille shell Bourne, les variables shell ont toutes des noms en majuscules; ce qui signifie que vous ne pouvez pas dire si une variable particulière est une variable d'environnement ou pas simplement en regardant son nom. Comment déterminez-vous quelles variables du shell Bourne sont locales (définies uniquement dans le shell actuel)?

Shoulderpadz
la source
4
Bourne shell ou Bourne-again shell? Pouvez-vous pointer vers une référence pour la variable variable majuscule?
Jeff Schaller
Dans le shell Bourne-again puisque toutes les variables sont en majuscules, comment pouvez-vous déterminer quelles variables bash sont locales?
Shoulderpadz
7
@Shoulderpadz rien ne vous empêche de créer des variables en minuscules.
muru
1
Par local , voulez-vous dire des variables qui n'ont pas été exportées?
Eliah Kagan
4
La distinction que vous demandez est les variables shell vs les variables d'environnement, pas les variables globales vs locales. Notez qu'il existe des variables shell qui ne sont pas des variables d'environnement (c'est-à-dire ce que vous appelez "local"), et il y a des variables d'environnement qui ne sont pas des variables shell (l'environnement peut contenir des noms qui ne sont pas des identificateurs shell valides, et donc ne peuvent pas être des variables).
chepner

Réponses:

17

Si vous voulez voir si une variable est exportée ou non, utilisez declare:

$ foo=a bar=b
$ export foo
$ declare -p foo bar
declare -x foo="a"
declare -- bar="b"
muru
la source
26

Le moyen le plus portable est export -p.

export -prépertorie les variables exportées. C'est généralement le casdeclare -x , si votre shell a declare.

Les shells de style Bourne actuellement utilisés devraient prendre en charge export -p, comme l' exige POSIX :

Lorsque -p est spécifié, l' exportation écrit dans la sortie standard les noms et les valeurs de toutes les variables exportées, au format suivant:

"export %s=%s\n", <name>, <value>

si le nom est défini, et:

"export %s\n", <name>

si le nom n'est pas défini.

La norme poursuit en expliquant que la valeur de la variable est affichée de telle manière qu'elle permet généralement de l'utiliser ultérieurement sur le côté droit d' =une affectation. C'est-à-dire qu'il peut être cité. Différents obus peuvent les afficher différemment mais avec le même effet. export -pfonctionne même dans des shells qui n'ont pas de fonction declareintégrée, comme Dash .

$ dash -c 'export -p | grep HOME='  # busybox sh and other ash give the same output.
export HOME='/home/ek'
$ posh -c 'export -p | grep HOME='  # ksh93, mksh, lksh, and others give the same output.
export HOME=/home/ek

J'ai redirigé la sortie vers la grepcompacité, mais si vous ne la filtrez pas, vous obtenez la liste complète de vos variables exportées. D'après votre question, il semble que c'est ce que vous pourriez trouver le plus utile.

Certains shells, comme Bash, utilisent un format non standard, sauf indication explicite de se comporter de manière conforme à POSIX. Dans Bash export -pdonne la même sortie que declare -xpar défaut.

$ bash -c 'export -p | grep HOME='
declare -x HOME="/home/ek"
$ bash -c 'POSIXLY_CORRECT= export -p | grep HOME='
export HOME="/home/ek"
$ bash -c 'set -o posix; export -p | grep HOME='
export HOME="/home/ek"
$ bash --posix -c 'export -p | grep HOME='
export HOME="/home/ek"
$ ln -s /bin/bash sh
$ ./sh -c 'export -p | grep HOME='  # Invoking bash as sh also puts it in POSIX mode.
export HOME="/home/ek"

Zsh affiche un format non standard même lorsque la compatibilité POSIX est activée:

$ zsh -c 'export -p | grep HOME='
typeset -x HOME=/home/ek
$ zsh -c 'emulate -R sh; export -p | grep HOME='
typeset -x HOME=/home/ek
$ ln -s /bin/zsh sh
$ ./sh -c 'export -p | grep HOME='
typeset -x HOME=/home/ek

Dans tous les cas, vous pouvez extraire des représentations portables (qui peuvent être citées) en recherchant un mot suivi de =. Cela ne dépend pas des mots précédents sur la ligne, tant qu'ils ne précèdent pas immédiatement =, ce qu'ils ne devraient pas. Par exemple:

% export -p | grep -oE '\w+=.*'
HOME=/home/ek
LANG=en_US.UTF-8
LESSCLOSE='/usr/bin/lesspipe %s %s'
....

Notez que toutes les entrées ne le sont pas nécessairement =. En effet, les variables peuvent être non définies mais exportées. Ces entrées sont filtrées par la grepcommande ci-dessus, qui peut ou non être ce que vous voulez.

La plupart du temps, vous voulez juste inspecter la sortie et donc vous ne se préoccuperont pas si les entrées sont précédées par export, declare -x, typeset -xou autre chose. Ensuite, lancez-vous export -p.

J'ai testé ces commandes sur Ubuntu 16.04 LTS avec des versions officiellement emballées de chaque shell.

Eliah Kagan
la source
0

Les variables qui ne sont PAS exportées peuvent être vues à partir de la sortie de la declarecommande dans bash.

Les variables qui sont exportées peut être vu à partir de la sortie declare -xou de exportcommande en bash.

S471
la source