Как преобразовать ".." в путевых именах в абсолютные имена в bash-скрипте? - PullRequest
41 голосов
/ 11 июля 2011

Как преобразовать .. в именах путей в абсолютные пути в bash-скрипте.То есть, если у меня есть путь /home/nohsib/dvc/../bop, я хочу, чтобы он был изменен на путь без точек, в этом случае /home/nohsib/bop

Как я могу это сделать?

Ответы [ 9 ]

48 голосов
/ 11 июля 2011

То, что вы ищете, это readlink:

absolute_path=$(readlink -m /home/nohsib/dvc/../bop)

Обратите внимание: Вам необходимо использовать GNU's readlink реализация, которая предлагает опцию "-m".Например, у readlink у BSD нет

33 голосов
/ 11 июля 2011

Попробуйте:

ABSOLUTE_PATH=$(cd /home/nohsib/dvc/../bop; pwd)
8 голосов
/ 03 января 2015

Одна проблема с использованием:

ABSOLUTE_PATH=$(cd ${possibleDirectory}; pwd)

означает, что, если $ {возможный_каталог} не существует, ABSOLUTE_PATH будет установлен в текущий каталог. Что, вероятно, НЕ то, что вы хотите или ожидаете.

Я думаю, что использование этой версии может быть более желательным в целом:

ABSOLUTE_PATH=$(cd ${possibleDirectory} && pwd)

Если $ {возможный_каталог} не существует или недоступен из-за отсутствия разрешений на доступ к каталогу, ABSOLUTE_PATH будет содержать пустую строку.

Преимущество этого состоит в том, что вы можете проверить пустую строку или позволить ей потерпеть неудачу естественным образом, в зависимости от обстоятельств. По умолчанию текущий каталог в случае неудачной команды 'cd' может привести к очень неожиданным и, возможно, катастрофическим результатам (например, rm -rf "$ ABSOLUTE_PATH")

3 голосов
/ 04 июня 2015

Если вы хотите сделать это без каких-либо символических ссылок, попробуйте использовать realpath с параметром -s:

$ realpath -s /home/nohsib/dvc/../bop
/home/nohsib/bop

Обратите внимание, что с realpath, как правило, всено последний компонент должен существовать.Таким образом, чтобы все вышеперечисленное работало, в файловой системе должно присутствовать следующее:

/home
/home/nohsib
/home/nohsib/dvc

Но вы можете обойти это требование, используя опцию -m.

$ realpath -sm /home/nohsib/dvc/../bop
/home/nohsib/bop

(Примечание realpath доступно не во всех системах, особенно в старых системах, отличных от Debian. К сожалению, Busybox realpath не поддерживает переключатели -s или -m.

3 голосов
/ 11 июля 2011

Использование

echo Absolute path: $(cd $1; pwd)
1 голос
/ 11 июля 2011

Просто еще одно примечание: если ваш текущий путь находится под символической ссылкой, вы можете определить истинный путь с помощью этого:

pwd -P

Чтобы решить вашу конкретную проблему, вам нужно будет ввести команду cdизмените каталог на путь без '..' в нем.Обратите внимание, что вы будете в той же папке, только с правильным путем:

cd `pwd -P`
0 голосов
/ 08 октября 2014

одно хорошее решение под оболочкой было бы:

readlink -ev mypathname

Он выводит полное имя пути с разрешенными точками.

0 голосов
/ 08 августа 2013

В качестве альтернативы GNU readlink и realpath я также создал функции, которые будут запускаться в сценариях независимо от внешних команд, таких как pwd и stuffs.

http://www.linuxquestions.org/questions/blog/konsolebox-210384/getting-absolute-paths-of-unix-directories-and-filenames-in-shell-scripts-3956/

Одним из них является этот. Это сохранит абсолютный путь до $ __. Я использовал read там, чтобы быть в безопасности от расширения пути.

function getabspath {
    local -a T1 T2
    local -i I=0
    local IFS=/ A

    case "$1" in
    /*)
        read -r -a T1 <<< "$1"
        ;;
    *)
        read -r -a T1 <<< "/$PWD/$1"
        ;;
    esac

    T2=()

    for A in "${T1[@]}"; do
        case "$A" in
        ..)
            [[ I -ne 0 ]] && unset T2\[--I\]
            continue
            ;;
        .|'')
            continue
            ;;
        esac

        T2[I++]=$A
    done

    case "$1" in
    */)
        [[ I -ne 0 ]] && __="/${T2[*]}/" || __=/
        ;;
    *)
        [[ I -ne 0 ]] && __="/${T2[*]}" || __=/.
        ;;
    esac
}
0 голосов
/ 11 июля 2011

Попробуйте это (при условии, что ваш относительный путь хранится в переменной $ rel_path):

echo "`cd $rel_path; pwd`"
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...