Executando scripts de outro diretório

11

Frequentemente, o script que eu quero executar não está localizado no meu diretório de trabalho atual e eu realmente não quero deixá-lo.

É uma boa prática executar scripts (BASH, Perl etc.) de outro diretório? Eles geralmente encontrarão todas as coisas necessárias para executar corretamente?

Em caso afirmativo, qual é a melhor maneira de executar um script "distante"? É isso

. /path/to/script

ou

sh /path/to/script

e como usar sudonesses casos? Isso, por exemplo, não funciona:

sudo . /path/to/script
Desmond Hume
fonte
Esteja ciente de que . /path/to/script origina o script! Você não precisa do período se apenas deseja executá-lo.
gniourf_gniourf

Respostas:

14

sh / path / to / script gerará um novo shell e executará o script independentemente do seu shell atual. O sourcecomando (.) Chamará todos os comandos no script no shell atual. Se o script chamar exitpor exemplo, você perderá o shell atual. Por esse motivo, geralmente é mais seguro chamar scripts em um shell separado com sh ou executá-los como binários usando o caminho completo (começando com /) ou relativo (./). Se chamados como binários, eles serão executados com o intérprete especificado (#! / Bin / bash, por exemplo).

Quanto a saber se um script encontrará ou não os arquivos necessários, não há uma boa resposta, além de olhar para o script para ver o que ele faz. Como opção, você sempre pode ir para a pasta do script em um subprocesso sem sair da pasta atual:

$(cd /wherever/ ; sh script.sh)
Ярослав Рахматуллин
fonte
3
Você quer dizer (cd /wherever/ ; sh script.sh)? Por que você tem um $na frente?
G-Man diz 'Reinstate Monica'
7

Você pode fazer isso definitivamente (com os ajustes que os outros mencionaram como sudo sh /pathto/script.shou ./script.sh). No entanto, eu faço uma de algumas coisas para executá-las em todo o sistema para não me preocupar com dirs e economizar uma digitação extra inútil.

1) Link simbólico para /usr/bin

ln -s /home/username/Scripts/name.sh /usr/bin/name

(certifique-se de que não haja um nome sobreposto, porque você obviamente o substituirá.) Isso também me permite mantê-los em minhas pastas de desenvolvimento para que eu possa ajustar conforme necessário.

2) Adicione o diretório Scripts ao seu caminho (usando .bash_profile - ou o que quer que seja que você tenha no seu shell)

PATH=/path/to/scripts/:$PATH

3) Crie Alias ​​no .bash_profile in ~/.bash_profileadicione algo como:

alias l="ls -l"

Como você pode ver, a sintaxe é apenas alias, dígitos que você deseja que atuem como um comando, o comando. Assim, digitar "l" em qualquer lugar do terminal resultaria em ls -l Se você quiser sudo, apenas alias sl="sudo ls -l"observe-se l vs sl (como um exemplo inútil).

De qualquer forma, você pode apenas digitar sudo nameofscripte seguir seu caminho. Não há necessidade de mexer com ./ ou. ou sh, etc. Apenas marque-os como executáveis ​​primeiro: D

nerdwaller
fonte
Eu recomendo a opção 2.
Bernhard
Por quê ?, é uma prática recomendada ou apenas um gosto?
Sergio
3

Eu costumo fazer como você diz

sh /path/to/script

E executá-lo como root / superusuário

sudo sh /path/to/script

Seu diretório atual importa apenas se os scripts assumirem que você está na mesma pasta que ele. Eu diria que a maioria dos scripts não faz isso e você está salvo para executá-lo como acima.

Bolli
fonte
não funcionaria se secure_path é definido em arquivo / etc / sudoers
l1zard
3

Normalmente, mantenho meus scripts em ( /usr/local/binou /usr/local/sbin/se o script precisar de privilégios de root) onde, de acordo com o FHS (File System Hierarchy Standard), eles pertencem.

Tudo que você precisa fazer é garantir que esses dois diretórios sejam adicionados ao seu PATH. Você pode fazer isso editando seu $HOME/.bashrcarquivo e adicionando esta linha:

export PATH=$PATH:/usr/local/sbin:/usr/local/bin

Se você deseja executar um script como root via sudo, você deve adicionar esses diretórios à variável secure_pathno seu /etc/sudoers.

Defaults    secure_path="/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin"

A edição deste arquivo é feita executando, o visudoque garante que você não cometa erros.

l1zard
fonte
Erro de digitação: você quer dizer em .bashrcvez de .bachrc.
gniourf_gniourf
0

Não tenho certeza se funciona assim no linux, assumindo que não, se ninguém sugeriu. Mas em vez de usar ././ para voltar aos diretórios. Você pode usar aspas para dar um caminho absoluto? Talvez não lhe dê acesso a toda a unidade para poder fazer isso.

Codezilla
fonte
0

Se você possui scripts por aí, precisa executar com freqüência e eles dependem da localização deles para encontrar recursos, você pode fazer isso facilmente, combinando comandos em um alias como este.

alias run-script="cd /home/user/path/to/script/ && bash script.sh"

Dessa forma, você não precisa alterar mais nada para fazê-lo funcionar.

EvR2f
fonte
0

Não sei por que ninguém sugeriu este, mas é super fácil! Pesquisei no Google algumas vezes e não consegui encontrar a resposta exata que estou dando, então pensei em compartilhar. IMO, esta, mas a melhor solução, também a mais fácil, para mim de qualquer maneira, no entanto, outros podem sentir e fazer as coisas de maneira diferente.

# Place this somewhere in your .bashrc/.bash_profile/etc and edit as you see fit

YOURCOMMAND () {
  cd /path/to/directory/containing/your/script/ && ./YOURSCRIPT
}

Primeiro, o comando 'cd' informando o diretório do local dos scripts. Em seguida, '&&' para que você possa amarrá-lo após executar o próximo comando. Por fim, abra seu script exatamente como você o executaria no terminal! Salve o seu arquivo BASH e leva 5 segundos para configurar.

Espero que isso tenha ajudado alguém.

AnonymousX
fonte
-1

Pergunta antiga, mas atemporal.

A solução que eu sempre vi é ter um $HOME/bindiretório e colocá-lo em primeiro lugar $PATH(via ~/.bashrcse ele ainda não estiver lá; em alguns sistemas ~/biné o primeiro a entrar $PATHpor padrão). Colocar scripts lá para execução ou links simbólicos para scripts / executáveis ​​em outros lugares é a maneira simples de lidar com problemas de caminho que não devem afetar o sistema ou outros usuários.

Se um script requer recursos adicionais que podem ser encontrados em relação à sua própria localização (não incomum), o envvar $BASH_SOURCEé usado. $BASH_SOURCEsempre contém o caminho absoluto para o próprio script atualmente em execução, independentemente do valor de $PWD.

Considere o seguinte:

ceverett@burrito:~$ echo $PATH
/home/ceverett/bin:/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin:/usr/games:/usr/local/games

Para que possamos ver o que $HOME/biné o primeiro a $PATHentrar, o que quer que eu coloque ~/binserá executado. Eu tenho um script de demonstração chamado ~/bin/findme:

#!/bin/bash

echo "Running from $BASH_SOURCE"

Isso pode ser usado para obter o caminho absoluto para a localização do script em execução.

ceverett@burrito:~$ findme
Running from /home/ceverett/bin/findme
ceverett@burrito:~$ cd foo
ceverett@burrito:~/foo$ findme
Running from /home/ceverett/bin/findme
ceverett@burrito:~/foo$ cd /
ceverett@burrito:/$ findme
Running from /home/ceverett/bin/findme
zxq9
fonte
(1) Embora isso pareça ser uma informação útil, a pergunta não perguntou como escrever scripts que usam recursos relativos à sua própria localização; perguntou sobre a execução de scripts. (2) Não tenho certeza de como o seu segundo parágrafo aborda a questão. Você está sugerindo que, se eu escrever um script e Desmond quiser executá-lo, ele deverá vinculá-lo ao seu bindiretório privado ? Isso parece complicado. (3) Além disso, quebra a independência da localização. Se /home/desmond/bin/foofor um link para o meu script, BASH_SOURCEserá /home/desmond/bin/foo, e o script não poderá encontrar seus recursos.
G-Man diz 'Reinstate Monica'
@ G-Man (1) O usuário não forneceu muito contexto. Sempre que essa pergunta me foi feita nos últimos 30 anos, sempre houve no contexto um usuário (geralmente um novo sysop ou desenvolvedor) executando uma mistura de scripts próprios e outros scripts adquiridos para automatizar tarefas triviais, por isso respondi que caminho. Isso faz supor um pouco de conhecimento de script na parte da pergunta do usuário. (2) Os scripts de todo o sistema geralmente são instalados /binou em um local conhecido em /opt. (3) Independência de localização é exatamente o que isso preserva ao escrever uma coleção interdependente de scripts pessoais.
Zxq9