Se script.sh for apenas algo típico como
#!/bin/bash echo "Hello World!"
Existe um preferido maneira de executar o script? Acho que você deve primeiro fazer o chmod para que se torne executável?
Resposta
Para o seu script específico, qualquer uma das formas funcionará, exceto que ./script.sh
requer execução e bits legíveis, enquanto bash script.sh
requer apenas bits legíveis.
O motivo de a diferença de requisitos de permissões está em como o programa que interpreta seu script é carregado:
-
./script.sh
faz seu shell executar o arquivo como se fosse um arquivo normal executável.
O shell se bifurca e usa uma chamada de sistema (por exemplo, execve
) para fazer o sistema operacional executar o arquivo no processo bifurcado. O sistema operacional verificará as permissões do arquivo (portanto, o bit de execução precisa ser definido) e encaminhará a solicitação para o carregador de programa , que examina o arquivo e determina como executá-lo. No Linux, os executáveis compilados começam com um número mágico ELF , enquanto os scripts começam com um #!
( hashbang ). Um cabeçalho hashbang significa que o arquivo é um script e precisa ser interpretado pelo programa especificado após o hashbang. Isso permite um script para dizer ao sistema como interpretar o script.
Com o seu script, o carregador do programa executará /bin/bash
e passará ./script.sh
como o argumento da linha de comando.
-
bash script.sh
faz seu shell executarbash
e passarscript.sh
como o argumento da linha de comando
Portanto, o sistema operacional carregará (nem mesmo olhando para script.sh
, porque é apenas um argumento de linha de comando). O processo bash
criado interpretará o script.sh
porque foi passado como o argumento da linha de comando. Porque script.sh
só é lido por bash
como um arquivo normal, o bit de execução não é necessário.
Eu recomendo usar ./script.sh
entretanto, porque você pode não saber qual interpretador o script está exigindo. Portanto, deixe o carregador do programa determinar isso para você.
Comentários
- Se o bit executável não estiver definido, você também pode executar o script fazendo ". ./script.sh"
- @Dog Você está correto. O ponto é um atalho para o comando embutido ' source ' , que executa o script no processo bash atual. Portanto, apenas o bit legível é necessário.
- @Dogeatcatworld embora seja verdade, executar
. ./script.sh
não é o mesmo algo como (ou./script.sh
. Considere o script#!/usr/bin/python -V
< newline >print test
. - Esteja ciente de que a origem de um script pode resultar na contaminação da sessão interativa. Por exemplo, se um script alterar a variável de ambiente PATH, essa alteração afetará os comandos executados após a origem. Essa abordagem deve ser reservada para situações em que você depende dos efeitos colaterais (scripts de configuração de ambiente e similares). Para outras situações em que você pode ' t alterar as permissões, executar o comando na linha shebang, seguido pelo nome do script, é a abordagem mais segura.
- Observe que , se você criar um script no diretório atual, não precisará usar ./ ; basta dizer
. script.sh
. Mas concordo com as pessoas que desencorajam o uso do comando.
em scripts que não deveriam ser invocados dessa forma. Estou surpreso que ninguém mencionou que, se o script contiverexit
comandos e você o fornecer, ele poderá desconectá-lo. Um problema menos terrível seria se o script fizesse umcd
, pois isso também afetaria o shell pai (interativo).
Resposta
bash script.sh
invoca o script diretamente usando o bash.
./script.sh
está usando o shebang #!/bin/bash
para determinar como executar.
Se você realmente deseja saber, qual binário é executado se você fizer um bash script.sh
você pode descobrir com which bash
.
Portanto, em seu exemplo, isso não faz diferença. Sim, você deve chmod +x script.sh
para poder executá-lo diretamente por meio de ./script.sh
.
Comentários
Resposta
Crie um arquivo Delete_Self.sh como este:
#!/bin/rm echo I am still here!
Execute isto script como sh Delete_Self.sh
você verá “Ainda estou aqui!” ecoado de volta.
Torne-o executável e execute-o como ./Delete_Self.sh
você verá que nada é ecoado de volta, enquanto o arquivo Delete_Self.sh
se foi.
Portanto, a diferença é que:
-
bash script.sh
irá ignorar o #! linha, porque bash é especificado como o programa para executar script.sh. -
./script.sh
lerá o #! linha para determinar o programa a ser executadoscript.sh
.
Comentários
- +1 para o bom exemplo
Resposta
Além das outras respostas, sabendo a diferença entre executar um script por meio de ./script.sh
(i) e fonte ./script.sh
(ii) é útil – A versão (i) cria um novo shell no qual executar o comando, enquanto (ii) o executa no shell atual – o que pode ser obrigatório se o executável alterar as variáveis de ambiente que precisam ser preservadas após a saída do executável. Por exemplo, para ativar um ambiente python conda, deve-se usar o seguinte:
source activate my_env
N.B. Outra alternativa para source
que você pode encontrar é o .
integrado, ou seja,
. activate my_env
/bin/bash
seja o primeirobash
em seu$PATH
.#!/bin/bash
só funciona se houver um/bin/bash
./script.sh
.