Je recherche un script bash dans le terminal , donc je quitte en cas d'erreur avec
set -o errexit
tue mon terminal, ce qui est extrêmement ennuyeux, car je dois fermer le terminal, en ouvrir un autre et réinitialiser certaines variables.
Jusqu'à présent, en utilisant
command || return
lignes, dans le script, fait exactement ce que je veux
set -o errexit
à faire ... Mais je veux que ce soit fait pour tout le script; pas seulement une ligne / commande
J'ai un fichier plein de commandes pour configurer un site, et je préfère ne pas faire de commande || revenir
pour chaque ligne du fichier
Y a-t-il une autre option définie, ou autre chose qui "reviendra" au lieu de quitter le terminal?
- Pour plus de clarté , je voudrais tuer le script et laisser le terminal dans le même état que le fait d'appuyer sur ctrl + C pour tuer un service exécuté dans le terminal. command || return
est-ce que. Mais je ne veux pas m'attacher || return
à chaque ligne du fichier. Je cherche donc quelque chose de similaire set -o errexit
qui ne provoque pas l'arrêt du terminal
--- Remarque: Création d'un script stupide avec deux lignes (super.sh):
create_path=~/Desktop/site_builder/create.sh
source $create_path blah
Et en plaçant set -o errexit
en haut de create.sh,
fonctionne exactement comme je l'attends. Cependant, c'est vraiment stupide de devoir créer un fichier avec deux lignes, juste pour appeler un autre script bash, au lieu de simplement l'appeler depuis le terminal. Ugghhh
voici quelques exemples:
dans super.sh
#!/bin/bash
create_path=~/Desktop/site_builder/create.sh
source $create_path blah
dans create.sh
#!/bin/bash
set -o errexit
#line below this is a line that fails and will cause the script to stop and return to the terminal as expected
sed "s/@@SITE_NAME@@/$dirname"
~/Desktop/site_builder/template_files/base.html > ~/Desktop/$dirname/templates/base.html # a line with a stupid error
dans le terminal:
$ bash super.sh
sortie comme prévu:
my-mac$
Cela marche. Quelle solution ennuyeuse.
Je souhaite , idéalement, exécuter ce qui se trouve dans le stupide fichier super.sh à partir du terminal, pas le fichier super.sh: D, sans que le terminal ne soit arrêté sur moi. Voici ce qui se passe avec ce que j'essaie de faire:
commande de terminal:
my-mac$ source $create_path blah
dans create.sh j'ai encore set -o errexit
Voici la sortie sur le terminal
sed: 1: "s/@@SITE_NAME@@/blah": unterminated substitute in regular expression
Saving session...
...copying shared history...
...saving history...truncating history files...
...completed.
[Process completed]
Et puis le terminal est gelé. Ctrl + C ne fonctionne pas, pas plus que Ctrl + D
Si au lieu de set -o errexit
, si j'utilise simplement des command || return
instructions partout dans le fichier create.sh, alors j'obtiens exactement ce que je veux, tout en exécutant les lignes dans supser.sh directement sur le terminal (au lieu d'appeler super.sh depuis le terminal). Mais ce n'est pas non plus une solution pratique.
Remarque: J'ai aimé la réponse de @terdon à propos de la création d'un shell enfant, donc j'ai fini par générer un sous-shell via le script au lieu du terminal, comme il l'a montré dans sa réponse en utilisant les accolades ( )
, autour du script entier. Sa réponse fonctionne aussi.
source $file_path argument
Le script est exécuté dans le même shell que je l'ai appelé (qu'estsource
- ce qui m'a été dit ... et agit comme c'est le cas) lescommand || return
instructions sont dans le fichier queRéponses:
Sourcez simplement le fichier avec une sécurité intégrée:
... alors la commande globale n'échouera pas, même si c'est le
source
cas.la source
source file || true
ne fait pas cela, pas plus quesource file || return
lorsque je tape ceci dans le terminal ...Jills-MBP:~ jillr$ source ~/Desktop/site_builder/create.sh blah || true
il exécute simplement la partie suivante du script en cas d'échec, donc retourne au lieu de vrai. La seule chose qui a fonctionné est descommand || return
instructions dans le fichier réel pour toutes les commandes, ce qui est stupide. Je ne sais pas si jeter tout cela dans une fonction puis appelerfunction || return
à la fin du fichier ferait du bien non plus.|| return
une commande qui échoue, oui, elle reviendra. Je pensais que nous essayions d'empêcher votre shell principal / parent de sortir?C'est la seule chose qui fonctionne pour ce que je devais accomplir (créer un environnement virtuel puis l'activer, puis installer les exigences à partir d'un script bash):
générer un shell sous-shell / enfant à partir du script, comme dans:
stupid_file.sh
lancez le stupid_file en utilisant:
LA FIN.
** prend un arc **
(crédit à Jeff et Terdon)
la source
bash $create_path blah
et voir s'il se ferme toujours, et s'exécute de la même manière, et installe toujours les choses correctement dans mon environnement virtuel. Plus de temps maintenant.(...)
, car toutes les affectations entre parenthèses n'affectent que ce sous-shell.foo=3; (foo=5); echo "$foo"
produira 3, pas 5.source file
depuis le terminal et attendre les mêmes résultats. Parce que ça n'a jamais marché. La seule fois où j'obtiens les mêmes résultats, c'est quand je crée explicitement un sous-shell, que ce soit via le terminal ou à partir du script. Je peux cependant utiliserbash
au lieu desource
pour exécuter le script, et obtenir les mêmes résultats, mais uniquement lorsquepip install -r $apath/requirements.txt
dans cet environnement activé. C'est pourquoi j'ai utilisé la source en premier lieu pour appeler le scriptComme solution de contournement simple, vous pouvez exécuter un shell dans votre shell actuel et y source. Quelque chose comme:
Ouvrez un nouveau terminal et configurez tout comme vous le souhaitez. Vous avez mentionné certaines variables d'environnement, etc. Installez-les ici.
Dans ce terminal, démarrez un nouveau shell. Par exemple,
bash
.Faire votre truc. Sourcez votre script. S'il se termine, vous êtes simplement jeté dans le premier shell et tout est toujours configuré. Courez à
bash
nouveau et vous êtes de retour aux affaires.Pour illustrer, j'ai créé ce script qui échouera si vous essayez de le source:
Voyons voir ce qui se passe si je commence une session shell imbriquée et la source puis (notez que j'utilise le nom portable pour la
source
commande,.
,source
est un bash):Comme vous pouvez le voir, l'erreur de syntaxe a provoqué la fermeture du script d'origine, ce qui a entraîné la fermeture de ma session shell, mais comme il s'agissait d'une session imbriquée, cela m'a simplement renvoyé au shell parent d'origine avec toutes les variables toujours configurées. . Maintenant, exécutez à nouveau un nouveau shell et vous pouvez revenir à la recherche de votre script.
la source
create_path=~/Desktop/site_builder/create.sh
dans le shell parent parce que je le fais si souvent. Et j'en ai besoin pour appeler la source $ create_path [argument] pour exécuter le script.export
les utilisez pas . Mais ce que vous décrivez n'a vraiment aucun sens. Cela ressemble de plus en plus à un problème XY . Vous voudrez peut-être publier une nouvelle question expliquant quel est votre objectif final. Je parie que nous pouvons vous donner une meilleure solution que tout ce sourcing bizarre.