OVH Cloud OVH Cloud

[Q] test si le shell est interactif ou non

15 réponses
Avatar
Nicolas.MICHEL
Bonjour

Dans un script, je voudrais tester si ce script est lancé par le système
ou s'il est lancé en mode interactif, dons avec quelqu'un derrière ...
De façon à réagir automatiquement si c'est la crontab qui a lancé le
script et à pauser des questions si le script est lancé par quelqu'un.

Est-ce possible ?

Merci d'avance :)

--
Nicolas

5 réponses

1 2
Avatar
Cyrille Lefevre
Bonjour

Dans un script, je voudrais tester si ce script est lancé par le système
ou s'il est lancé en mode interactif, dons avec quelqu'un derrière ...
De façon à réagir automatiquement si c'est la crontab qui a lancé le
script et à pauser des questions si le script est lancé par quelqu'un.


if [[ -t 0 ]]; then
echo interactif
else
echo batch
fi

marche aussi avec [ -t 0 ] et test -t

Regards, Cordialement,

Cyrille Lefevre.
--
mailto:Cyrille.Lefevre-news%
supprimer "%nospam% et ".invalid" pour me repondre.
remove "%nospam" and ".invalid" to answer me.

Avatar
Vincent Lefevre
Dans l'article <f59p78$21st$,
Cyrille Lefevre <cyrille.lefevre-news% écrit:

if [[ -t 0 ]]; then
echo interactif
else
echo batch
fi


Euh... interactif implique probablement stdin attaché à un terminal,
mais l'inverse n'est pas vrai. D'ailleurs:

prunille:~> cat tst
#!/bin/sh
if [[ -t 0 ]]; then
echo interactif
else
echo batch
fi
prunille:~> ./tst
interactif

Je pense que la solution portable (pour les shells POSIX) est de tester
si $- contient 'i'.

--
Vincent Lefèvre - Web: <http://www.vinc17.org/>
100% accessible validated (X)HTML - Blog: <http://www.vinc17.org/blog/>
Work: CR INRIA - computer arithmetic / Arenaire project (LIP, ENS-Lyon)

Avatar
Nicolas.MICHEL
Vincent Lefevre <vincent+ wrote:

Dans l'article <f59p78$21st$,
Cyrille Lefevre <cyrille.lefevre-news% écrit:

if [[ -t 0 ]]; then
echo interactif
else
echo batch
fi



Oui, ça semble fonctionner.
A ce que je comprends du "man test" c'est assez similaire à un
test via la commande "tty", non ?

Euh... interactif implique probablement stdin attaché à un terminal,
mais l'inverse n'est pas vrai. D'ailleurs:

prunille:~> cat tst
#!/bin/sh
if [[ -t 0 ]]; then
echo interactif
else
echo batch
fi
prunille:~> ./tst
interactif


Oui, c'est ce que je veux :
c'est un script de backup qui tourne via cron, mais qui permet s'il est
lancé à la main de configurer ce backup.
(en fait le script est finit, presque en prod, vous arriver trop tard
mais ça fait rien, c'est intéressant quand-même)

Je pense que la solution portable (pour les shells POSIX) est de tester
si $- contient 'i'.


C'est ce que Damien m'a proposé un peu plus haut dans ce fil, mais ça ne
fait pas ce que je veux, à savoir distinguer un script exécuté par cron
d'un script exécuté à la main, où il est possible de pauser des
questions et d'avoir des réponses, donc "interactif" si on veux bien.
(cron a de la peine à répondre et à taper des mots de passe, il faut
bien le dire :)
--
Nicolas


Avatar
Vincent Lefevre
Dans l'article <1i00cs6.1krvaffswsimeN%,
Nicolas MICHEL écrit:

Vincent Lefevre <vincent+ wrote:

Dans l'article <f59p78$21st$,
Cyrille Lefevre <cyrille.lefevre-news% écrit:

if [[ -t 0 ]]; then
echo interactif
else
echo batch
fi



Oui, ça semble fonctionner.
A ce que je comprends du "man test" c'est assez similaire à un
test via la commande "tty", non ?


Euh... il y a une différence entre shell interactif et contrôlé par un
terminal. Maintenant, si tu veux savoir si le processus est contrôlé
par un terminal, le test ci-dessus (ainsi que la commande tty, qui fait
effectivement le même test) ne fonctionnera plus dans le cas où stdin
est redirigé (cas typique du "programme | less", où l'utilisateur peut
agir sur less via le terminal bien que stdin soit redirigé).

La solution est d'utiliser /dev/tty. Tu peux commencer par essayer de
l'ouvrir en lecture: si tu as une erreur, c'est que le processus n'est
pas contrôlé par un terminal. Note: ce n'est théoriquement pas portable.
Alternativement, il y a la solution POSIX:

#include <stdio.h>

int main (void)
{
char *s;
s = ctermid (NULL);
if (fopen (s, "r") == NULL)
return 1;
puts (s);
return 0;
}

qui affiche un nom du fichier associé au terminal (e.g. /dev/tty),
ou termine avec le code 1 si le processus n'est pas contrôlé par un
terminal.

--
Vincent Lefèvre - Web: <http://www.vinc17.org/>
100% accessible validated (X)HTML - Blog: <http://www.vinc17.org/blog/>
Work: CR INRIA - computer arithmetic / Arenaire project (LIP, ENS-Lyon)



Avatar
Nicolas.MICHEL
Vincent Lefevre <vincent+ wrote:

Euh... il y a une différence entre shell interactif et contrôlé par un
terminal.


Oui, je me suis mal exprimé. Désolé.

Maintenant, si tu veux savoir si le processus est contrôlé
par un terminal, le test ci-dessus (ainsi que la commande tty, qui fait
effectivement le même test) ne fonctionnera plus dans le cas où stdin
est redirigé (cas typique du "programme | less", où l'utilisateur peut
agir sur less via le terminal bien que stdin soit redirigé).

La solution est d'utiliser /dev/tty. Tu peux commencer par essayer de
l'ouvrir en lecture: si tu as une erreur, c'est que le processus n'est
pas contrôlé par un terminal. Note: ce n'est théoriquement pas portable.
Alternativement, il y a la solution POSIX:

#include <stdio.h>

int main (void)
{
char *s;
s = ctermid (NULL);
if (fopen (s, "r") == NULL)
return 1;
puts (s);
return 0;
}

qui affiche un nom du fichier associé au terminal (e.g. /dev/tty),
ou termine avec le code 1 si le processus n'est pas contrôlé par un
terminal.


Ok.
Je croule sous le travail, donc je vais me mettre ça sous le coude et
tester quand j'en aurai le temps.

Merci mille fois :)
--
Nicolas

1 2