# Comment Imbriquer && (AND) et || ( OR ) en bash ?

**URL:** <https://www.debian-fr.org/t/comment-imbriquer-and-et-or-en-bash/53589>\
**Category:** Programmation\
**Created:** [Février 21, 2016, 12:23 UTC](https://www.debian-fr.org/t/comment-imbriquer-and-et-or-en-bash/53589 "2016-02-21T12:23:11Z")\
**Posts on this page:** 10\
**Page:** 1

<div class="post-metadata">

**Author:** ![josephtux](https://www.debian-fr.org/user_avatar/www.debian-fr.org/josephtux/32/3985_2.png) [@josephtux](https://www.debian-fr.org/u/josephtux)\
**Post date:** [Février 21, 2016, 12:23 UTC](https://www.debian-fr.org/t/comment-imbriquer-and-et-or-en-bash/53589/1 "2016-02-21T12:23:11Z")

</div>

Bonjour,  
Avec le code suivant,

```auto
mount | egrep '/mnt/S_racine/lv_var' && echo 'Déja montée' ||\
    sudo mount -t xfs /dev/mapper/groupe_unique-lv_var /mnt/S_racine/lv_var &&\
    echo " montée " || exit 5
```

J’espérai avoir le comportement suivant:  
1 savoir si la partition est bien monté ( c’est OK )  
2 si c’est le cas afficher ‘Déja monté’ ( c’est OK )  
sinon la monter ( c’est OK )  
et alors seulement afficher ‘montée’ ( et la ça affiche même si c’était déjà monté )  
3 Enfin sortir du script si ce montage a échoué ( erreur pas encore testée, mais sans problème: ça ne sort pas )

On voit que le “&&” après un “||” garde la vérité de la 1ère commande si le “||” est faux (donc inutile)  
J’aimerai donc regrouper les conditions, un peu comme ceci:

commande1 && echo OK || ( commande2 && echo OK || ( echo message ; exit ) )

Malheureusement, je crois que le regroupement des commandes entre parenthèses lance un sous-shell , et dans ce cas “exit” ne fait que sortir du sous-shell.[size=85]( et même, ici du 2e sous-shell )[/size]

La question: existe-t-il un moyen de faire des regoupements de commandes dans la même instance (le même processus) du shell ?

Merci à tous

---

<div class="post-metadata">

**Author:** ![josephtux](https://www.debian-fr.org/user_avatar/www.debian-fr.org/josephtux/32/3985_2.png) [@josephtux](https://www.debian-fr.org/u/josephtux)\
**Post date:** [Février 21, 2016, 12:23 UTC](https://www.debian-fr.org/t/comment-imbriquer-and-et-or-en-bash/53589/2 "2016-02-21T12:23:11Z")

</div>

Réponse: ?  
remplacer les parenthèses de mon exemple par des accolades { } ( comme en Perl )

`mount | egrep '/mnt/S_racine/S_boot' && echo 'Déja montée' ||\
    ( sudo mount -t ext4 -U 743abb88-2fe8-4dbe-891c-adcc16708a52 /mnt/S_racine/S_boot &&\
    echo " montée ") || { echo '/mnt/S_racine/S_boot N'A PAS PU ÊTRE MONTÉ ; exit 2 }
`  
ne marche pas:  
La commande n’est pas finie:  
en ligne de commande, on obtient une invite (un prompt):

> 

et en script, un message "fin de fichier inattendue ligne "(dernière)

Je sèche; je vais donc, soit renoncer à blinder mon script, soit devoir utiliser les tests avec if.. que je voulais éviter.

---

<div class="post-metadata">

**Author:** ![MisterFreez](https://www.debian-fr.org/letter_avatar_proxy/v4/letter/m/bb73d2/32.png) [@MisterFreez](https://www.debian-fr.org/u/MisterFreez)\
**Post date:** [Février 21, 2016, 12:23 UTC](https://www.debian-fr.org/t/comment-imbriquer-and-et-or-en-bash/53589/3 "2016-02-21T12:23:18Z")

</div>

Les parenthèses n’ouvrent pas de nouveaux shell sauf précédé de $. Tu devrais pouvoir utiliser les parenthèses peut être échappés par .  
Mais je suis d’avis que tu devrais l’écrire sous forme if else.

---

<div class="post-metadata">

**Author:** ![josephtux](https://www.debian-fr.org/user_avatar/www.debian-fr.org/josephtux/32/3985_2.png) [@josephtux](https://www.debian-fr.org/u/josephtux)\
**Post date:** [Février 21, 2016, 12:23 UTC](https://www.debian-fr.org/t/comment-imbriquer-and-et-or-en-bash/53589/4 "2016-02-21T12:23:23Z")

</div>

Merci MisterFreez pour cette précision et effectivement, les lignes de la forme:

`mount | egrep '/mnt/S_racine type' && echo 'Déja montée' ||\
( sudo mount -t ext4 -U 543f1c11-3878-4a9f-995f-19f84166803a /mnt/SC_racine &&\
echo " montée " ) || exit 1`  
fonctionnent:  
exit 1 agit si la commande mount renvoie une erreur et  
echo " montée " dans le cas contraire

---

<div class="post-metadata">

**Author:** ![syam](https://www.debian-fr.org/user_avatar/www.debian-fr.org/syam/32/2951_2.png) [@syam](https://www.debian-fr.org/u/syam)\
**Post date:** [Février 21, 2016, 12:23 UTC](https://www.debian-fr.org/t/comment-imbriquer-and-et-or-en-bash/53589/5 "2016-02-21T12:23:23Z")

</div>

> [@MisterFreez](#):
>
> Les parenthèses n’ouvrent pas de nouveaux shell sauf précédé de $.

C’est faux : [tldp.org/LDP/abs/html/subshells.html](http://tldp.org/LDP/abs/html/subshells.html)  
Les parenthèses (avec ou sans $ devant, peu importe) ouvrent toujours un nouveau shell, les accolades jamais.  
Facilement vérifiable en comptant le nombre de process bash (ps aux | grep -c bash) pendant l’exécution des deux commandes suivantes :

1. while true; do sleep 1; done
2. (while true; do sleep 1; done)

---

<div class="post-metadata">

**Author:** ![MisterFreez](https://www.debian-fr.org/letter_avatar_proxy/v4/letter/m/bb73d2/32.png) [@MisterFreez](https://www.debian-fr.org/u/MisterFreez)\
**Post date:** [Février 21, 2016, 12:23 UTC](https://www.debian-fr.org/t/comment-imbriquer-and-et-or-en-bash/53589/6 "2016-02-21T12:23:26Z")

</div>

Je suis surpris. Je testerais peut être ce soir.

---

<div class="post-metadata">

**Author:** ![Watael](https://www.debian-fr.org/letter_avatar_proxy/v4/letter/w/a4c791/32.png) [@Watael](https://www.debian-fr.org/u/Watael)\
**Post date:** [Février 21, 2016, 12:23 UTC](https://www.debian-fr.org/t/comment-imbriquer-and-et-or-en-bash/53589/7 "2016-02-21T12:23:30Z")

</div>

[quote]exit 1 agit si la commande mount renvoie une erreur[/quote]non, exit 1 est exécuté si grep ne retourne pas d’erreur.

man bash / Pipelines:[quote]The return status of a pipeline is the exit status of the last command,[…][/quote]

Edit:  
ah ouais, non. J’ai lu trop rapidement, mais un peu de clarté ne nuirait pas`if mount | egrep '/mnt/S_racine type'; then echo 'Déja montée'; else sudo mount -t ext4 -U 543f1c11-3878-4a9f-995f-19f84166803a /mnt/SC_racine && echo " montée " || exit 1; fi`

---

<div class="post-metadata">

**Author:** ![josephtux](https://www.debian-fr.org/user_avatar/www.debian-fr.org/josephtux/32/3985_2.png) [@josephtux](https://www.debian-fr.org/u/josephtux)\
**Post date:** [Février 21, 2016, 12:28 UTC](https://www.debian-fr.org/t/comment-imbriquer-and-et-or-en-bash/53589/8 "2016-02-21T12:28:17Z")

</div>

L’intérêt de l’exercice était justement de se passer de if .

( je n’ai rien a priori contre if ! -mais en y réfléchissant, la ligne de commande sans if gagne en concision ce qu’elle perd peut-être en clarté quoique…- )

---

<div class="post-metadata">

**Author:** ![MisterFreez](https://www.debian-fr.org/letter_avatar_proxy/v4/letter/m/bb73d2/32.png) [@MisterFreez](https://www.debian-fr.org/u/MisterFreez)\
**Post date:** [Février 21, 2016, 12:28 UTC](https://www.debian-fr.org/t/comment-imbriquer-and-et-or-en-bash/53589/9 "2016-02-21T12:28:18Z")

</div>

Elle ne perd en clarté que si on fait de l’uniligne :

`if mount | egrep -q '/mnt/S_racine type'; then
    echo 'Déja montée';
else
    if sudo mount -t ext4 -U 543f1c11-3878-4a9f-995f-19f84166803a /mnt/SC_racine ; then
        exit 1
    else
       echo " montée "
    fi
fi`

L’uniligne et le golfe ne servent que pour des tâches quotidiennes et encore une fonction le faire très bien.

---

<div class="post-metadata">

**Author:** ![josephtux](https://www.debian-fr.org/user_avatar/www.debian-fr.org/josephtux/32/3985_2.png) [@josephtux](https://www.debian-fr.org/u/josephtux)\
**Post date:** [Février 21, 2016, 12:47 UTC](https://www.debian-fr.org/t/comment-imbriquer-and-et-or-en-bash/53589/10 "2016-02-21T12:47:59Z")

</div>

Oui MisterFreeze, mais pouvoir faire de l’uniligne est une façon d’être rapide et efficace sans avoir à écrire un script, d’ou l’intéret de s’exercer et d’enrichir sa trousse à outil d’urgence 😉

Bien sur, un script permet, entre autre, d’être plus lisible

je persiste : je n’ai rien contre if 😛
