Como posso testar para ver se existe uma aplicação em $ PATH?

18

Estou tentando escrever todos os meus scripts sh startup / env para trabalhar com tanto DRY e quanto: "funciona em todos os * nix em que eu clonei", o quanto possível . Isso significa garantir que, se eu tentar executar um código que não esteja lá, o código falhe normalmente. Para esse fim, preciso testar se existem programas. Eu sei como testar se existe um arquivo, mas não sei como testar para ver se um aplicativo é executável no caminho. Eu prefiro usar o $ PATH, pois alguns deles precisam trabalhar em arch, ubuntu e centos. Alguns podem ser instalados no meu homedir, em sistemas onde não tenho raiz, outros podem não estar instalados e outros ainda podem ser instalados em caminhos de sistema.

    
por xenoterracide 19.12.2010 / 00:26

2 respostas

19

Use type commandname . Isso retorna true se commandname for qualquer coisa executável: alias, função, comando interno ou externo (pesquisado em $PATH ). Como alternativa, use command commandname que retorna true se commandname for interno ou externo comando (pesquisado em $PATH ).

exists () {
  type "$1" >/dev/null 2>/dev/null
}

Existem algumas variantes sh (definitivamente pré-POSIX; eu sei de /bin/sh sob OSF1 ≤3.xe algumas versões do shell Almquist encontradas nas primeiras versões do NetBSD e algumas distribuições Linux do século 20) onde type sempre retorna 0 ou não existe. Eu não acho que nenhum sistema tenha sido enviado com este milênio. Se você alguma vez encontrá-los, aqui está uma função que você pode usar para pesquisar em $PATH manualmente:

exists () { (
    IFS=:
    for d in $PATH; do
      if test -x "$d/$1"; then return 0; fi
    done
    return 1
) }

Esta função é geralmente útil se você quiser excluir funções e itens internos e procurar o nome em $PATH . A maioria dos shells tem um built-in para isso, command -v , embora seja uma adição relativamente recente ao POSIX (ainda opcional a partir do POSIX: 2004). É basicamente uma versão para programadores de type : ele imprime o caminho completo para um executável em $PATH , o nome para um built-in ou função e uma definição de alias para um alias.

exists_in_path () {
  case $(command -v -- "$1") in
    /*) return 0;;
    alias\ *) return 1;; # alias
    *) return 1;; # built-in or function
  esac
}

Ksh, bash e zsh também têm type -p para procurar apenas executáveis em $PATH . Observe que, no bash, o status de retorno de type -p foo é 0 se foo for uma função interna; Se você quiser testar um executável em $PATH , precisará verificar se a saída não está vazia. type -p não está em POSIX; por exemplo o Debian's ash (que é /bin/sh no Ubuntu) não tem isso.

    
por 19.12.2010 / 00:42
1

Se você está apenas procurando por programas externos, você também pode usar qual. Não sei quão portátil é isso.

    
por 19.12.2010 / 07:38