Depois de iniciar um terminal bash, notei que a variável PATH contém entradas duplicadas. Meu terminal inicia um shell de login , portanto, ~/.bash_profile
é fornecido, seguido por ~/.profile
e ~/.bashrc
. Somente em ~/.profile
que eu crio as entradas de caminhos duplicadas.
Para ser pedante, esta é a ordem na qual os arquivos que DEVEM ser adquiridos estão sendo adquiridos:
Sourced /etc/profile
Sourced /etc/bash.bashrc
Sourced .bash_profile
Sourced .profile
Sourced .bashrc
Antes que alguém marque isso como uma duplicata de "A variável PATH contém duplicatas", continue lendo.
No começo, pensei que isso tivesse a ver com ~/.profile
a origem de duas vezes; portanto, o arquivo foi gravado em um arquivo de log sempre que foi originado e, surpreendentemente, ele registrou apenas uma entrada, o que me diz que foi originada apenas uma vez. Ainda mais surpreendente é o fato de que, quando eu comento as entradas que estavam ~/.profile
, as entradas ainda aparecem na PATH
variável. Isso me levou a três conclusões, uma das quais foi rapidamente descartada:
- O Bash ignora comentários válidos do bash e ainda executa o código comentado
- Existe um script que lê
~/.profile
e ignora qualquer código que imprima uma saída (o arquivo de log, por exemplo) - Há outra cópia minha
~/.profile
que está sendo adquirida em outro lugar
O primeiro, concluí rapidamente que não era o caso devido a alguns testes rápidos. A segunda e terceira opções são onde eu preciso de ajuda.
Como faço para reunir um log de scripts que são executados quando meu terminal é inicializado? Usei echo
nos arquivos que verifiquei para saber se eles são originados pelo bash, mas preciso encontrar um método conclusivo que rastreie a execução até o ponto em que o terminal estiver pronto para eu começar a digitar nele.
Se o exposto acima não for possível, alguém pode sugerir onde mais posso procurar para ver quais scripts estão sendo executados .
Referência futura
Este é o script que agora uso para adicionar ao meu caminho:
function add_to_path() {
for path in ${2//:/ }; do
if ! [[ "${!1}" =~ "${path%/}" ]]; then # ignore last /
new_path="$path:${!1#:}"
export "$1"="${new_path%:}" # remove trailing :
fi
done
}
Eu uso assim:
add_to_path 'PATH' "/some/path/bin"
O script verifica se o caminho já existe na variável antes de anexá-lo.
Para usuários zsh, você pode usar este equivalente:
function add_to_path() {
for p in ${(s.:.)2}; do
if [[ ! "${(P)1}" =~ "${p%/}" ]]; then
new_path="$p:${(P)1#:}"
export "$1"="${new_path%:}"
fi
done
}
Editar 28/8/2018
Mais uma coisa que descobri que poderia fazer com esse script é também corrigir o caminho. Então, no início do meu .bashrc
arquivo, faço algo assim:
_temp_path="$PATH"
PATH='/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin:/usr/games:/usr/local/games:/snap/bin'
add_to_path 'PATH' "$_temp_path"
unset _temp_path
Cabe a você o que PATH
deve começar. Examine PATH
primeiro para decidir.
~/.profile
se~/.bash_profile
não existe ...~/.profile
e~/.bashrc
from~/.bash_profile
Respostas:
Se o seu sistema possuir
strace
, você poderá listar os arquivos abertos pelo shell, por exemplo, usando(
-li
significa shell de logon interativo; use apenas-i
para um shell interativo sem logon.)Isso mostrará uma lista de arquivos que o shell abriu ou tentou abrir. No meu sistema, eles são os seguintes:
/etc/profile
/etc/profile.d/*
(vários scripts em/etc/profile.d/
)/home/<username>/.bash_profile
(isso falhar, não tenho esse arquivo)/home/<username>/.bash_login
(isso falhar, não tenho esse arquivo)/home/<username>/.profile
/home/<username>/.bashrc
/home/<username>/.bash_history
(histórico das linhas de comando; este não é um script)/usr/share/bash-completion/bash_completion
/etc/bash_completion.d/*
(vários scripts que fornecem a funcionalidade de preenchimento automático)/etc/inputrc
(define ligações de teclas; isso não é um script)Use
man strace
para mais informações.fonte
echo $0
no terminal dá-bash
mais do que o esperadobash
. Você tem outras sugestões para isso?$0
é um traço-
, ou quando chamado com a opção-l
.echo PATH=\""$PATH"\"
no início e no final de.profile
e.bashrc
? E por que você não faz o que todo mundo faz e define o PATH totalmente ou, se adicionar um diretório, guardaecho ":$PATH:" | grep -q ":/path/to/dir:" || export PATH="$PATH:/path/to/dir"
:?sudo bash -c "echo exit|dtruss bash -li|& less|grep '^open'"
no macOS. (basta substituirstrace
comdtruss
)