Сценарий оболочки не запущен, команда не найдена

Я очень, очень плохо знаком с программированием в UNIX (работаю на MacOSX Mountain Lion через Terminal). Я изучал основы из курса биоинформатики и молекулярных методов (у нас было два класса), где мы в конечном итоге будем использовать Perl и Python для целей управления данными. В любом случае, перед нами была поставлена ​​задача написать скрипт оболочки, чтобы взять данные из группы файлов и записать их в новый файл в формате, который может быть прочитан определенной программой (Migrate-N).

Я получил ряд функций, чтобы делать именно то, что мне нужно, независимо, когда я набираю их в командной строке, но когда я собираю их все вместе в сценарии и пытаюсь запустить его, я получаю ошибку. Вот подробности (прошу прощения за длину):

#! /bin/bash

grep -f Samples.NFCup.txt locus1.fasta > locus1.NFCup.txt
grep -f Samples.NFCup.txt locus2.fasta > locus2.NFCup.txt
grep -f Samples.NFCup.txt locus3.fasta > locus3.NFCup.txt
grep -f Samples.NFCup.txt locus4.fasta > locus4.NFCup.txt
grep -f Samples.NFCup.txt locus5.fasta > locus5.NFCup.txt
grep -f Samples.Salmon.txt locus1.fasta > locus1.Salmon.txt
grep -f Samples.Salmon.txt locus2.fasta > locus2.Salmon.txt
grep -f Samples.Salmon.txt locus3.fasta > locus3.Salmon.txt
grep -f Samples.Salmon.txt locus4.fasta > locus4.Salmon.txt
grep -f Samples.Salmon.txt locus5.fasta > locus5.Salmon.txt
grep -f Samples.Cascades.txt locus1.fasta > locus1.Cascades.txt
grep -f Samples.Cascades.txt locus2.fasta > locus2.Cascades.txt
grep -f Samples.Cascades.txt locus3.fasta > locus3.Cascades.txt
grep -f Samples.Cascades.txt locus4.fasta > locus4.Cascades.txt
grep -f Samples.Cascades.txt locus5.fasta > locus5.Cascades.txt

echo 3 5 Salex_melanopsis > Smelanopsis.mig
echo 656 708 847 1159 779 >> Smelanopsis.mig
echo 154 124 120 74 126 NFCup >> Smelanopsis.mig
cat locus1.NFCup.txt locus2.NFCup.txt locus3.NFCup.txt locus4.NFCup.txt locus5.NFCup.txt >> Smelanopsis.mig
echo 32 30 30 18 38 Salmon River >> Smelanopsis.mig
cat locus1.Salmon.txt locus2.Salmon.txt locus3.Salmon.txt locus4.Salmon.txt locus5.Salmon.txt >> Smelanopsis.mig
echo 56 52 24 29 48 Cascades >> Smelanopsis.mig
cat locus1.Cascades.txt locus2.Cascades.txt locus3.Cascades.txt locus4.Cascades.txt locus5.Cascades.txt >> Smelanopsis.mig

Серия greps просто извлекает данные последовательности ДНК для каждого сайта для каждого локуса в новые текстовые файлы. Файлы Samples...txt содержат идентификационные номера образцов для сайта, файлы.fasta содержат информацию о последовательности, упорядоченную по идентификатору образца; grepping прекрасно работает в командной строке, если я запускаю его по отдельности.

Вторая группа кода создает фактический новый файл, который мне нужен, который заканчивается на.mig. Линии эха - это данные о количестве (базовых пар на локус, популяции в анализе, выборках на сайт и т. Д.), По которым программе требуется информация. Линии кошки должны объединять локус с помощью данных сайта, созданных всеми данными ниже информации о конкретном сайте, продиктованной в строке эха. Вы, без сомнения, получите картину.

Для создания сценария оболочки я начал в Excel, чтобы я мог легко копировать-вставлять / автозаполнять ячейки, сохраняя текст с разделителями табуляции, а затем открывая этот текстовый файл в TextWrangler, чтобы удалить вкладки перед сохранением в виде файла.sh (строка перерывы: Unix (LF) и Encoding: Unicode (UTF-8)) в том же каталоге, что и все файлы, используемые в сценарии. Я пытался использовать chmod +x FILENAME.sh а также chmod u+x FILENAME.sh чтобы убедиться, что это исполняемый файл, но безрезультатно. Даже если я урежу скрипт до одной строки grep (с первой строкой #! / Bin/bash), я не смогу заставить его работать. Процесс занимает всего минуту, когда я набираю его непосредственно в командной строке, поскольку ни один из этих файлов не превышает 160 КБ, а некоторые значительно меньше. Это то, что я печатаю и что получаю, когда пытаюсь запустить файл (HW - правильный каталог)

localhost:HW Mirel$ MigrateNshell.sh
-bash: MigrateNshell.sh: command not found

Я был в этом тупике в течение двух дней, так что любая помощь будет принята с благодарностью! Спасибо!!

13 ответов

По соображениям безопасности оболочка не будет искать в текущем каталоге (по умолчанию) исполняемый файл. Вы должны быть конкретны, и сказать bash что ваш скрипт находится в текущем каталоге (.):

$ ./MigrateNshell.sh

Измените первую строку на следующую, как указал Марк Б

#!/bin/bash 

Затем пометьте скрипт как исполняемый и выполните его из командной строки

chmod +x MigrateNshell.sh
./MigrateNshell.sh

или просто выполните bash из командной строки, передав в сценарии в качестве параметра

/bin/bash MigrateNshell.sh

Убедитесь, что вы не используете "PATH" в качестве переменной, которая переопределит существующий PATH для переменных среды.

Также попробуйте dos2unix сценарий оболочки, потому что иногда он имеет окончания строки Windows и оболочка не распознает его.

$ dos2unix MigrateNshell.sh

Это помогает иногда.

Пытаться chmod u+x MigrateNshell.sh

#! /bin/bash
  ^---

удалить указанное место. Шебанг должен быть

#!/bin/bash

Unix имеет переменную с именем PATH это список каталогов, где можно найти команды.

$ echo $PATH
/usr/local/bin:/usr/bin:/bin:/usr/sbin:/sbin:/usr/local/bin:/Users/david/bin

Если я наберу команду foo в командной строке моя оболочка сначала увидит, есть ли исполняемая команда /usr/local/bin/foo, Если есть, он выполнит /usr/local/bin/foo, Если нет, он увидит, есть ли исполняемая команда /usr/bin/foo и если не там, он будет смотреть, чтобы увидеть, если /bin/foo существует и т.д., пока не доберется до /Users/david/bin/foo,

Если он не может найти команду foo в любом из этих каталогов, скажите мне, команда не найдена.

Есть несколько способов справиться с этой проблемой:

  • Используйте командуbash foo поскольку foo это сценарий оболочки
  • Включите имя каталога при выполнении команды, например /Users/david/foo или же $PWD/foo или просто ./foo,
  • Измени свой $PATH переменная, чтобы добавить каталог, содержащий ваши команды в PATH.

Вы можете изменить $HOME/.bash_profile или же $HOME/.profile если .bash_profile не существует Я сделал это, чтобы добавить в /usr/local/bin который я поместил первым на моем пути. Таким образом, я могу переопределить стандартные команды, которые есть в ОС. Например, у меня есть Ant 1.9.1, но Mac поставляется с Ant 1.8.4. Я положил ant команда в /usr/local/binтак моя версия antвыполнит первым. Я также добавил $HOME/bin до конца пути для моих собственных команд. Если бы у меня был файл, подобный тому, который вы хотите выполнить, я поместил бы его в $HOME/bin, чтобы выполнить его.

Было несколько хороших комментариев о добавлении строки shebang в начало сценария. Я бы хотел добавить рекомендацию по использованию команды env для дополнительной переносимости.

В то время как #!/bin/bash может быть правильное расположение в вашей системе, это не универсальное. Кроме того, это не может быть предпочтительным пользователем bash. #!/usr/bin/env bash выберет первый bash найденный в пути.

Также убедитесь, что /bin/bash является правильным местом для bash .... если вы взяли эту строку из примера где-то, она может не соответствовать вашему конкретному серверу. Если вы указываете неверное местоположение для bash, у вас возникнут проблемы.

Добавьте ниже строки в вашем пути.profile

PATH=$PATH:$HOME/bin:$Dir_where_script_exists

export PATH

Теперь ваш скрипт должен работать без ./

Радж Дагла

Я тоже новичок в сценариях оболочки, но у меня была такая же проблема. Убедитесь, что в конце вашего скрипта у вас есть пустая строка. Иначе это не сработает.

как упоминал @broadmonkey, я проверил наличие bash в bin/ и не смог его там найти. Я пытаюсь запустить сценарий оболочки внутри контейнера докеров. Я увидел, что там есть "sh", поэтому изменил #!/bin/bash на #!/bin/sh, и это сработало.

Первый:

chmod 777 ./MigrateNshell.sh

Затем:

./MigrateNshell.sh

Или добавьте вашу программу в каталог, распознанный в переменной $PATH. Пример: Пример переменной пути, который затем позволит вам вызывать вашу программу без ./

Другие вопросы по тегам