У меня есть сценарий, которые используют хижину: #!/bin/sh
, но когда я выполняю его в своем терминале Ubuntu 14.04, это не работает, и это говорит, что некоторые строки имеют неожиданный оператор.
Мой друг в MacOSX мог запустить тот скрипт с помощью #!/bin/sh
хижина.
Я пытался изменить хижину в #!/usr/bin/env bash
, и внезапно, работы сценария! Что происходит здесь на самом деле?
Я действительно надеюсь, что мог также работать !#/bin/sh
хижина, так, чтобы я не должен был изменять каждый сценарий, который я имею.
Ваш друг на другом компьютере, вероятно, использует ОС, которая имеет /bin/sh
связанный с /bin/bash
. В Ubuntu (на самом деле, Debian и большинство производных Debian), /bin/sh
не связан с /bin/bash
, но к /bin/dash
, который не поддерживает многих bash
- определенные функции, но значительно быстрее.
На дуге Linux:
$ ls -l /bin/sh
lrwxrwxrwx 1 root root 4 Sep 28 15:26 /bin/sh -> bash
На Ubuntu:
$ ls -l /bin/sh
lrwxrwxrwx 1 root root 4 Feb 19 2014 /bin/sh -> dash
Если Вы используете хижину, имеете в виду это. Так как Ваш сценарий содержит bash
- измы, использовать /bin/bash
в хижине. Или напишите портативный, совместимый POSIX код.
Можно ускорить этот процесс при помощи checkbashisms
программа упоминается в этой статье LWN. Это - часть devscripts
пакет, так установите его сначала:
sudo apt-get install devscripts
Таким образом:
checkbashisms /path/to/script.sh || sed -i '1 s;/bin/sh;/bin/bash;' /path/to/script.sh
Можно преобразовать это в сценарий (сказать convert.sh
):
#! /bin/sh
for i
do
checkbashisms "$i"
if [ $? = "1" ]
then
sed -i '1 s;/bin/sh;/bin/bash;' "$i"
fi
done
Определенный код возврата 1
средства это checkbashisms
найденный возможным bash
изм и другие возвращаемые значения указывают на другие проблемы (файл не читаемая, недостающая хижина, и т.д.), таким образом, мы можем проверить на то конкретное возвращаемое значение.
И затем назовите его с:
./convert.sh /path/to/first/script.sh /path/to/second/script.sh
# or
./convert.sh *.sh
# or
find . -iname '*.sh' -exec ./convert.sh {} +
Замена /bin/sh
с символьной ссылкой на /bin/bash
.
Рекомендуемое чтение:
bash
и dash
синтаксис и выставочные изменения необходимы./bin/sh
- подобный.В моем случае проблемой был экспорт IFS
определение переменной в ~/.bashrc (~/.profile)
#Loop over filenames with spaces
export IFS=$'\n'
При изменении на также
export IFS=$' \t\n' #default according to man dash
или
IFS=$'\n'
#!/bin/sh сценарии начал работать снова. В последнем случае определение больше не распространяет к разветвленным процессам/bin/sh. Значение IFS объяснено здесь, и установка его к '\n' вызывает проблемы в сценариях, интерпретируемых оболочкой тире, которая может быть оболочкой по умолчанию /bin/sh -> dash
связанный с в Вашем распределении (например, debian).