Pourquoi les gens recherchent bash_profile auprès de bashrc au lieu de l'inverse?

7

Il semble que la plupart des émulateurs de terminaux n'exécutent pas de sessions locales en tant que connexion par défaut. Ils chargeront donc bashrc plutôt que bash_profile. Alors, pourquoi la plupart des gens mettent-ils tout dans bash_profile et le font-ils chercher par bashrc plutôt que l’inverse? Par "la plupart des gens", j'entends la plupart des gens que j'ai vus jusqu'à présent. Peut-être que ce n'est pas aussi répandu que je pense.

Plutôt que de placer notre configuration là-bas et d'avoir bash_profile source, ne serait-il pas plus logique et cohérent avec la communauté Linux de tout mettre dans bashrc et d'avoir la source bash_profile?

J'ai entendu de bonnes choses à propos d'iTerm2, et cela ressemble à cela. À peu près tous les autres émulateurs de terminal (à l'exception du terminal OSX par défaut) finiraient par charger bashrc lorsque j'exécute localement. Ce n’est pas important, tant que l’un se source l’autre, mais je ne comprends pas pourquoi préférer bash_profile est la norme?

Note secondaire mineure: je me suis trompé sur iTerm2. Par défaut, l'exécution des sessions de connexion est identique à celle de Terminal.app, bien que les deux émulateurs semblent avoir une option qui vous permet de modifier cela.

ivan
la source

Réponses:

10

Les gens sources bash_profile de bashrc au lieu de l’inverse en raison de conventions locales .

Toutes les opinions que j'ai lues sur la configuration de leurs fichiers de démarrage sont bashprincipalement basées sur la convention locale. La convention locale ne mentionne généralement pas la situation dans son ensemble en ce sens qu’elle ne parle pas beaucoup du cas non interactif et non connecté. La chose amusante est, et j’ai regardé, mais je vois rarement quelqu'un mentionner crondans ses discours pourquoi il faut placer des variables dans un fichier de démarrage plutôt que dans un autre. En fait, je n'ai entendu aucun commentaire dire: " / bin / sh est là pour une raison. Bash émule le shell Bourne original, / bin / sh, lorsqu'il est invoqué en tant que tel. " Tout d'abord, je m'éloigne un peu, ce cas est important pour les personnes qui travaillent avec le shell non seulement de manière interactive, mais qui fournissent des services non interactifs,arrière - plan ) des cron scripts qui ont besoin d'un traitement shell minimal c. -à- traitement de fond ne nécessite pas les subtilités des invites de couleur, l' histoire et la substitution commande, une variable $ TERM correctement défini, etc.

En outre cron, ce que je vois habituellement, ce sont les personnes qui créent des chemins de recherche minimaux ou des programmes appelants pleinement qualifiés, et qui ne savent pas comment traiter les sorties non connectées à un terminal (c’est-à-dire le non-interactif, le non-login bashou le shcasier) lorsqu’ils travaillent avec leurs cronscripts. Cela est généralement dû au manque de compréhension de la séquence de démarrage du shell, ce qui amène l'utilisateur à mettre en œuvre ses propres fichiers de démarrage de manière incohérente ou incohérente par rapport aux conventions déjà établies dans les /etcfichiers de démarrage locaux .

En élaborant, la configuration effectuée par convention locale est présentée dans cette installation et les /etcfichiers du shell . Si vous examinez les /etcfichiers d'une installation UNIX qui sont appelés dans le cadre d'une bashséquence de démarrage typique, vous devez alors créer leur propre démarrage d'une manière complémentaire à la convention établie dans ces /etcfichiers de démarrage.

Le projet de documentation Linux indique:

/ etc / skel / Les fichiers par défaut de chaque nouvel utilisateur sont stockés dans ce répertoire. Chaque fois qu'un nouvel utilisateur est ajouté, ces fichiers squelettes sont copiés dans leur répertoire de base. Un système moyen aurait: fichiers .alias, .bash_profile, .bashrc et .cshrc. Les autres fichiers sont laissés à l'administrateur système.

Bien que le bashmanuel ne mentionne pas explicitement ces fichiers qui se trouvent couramment dans le /etc/skelrépertoire, SunOS, Solaris, RedHat, Ubuntu, HP-UX, umips et Ultrix contiennent des /etc/skelfichiers sur lesquels modéliser les fichiers de démarrage du shell de l'utilisateur. OSX ne le fait clairement pas - j'utilise OSX 10.9.1 maintenant. Malheureusement, OSX ne vous donne pas grand chose à faire en termes de convention, mais comme OSX est un dérivé de BSD, j’ai simplement utilisé un autre dérivé de BSD, puis ma propre bashséquence de démarrage, ajustant pour l’adapter aux conventions locales utilisées dans les /etcfichiers de démarrage OSX 10.9.1 .

Un point important qui a été mentionné dans un commentaire parallèle est que pour OSX, la convention est de démarrer chaque nouveau terminal en tant que shell de connexion interactif. C'est bien la valeur par défaut sous OSX. Cette convention ne pose pas de problème tant que les utilisateurs d'une installation sont cohérents. Le comportement par défaut du terminal sous OSX peut être modifié pour se conformer aux conventions de démarrage du shell d'autres distributions UNIX , en modifiant les préférences suivantes du terminal , en particulier en modifiant le paramètre Shells open with:permettant d'émettre la /usr/bin/login -f -l whmcclos bash -icommande:

entrez la description de l'image ici

Avec tout cela en guise de contexte ou d’introduction, je vais donner suite à mon meilleur conseil , à savoir ce qu’il vaut.

Mon meilleur conseil:

Examinez les fichiers que les administrateurs de votre distribution UNIX ont mis en place. Commencez par les emplacements suivants, s'ils existent. N'oubliez pas d'utiliser la ls -acommande, car certains fichiers commencent par un point. Voyez comment ces fichiers sont utilisés au démarrage et voyez comment vos propres fichiers de démarrage interagissent avec eux:

/etc/bashrc
/etc/profile
/etc/skel/.bash_logout
/etc/skel/.bashrc
/etc/bash.bashrc
/etc/bash_completion

Recherchez dans le bashmanuel la séquence d’appel et de démarrage. Tout est très bien aménagé.

Avec tout cela comme avertissement - voici comment j'ai fait les choses sur mon installation OSX 10.9.1 - Les autres distributions UNIX SERONT différentes, mais ce qui est présenté ci-dessous devrait fonctionner avec la plupart sinon la totalité des distributions UNIX, mais utilisez ces autres distributions UNIX convention comme guide pour adapter le ci-dessous à vos propres objectifs:

.profil

# ~/.profile: executed by the command interpreter for login shells.

# This file is not read by bash(1), if ~/.bash_profile or ~/.bash_login
# exists.  Note, however, that we will have a ~/.bash_profile and it
# will simply source this file as a matter of course.

# See /usr/share/doc/bash/examples/startup-files for examples.
# The files are located in the bash-doc package.

# From here on out, I basically set up my PATH, LD_LIBRARY_PATH, and anything else I'd like
# global to running programs and how those programs find their libraries.  This is shared by
# `cron`, so we really don't want interactive stuff, here.  Also, I setup my environments
# for brew, macports, and fink here, essentially with setting PATH, and invocation of those
# package initialization file as in:

# Brew and locally compiled stuff:
export PATH=/usr/local/bin:$PATH
export PATH=/usr/local/sbin:$PATH

# The following line puts gnu utilities without the prefix "g" in the path
# i.e. tar/gtar:
export PATH=$PATH:/usr/local/Cellar/coreutils/8.21/libexec/gnubin

# MacPorts shoves stuff in /opt, so to get at that stuff...
export PATH=/opt/local/bin:$PATH
export PATH=/opt/local/sbin:$PATH

# Set up for using Fink, which lives in /sw:
[ -e /sw/bin/init.sh ] && . /sw/bin/init.sh

# My stuff:
export PATH=~/perl:$PATH
export PATH=~/bin:$PATH
export PATH=.:$PATH

.bashrc

# ~/.bashrc: executed by bash(1) for non-login shells.
# see /usr/share/doc/bash/examples/startup-files (in the package bash-doc)
# for examples

# If not running interactively, don't do anything
[ -z "$PS1" ] && return

# From here on out, I put in things that are meaningful to interactive shells, like aliases,
# `shopt` invocations, HISTORY control, terminal characteristics, PROMPT, etc.

.bash_profile

# ~/.bash_profile: executed by the command interpreter for login shells.

# Because of this file's existence, neither ~/.bash_login nor ~/.profile
# will be sourced.

# See /usr/share/doc/bash/examples/startup-files for examples.
# The files are located in the bash-doc package.

# Because ~/.profile isn't invoked if this files exists,
# we must source ~/.profile to get its settings:
if [ -r ~/.profile ]; then . ~/.profile; fi

# The following sources ~/.bashrc in the interactive login case,
# because .bashrc isn't sourced for interactive login shells:
case "$-" in *i*) if [ -r ~/.bashrc ]; then . ~/.bashrc; fi;; esac

# I'm still trying to wrap my head about what to put here.  A suggestion
# would be to put all the `bash` prompt coloring sequence functions as
# described on http://brettterpstra.com/2009/11/17/my-new-favorite-bash-prompt/

C'est donc mes deux centimes. Gardez à l'esprit que mes exemples ont essayé de montrer le chemin de contrôle à travers les fichiers de démarrage et d'éviter ce que les conventions d'un site particulier peuvent imposer.

Billy McCloskey
la source
Récemment, Apple a inclus des messages dans la page de manuel cron indiquant qu'il est toujours pris en charge, mais Apple affirme que le service de lancement est plus flexible, je n'abandonne pas le processus d'arrière-plan cron, mais je sais que les administrateurs système n'aiment pas vraiment me laisser avec un fil de contrôle quand je ne suis pas techniquement connecté. En parlant de threads de contrôle pour entrer, quelque part autour de Yosemite, le port ssh 22 a été intégré au service de lancement, et le service de lancement intercepte la tentative ssh, puis achemine ce port vers le port 22!
Billy McCloskey
La raison pour laquelle j’appelle la nouvelle routine du port 22 pour ssh est que tôt ou tard, vous allez entrer dans les clés PGP rsa et autres, et pour que ce commentaire soit à propos, il est essentiel que vos fichiers .bashrc et .bash_profile soient correctement configurés. , ou les tentatives de connexion fantôme de type ssh pour un service simple, en particulier avec le cryptage PGP activé, échoueront lamentablement! Assurez-vous donc que vos fichiers .bashrc et .bash_profile, etc. sont en place avant de manipuler PGP et ssh. si un simple "ssh me @ myIP ls" échoue, vérifiez si vous avez les fichiers .bash_profile, etc. ci-dessus corrects et en place, ou copiés de quelqu'un
Billy McCloskey
Je ne fais que le dernier commentaire en ce sens que j’ai configuré 3 comptes ssh au cours des 3 derniers mois, et chaque fois, j’ai suivi toutes les étapes appropriées, mais j’ai configuré les scripts de shell de démarrage, puis j’ai passé des heures à essayer de comprendre pourquoi je devais appeler. "ls" comme "/ bin / ls" et rien d'autre n'a très bien fonctionné. Toutes les 3 fois, j'ai oublié de donner au nouvel utilisateur une copie de mes fichiers de démarrage du shell. Et, une fois que je l’ai fait, chaque fois, tous leurs problèmes ont disparu. Alors? Voilà. Une sorte de traitement en arrière-plan - connexions ssh'd pour services.
Billy McCloskey
Très bonne réponse! Une chose, je vois que vous mentionnez un fichier à /etc/bashrcen plus de /etc/nash.bashrc. J'étais sur le point de supprimer cela en supposant que c'était une erreur, mais je pensais que je demanderais. Existe-t-il des systèmes livrés avec un /etc/bashrcfichier? Je n'en ai pas vu dans le monde Linux.
Terdon
Mac OS X 10.13.1, que j'ai récemment installé, contient un /etc/bashrcfichier pré-installé .
Billy McCloskey
4

pourquoi mettons-nous tout dans bash_profile en premier lieu?

Le fichier .profile a été utilisé à l’origine par / bin / sh, l’utilisation de .profile permet une compatibilité ascendante.

Sauf si vous utilisez mac, tout n'est pas mis dans bash_profile. Il est mis en bashrc

Ne serait-il pas plus logique et cohérent avec la communauté Linux de tout mettre dans bashrc et d'avoir la source bash_profile?

Il est courant de mettre des informations système dans le shell chargé lors de la connexion à la machine (disponibilité, paquets nécessitant une mise à jour, durée de la CPU, etc.). Si bashrc obtient bash_profile, vous verrez toutes ces informations à chaque fois que vous ouvrez un nouveau shell.

Sous Unix:

.bash_profile est chargé par les shells de connexion
.bashrc est chargé par les shells interactifs

Sauf Mac, qui charge le shell de connexion pour chaque nouveau terminal (interactif ou non)

Ressources additionnelles

différence entre bashrc et bash-profile

Où les variables d'environnement sont spécifiées

spuder
la source
@ spuder- Je ne suis pas sûr de ce que vous faites avec la déclaration Sauf pour Mac, qui charge le shell de connexion pour chaque nouveau terminal (interactif ou non) . Je viens d'ouvrir un nouveau terminal dans iTerm2 et OSX Term.app, et les deux m'ont présenté des shells de connexion interactifs. Votre point est?
Billy McCloskey
Mac est opposé à la plupart des autres Unix. Dans Ubuntu, la bashrc est chargée lorsque de nouveaux terminaux sont ouverts.
Spuder
OSX fait le bashdémarrage différemment. on peut soutenir que chaque distribution UNIX a une convention établie par l'administrateur, reflétée dans les fichiers de démarrage du shell /etc/skelet autres /etc, qui impose aux utilisateurs locaux une infrastructure qui varie avec la distribution. Il est difficile de faire une déclaration générale sur la convention qui convient. J'irais avec la convention locale, et étendre cela. Le bashmanuel énonce clairement quand $HOME/.bashrcest invoqué; pour OSX et tous les autres : interactif et non connecté. C’est l’infrastructure héritée pour le démarrage du shell qui doit être gérée à la fin.
Billy McCloskey
@ supder- Je conviens avec vous que Terminal.app d'OSX force chaque bashshell connecté à être un shell de connexion par défaut. Un utilisateur averti souhaitant suivre les conventions utilisées dans ubuntu éditerait simplement les préférences OSX Terminal.app et modifierait les Shells ouverts avec: de shell de connexion par défaut à la commande (chemin complet): définie sur /usr/bin/login -f -l userid bash -i. Cela changera la convention pour lancer tous les fichiers Terminal.app en tant que shells interactifs non connectés, comme ubuntu. Quoi qu'il en soit, il s'agit d'une convention locale différente de celle de linux et sur laquelle vous pouvez travailler.
Billy McCloskey
2

[...] Je ne comprends pas pourquoi préférer bash_profile est la norme?

Qui a dit que c'était la norme? Le manuel de Bash lui-même a ceci à dire sur le sujet:

Donc, généralement, votre ~ / .bash_profile contient la ligne

si [-f ~ / .bashrc]; puis . ~ / .bashrc; Fi

après (ou avant) toute initialisation spécifique à la connexion.

jjlin
la source
C'est intéressant. J'ai certainement l'impression que la plupart des gens l'appliquent dans l'autre sens (bashrc sourcing bash_profile), mais mon expérience est limitée.
ivan
1
C’est vrai pour Linux, c’est le contraire pour Mac
spuder le