Devo estar perdendo algo incrivelmente simples sobre como fazer isso, mas tenho um script simples:
extract () {
if [ -f $1 ] ; then
case $1 in
*.tar.bz2) tar xvjf $1 ;;
*.tar.gz) tar xvzf $1 ;;
*.tar.xz) tar xvJf $1 ;;
*.bz2) bunzip2 $1 ;;
*.rar) unrar x $1 ;;
*.gz) gunzip $1 ;;
*.tar) tar xvf $1 ;;
*.tbz2) tar xvjf $1 ;;
*.tgz) tar xvzf $1 ;;
*.zip) unzip $1 ;;
*.Z) uncompress $1 ;;
*.7z) 7z x $1 ;;
*.xz) unxz $1 ;;
*.exe) cabextract $1 ;;
*) echo "\'$1': unrecognized file compression" ;;
esac
else
echo "\'$1' is not a valid file"
fi
}
O script funciona, mas não consigo executá-lo por padrão quando faço login.
Eu consultei esta resposta muito completa: Como definir e carregar sua própria função de shell em zsh , e consegui fazer com que meu $ fpath mostrasse o diretório apropriado onde armazenei a função.
Em meu perfil .zshrc, adicionei fpath=( ~/.local/bin "${fpath[@]}" )
ao fundo, que é o caminho onde minhas funções residem.
Quando eu insiro echo $fpath
, recebo:
/home/me/.local/bin /home/me/.oh-my-zsh/plugins/git /home/me/.oh-my-zsh/functions /home/me/.oh-my-zsh/completions ...
No entanto, não funciona, a menos que eu digite explicitamente autoload -Uz extract
toda vez que faço login.
Existe uma maneira de fazer com que todo o diretório seja carregado automaticamente quando eu fizer login?
Você está misturando scripts e funções.
Fazendo um roteiro
Um script é um programa autônomo. Pode acontecer de estar escrito em zsh, mas você pode invocá-lo de qualquer lugar, não apenas de uma linha de comando zsh. Se acontecer de você executar um script escrito em zsh a partir de uma linha de comando zsh ou outro script zsh, isso é uma coincidência que não afeta o comportamento do script. O script é executado em seu próprio processo, não influencia seu pai (por exemplo, não pode alterar as variáveis ou o diretório atual).
Seu código realiza uma tarefa autônoma que pode ser chamada de qualquer lugar e não precisa acessar o estado do shell que o executa, portanto, deve ser um script, não uma função.
Um script deve ser um arquivo executável:
chmod +x /path/to/script
. Ele deve começar com uma linha shebang para permitir que o kernel saiba qual programa usar para interpretar o script. No seu caso, adicione esta linha ao topo do arquivo:Coloque o arquivo em um diretório listado na
$PATH
variável. Muitos sistemas configurados~/bin
ou~/.local/bin
no padrão do usuárioPATH
, então você pode usá-los. Se você deseja adicionar outro diretório, consulte http://unix.stackexchange.com/questions/26047/how-to-correctly-add-a-path-to-pathQuando você digita um nome de comando que não é um alias, uma função ou um built-in, o shell procura um arquivo executável com esse nome
$PATH
e o executa. Assim você não precisa declarar o script para o shell, basta soltá-lo no lugar certo.Fazendo uma função
Uma função é um código executado dentro de uma instância de shell existente. Ele tem acesso total a todos os estados do shell: variáveis, diretório atual, funções, histórico de comandos, etc. Você só pode invocar uma função em um shell compatível.
Seu código pode funcionar como uma função, mas você não ganha nada tornando-o uma função e perde a capacidade de invocá-lo de outro lugar (por exemplo, de um gerenciador de arquivos).
No zsh, você pode disponibilizar uma função para sessões interativas incluindo sua definição em
~/.zshrc
. Como alternativa, para evitar a confusão.zshrc
com um número muito grande de funções, você pode usar o mecanismo de carregamento automático. O carregamento automático funciona em duas etapas:autoload -U myfunction
.myfunction
é invocado pela primeira vez, o zsh procura um arquivo chamadomyfunction
nos diretórios listados em$fpath
e usa o primeiro arquivo encontrado como a definição demyfunction
.Todas as funções precisam ser definidas antes do uso. Por isso não basta colocar o arquivo em
$fpath
. Declarar a função comautoload
realmente cria uma definição de stub que diz “carregue esta função$fpath
e tente novamente”:O Zsh tem um mecanismo para gerar esses stubs explorando arquivos
$fpath
. Está embutido no subsistema de conclusão.#autoload
como a primeira linha do arquivo..zshrc
, certifique - se de definir totalmentefpath
antes de chamar a função de inicialização do sistema de conclusãocompinit
.Observe que o arquivo que contém uma definição de função deve conter o corpo da função , não a definição da função, porque o que o zsh executa quando a função é chamada é o conteúdo do arquivo. Então, se você quisesse colocar seu código em uma função, você o colocaria em um arquivo chamado
extract
que está em um dos diretórios em$fpath
, contendoSe você deseja ter um código de inicialização que seja executado quando a função é carregada ou para definir funções auxiliares, você pode usar este idioma (usado na distribuição zsh). Coloque a definição da função no arquivo, mais todas as definições auxiliares e qualquer outro código de inicialização. Ao final, chame a função, passando os argumentos. Então
myfunction
conteria:PS
7z x
funciona na maioria dos tipos de arquivo.Existem várias possibilidades para corrigir esse problema: