Stations de travail en ligne OnWorks Linux et Windows

Logo

Hébergement gratuit en ligne pour les postes de travail

<Précédent | Table des matières | Suivant>

Commandes de groupe et sous-shells

bash permet de regrouper les commandes. Cela peut être fait de deux manières ; soit avec un commande de groupe ou avec un sous-coquille. Voici des exemples de la syntaxe de chacun :

Commande de groupe :

{ commande1; commande2 ; [commande3; ...] }

Sous-shell :

(commande1; commande2; [commande3;...])

Les deux formes diffèrent en ce qu'une commande de groupe entoure ses commandes d'accolades et un sous-shell utilise des parenthèses. Il est important de noter qu'en raison de la manière bash implémente les commandes de groupe, les accolades doivent être séparées des commandes par un espace et la dernière commande doit se terminer par un point-virgule ou une nouvelle ligne avant l'accolade fermante.

Alors à quoi servent les commandes de groupe et les sous-shells ? S'ils ont une différence importante (sur laquelle nous reviendrons dans un instant), ils sont tous deux utilisés pour gérer la redirection. Considérons un segment de script qui effectue des redirections sur plusieurs commandes :



ls -l > sortie.txt

echo "Liste de foo.txt" >> output.txt cat foo.txt >> output.txt

ls -l > sortie.txt

echo "Liste de foo.txt" >> output.txt cat foo.txt >> output.txt


C'est assez simple. Trois commandes avec leur sortie redirigée vers un fichier nommé output.txt. En utilisant une commande de groupe, nous pourrions coder ceci comme suit :


{ ls -l; echo "Liste de foo.txt" ; chat foo.txt; } > sortie.txt

{ ls -l; echo "Liste de foo.txt" ; chat foo.txt; } > sortie.txt


L'utilisation d'un sous-shell est similaire :



(ls -l; echo "Liste de foo.txt"; cat foo.txt) > output.txt

(ls -l; echo "Liste de foo.txt"; cat foo.txt) > output.txt


En utilisant cette technique, nous nous sommes épargnés de la frappe, mais là où une commande de groupe ou un sous-shell brille vraiment, c'est avec les pipelines. Lors de la construction d'un pipeline de commandes, il est souvent utile de combiner les résultats de plusieurs commandes en un seul flux. Les commandes de groupe et les sous-shells facilitent la tâche :



{ ls -l; echo "Liste de foo.txt" ; chat foo.txt; } | lpr

{ ls -l; echo "Liste de foo.txt" ; chat foo.txt; } | lpr


Ici, nous avons combiné la sortie de nos trois commandes et les avons transférées dans l'entrée de LPR produire un rapport imprimé.

Dans le script qui suit, nous utiliserons des commandes de groupes et examinerons plusieurs techniques de programmation pouvant être utilisées en conjonction avec des tableaux associatifs. Ce script, appelé tableau-2, lorsqu'on lui donne le nom d'un répertoire, imprime une liste des fichiers dans le répertoire avec les noms du propriétaire du fichier et du propriétaire du groupe. A la fin de la liste, le script imprime un décompte du nombre de fichiers appartenant à chaque propriétaire et groupe. Ici, nous voyons les résultats (condensés par souci de concision) lorsque le script reçoit le répertoire

/usr/bin :


[moi@linuxbox ~]$ tableau-2 /usr/bin

/usr/bin/2to3-2.6

racine

racine

/usr/bin/2to3

racine

racine

/usr/bin/a2p

racine

racine

/usr/bin/anavigateur

racine

racine

/usr/bin/aconnect

racine

racine

/usr/bin/acpi_fakekey

racine

racine

/usr/bin/acpi_listen

racine

racine

/usr/bin/add-apt-dépôt

racine

racine

.

.

.

/usr/bin/zipgrep

racine

racine

/usr/bin/infozip

racine

racine

/usr/bin/zipnote

racine

racine

/usr/bin/zip

racine

racine


/usr/bin/zipsplit

/usr/bin/zjsdecode

/usr/bin/zsoelim

racine racine racine

racine racine racine

Propriétaires du fichier : démon : 1


des dossiers)

racine : 1394

des dossiers)

image

Propriétaires du groupe de fichiers : crontab : 1 fichier(s) démon : 1 fichier(s) lpadmin : 1 fichier(s) mail : 4 fichier(s) mlocate : 1 fichier(s) root : 1380 fichier(s) shadow : 2 fichier ssh : 1 fichier(s)

tty : 2 fichier(s)

utmp : 2 fichier(s)


image

#! / Bin / bash

#! / Bin / bash

# array-2 : utilisez des tableaux pour compter les propriétaires de fichiers

declare -A files file_group file_owner groupe les propriétaires si [[ ! -d "$1" ]]; alors

echo "Usage : array-2 dir" >&2 exit 1

fi


pour i dans "$1"/* ; do owner=$(stat -c %U "$i") group=$(stat -c %G "$i") files["$i"]="$i" file_owner["$i"]=$ propriétaire file_group["$i"]=$group ((++owners[$owner])) ((++groups[$group]))

fait


# Lister les fichiers collectés

{ pour i dans "${fichiers[@]}" ; do printf "%-40s %-10s %-10s\n" \

"$i" ${file_owner["$i"]} ${file_group["$i"]} done } | sorte

# array-2 : utilisez des tableaux pour compter les propriétaires de fichiers

declare -A files file_group file_owner groupe les propriétaires si [[ ! -d "$1" ]]; alors

echo "Usage : array-2 dir" >&2 exit 1

fi


pour i dans "$1"/* ; do owner=$(stat -c %U "$i") group=$(stat -c %G "$i") files["$i"]="$i" file_owner["$i"]=$ propriétaire file_group["$i"]=$group ((++owners[$owner])) ((++groups[$group]))

fait


# Lister les fichiers collectés

{ pour i dans "${fichiers[@]}" ; do printf "%-40s %-10s %-10s\n" \

"$i" ${file_owner["$i"]} ${file_group["$i"]} done } | sorte

Voici une liste (avec les numéros de ligne) du script :


1

2

3

4

5

6

7

8

9

10

11

12

13

14

15

16

17

18

19

20

21

22

23

24

25

26

1

2

3

4

5

6

7

8

9

10

11

12

13

14

15

16

17

18

19

20

21

22

23

24

25

26


27

28

29

30

31

32

33

34

35

36

37

38

39

40

27

28

29

30

31

32

33

34

35

36

37

38

39

40


image

echo

echo

# Liste des propriétaires

echo "Propriétaires du fichier :"

{ pour i dans "${!owners[@]}" ; faire

printf "%-10s : %5d fichier(s)\n" "$i" ${owners["$i"]} done } | sorte

echo


# Liste des groupes

echo "Propriétaires du groupe de fichiers :"

{ pour i dans "${!groups[@]}" ; faire

printf "%-10s : %5d fichier(s)\n" "$i" ${groupes["$i"]} done } | sorte

# Liste des propriétaires

echo "Propriétaires du fichier :"

{ pour i dans "${!owners[@]}" ; faire

printf "%-10s : %5d fichier(s)\n" "$i" ${owners["$i"]} done } | sorte

echo


# Liste des groupes

echo "Propriétaires du groupe de fichiers :"

{ pour i dans "${!groups[@]}" ; faire

printf "%-10s : %5d fichier(s)\n" "$i" ${groupes["$i"]} done } | sorte

Jetons un coup d'œil à la mécanique de ce script :

Ligne 5: Les tableaux associatifs doivent être créés avec le déclarer commande en utilisant la -A

option. Dans ce script, nous créons cinq tableaux comme suit :

fichiers contient les noms des fichiers du répertoire, indexés par nom de fichier groupe_fichier contient le groupe propriétaire de chaque fichier, indexé par nom de fichier propriétaire_fichier contient le propriétaire de chaque fichier, indexé par nom de fichier groupes contient le nombre de fichiers appartenant aux propriétaires du groupe indexé contient le nombre de fichiers appartenant au propriétaire indexé

Lignes 7 à 10 : vérifie qu'un nom de répertoire valide a été transmis comme paramètre de position. Sinon, un message d'utilisation s'affiche et le script se termine avec un état de sortie de 1.

Lignes 12-20 : Parcourez les fichiers du répertoire. En utilisant le état commande, les lignes 13 et 14 extraient les noms du propriétaire du fichier et du propriétaire du groupe et attribuent les valeurs à leurs tableaux respectifs (lignes 16, 17) en utilisant le nom du fichier comme index du tableau. De même, le nom du fichier lui-même est attribué au fichiers tableau (ligne 15).

Lignes 18-19 : Le nombre total de fichiers appartenant au propriétaire du fichier et au propriétaire du groupe est incrémenté de un.

Lignes 22-27 : La liste des fichiers est sortie. Cela se fait à l'aide de l'expansion du paramètre "${array[@]}" qui s'étend à la liste complète des éléments du tableau, chaque élément étant traité comme un mot distinct. Cela permet la possibilité qu'un nom de fichier contienne des espaces intégrés. Notez également que la boucle entière est entourée d'accolades formant ainsi une commande de groupe. Cela permet à la totalité de la sortie de la boucle d'être acheminée dans le sort commander. Ceci est nécessaire car l'expansion des éléments du tableau n'est pas triée.

Lignes 29-40 : Ces deux boucles sont similaires à la boucle de liste de fichiers, sauf qu'elles utilisent le "${!


array[@]}" qui se développe dans la liste des index de tableau plutôt que dans la liste des éléments du tableau.


 

Meilleur système d'exploitation Cloud Computing chez OnWorks :