Ao executar scripts no bash, tenho que escrever ./
no começo:
$ ./manage.py syncdb
Caso contrário, recebo uma mensagem de erro:
$ manage.py syncdb
-bash: manage.py: command not found
Qual é a razão para isto? Eu pensei que .
é um alias para a pasta atual e, portanto, essas duas chamadas devem ser equivalentes.
Também não entendo por que não preciso ./
ao executar aplicativos, como:
user:/home/user$ cd /usr/bin
user:/usr/bin$ git
(que é executado sem ./
)
bash
shell
unix
command-line
Dan Abramov
fonte
fonte
Respostas:
Porque em Unix, normalmente, o diretório atual não está na
$PATH
.Quando você digita um comando, o shell pesquisa uma lista de diretórios, conforme especificado pela
PATH
variável. O diretório atual não está nessa lista.O motivo para não ter o diretório atual nessa lista é segurança.
Digamos que você seja root e entre no diretório de outro usuário e digite em
sl
vez dels
. Se o diretório atual estiverPATH
, o shell tentará executar osl
programa nesse diretório (já que não há outrosl
programa). Essesl
programa pode ser malicioso.Ele funciona
./
porque o POSIX especifica que um nome de comando que contém a/
será usado diretamente como um nome de arquivo, suprimindo uma pesquisa$PATH
. Você poderia ter usado o caminho completo para exatamente o mesmo efeito, mas./
é mais curto e fácil de escrever.EDITAR
Essa
sl
parte foi apenas um exemplo. Os diretóriosPATH
são pesquisados sequencialmente e, quando uma correspondência é feita, o programa é executado. Portanto, dependendo daPATH
aparência, digitar um comando normal pode ou não ser suficiente para executar o programa no diretório atual.fonte
ls
executável..\my.bat
etc para executarsl
comando chamado locomotiva a vapor, embora não disponível por padrão ;-)Quando o bash interpreta a linha de comando, ele procura comandos nos locais descritos na variável de ambiente
$PATH
. Para vê-lo, digite:Você terá alguns caminhos separados por dois pontos. Como você verá, o caminho atual
.
geralmente não está$PATH
. Portanto, o Bash não pode encontrar seu comando se ele estiver no diretório atual. Você pode alterá-lo tendo:Esta linha adiciona o diretório atual
$PATH
para que você possa fazer:É não recomendado, pois tem problema de segurança, além de você pode ter comportamentos estranhos, como
.
varia de acordo com o diretório que você está em :)Evitar:
Como você pode "mascarar" algum comando padrão e abrir a porta para brechas de segurança :)
Apenas meus dois centavos.
fonte
Seu script, quando estiver no diretório inicial, não será encontrado quando o shell examinar a
$PATH
variável de ambiente para encontrar seu script.O
./
texto diz 'procure no diretório atual o meu script em vez de examinar todos os diretórios especificados em$PATH
'.fonte
Quando você inclui o '.' você está essencialmente dando o "caminho completo" para o script executável do bash, para que seu shell não precise verificar sua variável PATH. Sem o '.' seu shell procurará na sua variável PATH (que você pode ver executando
echo $PATH
para ver se o comando digitado está em alguma das pastas do seu PATH. Caso contrário, como no caso do manage.py), ele diz Não é possível encontrar o arquivo.É uma prática recomendada incluir o diretório atual no PATH, o que é razoavelmente explicado aqui: http://www.faqs.org/faqs/unix-faq/faq/part2/section- 13.htmlfonte
No * nix, diferentemente do Windows, o diretório atual geralmente não está na sua
$PATH
variável. Portanto, o diretório atual não é pesquisado ao executar comandos. Você não precisa./
executar aplicativos porque esses aplicativos estão no seu $ PATH; provavelmente eles estão dentro/bin
ou/usr/bin
.fonte
Esta pergunta já tem respostas impressionantes, mas eu gostaria de acrescentar que, se o seu executável estiver no PATH, e você obtiver resultados muito diferentes ao executar
para os que você recebe se você correr
(digamos que você tenha mensagens de erro com uma e não com a outra), o problema pode ser o fato de você ter duas versões diferentes do executável em sua máquina: uma no caminho e a outra não.
Verifique isso executando
qual executável
e
Corrigiu meus problemas ... Eu tinha três versões do executável, apenas uma delas foi compilada corretamente para o ambiente.
fonte
Justificativa para a
/
regra POSIX PATHA regra foi mencionada em: Por que você precisa de ./ (barra) antes do nome do executável ou do script para executá-lo no bash?mas gostaria de explicar por que acho que esse é um bom design com mais detalhes.
Primeiro, uma versão completa explícita da regra é:
/
(por exemplo./someprog
,/bin/someprog
,./bin/someprog
): CWD é utilizado e não é PATH/
(por exemplosomeprog
): PATH é usado e CWD não éAgora, suponha que executando:
pesquisaria:
Então, se você queria fugir
/bin/someprog
da sua distribuição, e fez:algumas vezes funcionava, mas outras falhava, porque você pode estar em um diretório que contém outro não relacionado
someprog
programa .Portanto, você aprenderia em breve que isso não é confiável e acabaria sempre usando caminhos absolutos quando desejar usar o PATH, derrotando, portanto, o objetivo do PATH.
É também por isso que ter caminhos relativos no PATH é uma péssima ideia. Eu estou olhando para você
node_modules/bin
.Por outro lado, suponha que executando:
Pesquisaria:
Então, se você acabou de baixar um script
someprog
de um repositório git e quiser executá-lo no CWD, nunca terá certeza de que este é o programa real a ser executado, porque talvez sua distribuição possua:que está no seu PATH de algum pacote que você instalou depois de beber demais depois do Natal do ano passado.
Portanto, mais uma vez, você seria forçado a sempre executar scripts locais relativos ao CWD com caminhos completos para saber o que está executando:
o que seria extremamente irritante também.
Outra regra que você pode ser tentado a criar seria:
mas, mais uma vez, isso força os usuários a sempre usar caminhos absolutos para scripts não PATH
"$(pwd)/someprog"
.A
/
regra de pesquisa de caminho oferece uma solução simples de lembrar para o problema sobre:PATH
PATH
o que torna super fácil saber sempre o que você está executando, confiando no fato de que os arquivos no diretório atual podem ser expressos como
./somefile
ousomefile
e, portanto, atribui um significado especial a um deles.Às vezes, é um pouco chato que você não possa procurar em
some/prog
relação aPATH
, mas não vejo uma solução mais saudável para isso.fonte
Quando o script não está no caminho, é necessário fazê-lo. Para mais informações, leia http://www.tldp.org/LDP/Bash-Beginners-Guide/html/sect_02_01.html
fonte
Tudo tem uma ótima resposta à pergunta, e sim, isso só é aplicável ao executá-lo no diretório atual, a menos que você inclua o caminho absoluto. Veja minhas amostras abaixo.
Além disso, a (barra) fez sentido para mim quando tenho o comando na pasta filho tmp2 (/ tmp / tmp2) e ela usa (barra dupla).
AMOSTRA:
fonte