Encontre apenas o destino do symlink

46

Para uso em um script de shell, estou procurando uma forma de linha de comando para obter o destino de um link simbólico. O mais próximo que cheguei até agora é stat -N src , que gera src -> dst . É claro que eu poderia analisar a saída e obter dst , mas gostaria de saber se existe alguma maneira direta de obter o destino.

    
por gerrit 10.09.2012 / 16:20

6 respostas

54

Outra opção seria usar o comando especificamente projetado readlink , se disponível.

Por exemplo,

$ readlink -f 'command -v php'
/usr/bin/php7.1
    
por 10.09.2012 / 16:21
14

No Mac OS X e no FreeBSD / NetBSD / etc. é:

stat -f %Y <filename>

Mais genericamente, acho que a solução é (stat --printf =% N usa aspas estranhas):

ls -l b | sed -e 's/.* -> //'

Exemplo:

# ln -s a b
# stat -f %Y b
a

Outro método é:

# find b -maxdepth 0 -printf %l
a#

A última linha é desconfigurada porque não tem nova linha, mas isso é bom se você precisar do resultado em uma variável, assim

# f=$(find b -maxdepth 0 -printf %l)
# echo $f
a

O -maxdepth é necessário para impedir que find entre em diretórios se b for um diretório.

    
por 23.06.2014 / 09:51
3

Isso pode ser feito usando o GNU find : find src -prune -printf "%l\n" .

    
por 10.09.2012 / 16:20
1

Portável: sem sorte, exceto usar heurística para analisar a saída ls -l ou usar perl -le 'print readlink("some-file")'

alguns sistemas têm um comando readlink , alguns com uma opção -f para obter o caminho absoluto.

Existem várias implementações de um comando stat como um wrapper para as chamadas do sistema stat / lstat . O GNU não é útil a esse respeito, mas o de zsh é mais:

zmodload zsh/stat
stat +link the-link

Ainda com o zsh, você pode obter o caminho absoluto de um arquivo (remove cada componente do symlink) com o modificador :A (aplica-se à expansão de variáveis, expansão do histórico e globbing:

~$ gstat -c %N b
'b' -> 'a'
~$ var=b
~$ echo $var:A
/home/me/a
~$ echo b(:A)
/home/me/a
~$ echo ?(@:A)
/home/me/a
    
por 10.09.2012 / 23:12
1

Em um sistema no qual eu não tenho nenhum comando readlink ou stat , mas eu tenho o Python 2.x, estou usando um script curto:

#!/usr/bin/env python

import os, sys

if __name__ == "__main__":
    src = sys.argv[1]
    target = os.readlink(src)
    if not os.path.isabs(target):
            target = os.path.abspath(os.path.join(os.path.dirname(src), target))
    print target

Observe que, diferentemente de readlink -f , isso pode seguir apenas um nível de link simbólico.

    
por 10.07.2018 / 04:28
0

realpath do comando coreutils package,

como vinculado na página de manual do comando readlink .

por exemplo:

realpath /bin/python

saídas

/usr/bin/python2.7

na minha máquina.

    
por 18.01.2017 / 14:52