Вопрос или проблема
Ситуация: У меня есть bash-скрипт, который предназначен для выполнения с помощью cron. Я тестировал скрипт в терминале, и он работал нормально. Однако после того, как я настроил выполнение скрипта через cron, он начал давать сбои.
Мне потребовалось много сил, чтобы выяснить, что одна из команд в скрипте требует TTY для работы, что не предоставляется в среде выполнения cron. (Для любопытных: команда была docker-compose
, которая выдавала сообщение устройство ввода не является TTY
)
Вопрос: Я все еще хочу найти способ тестировать свои shell-скрипты из терминала перед тем, как настраивать их для cron. Есть ли способ запустить shell-скрипт из терминала так, будто он выполняется cron? Например, cron run_my_command_now 'echo 123'
. Или может быть, есть способ запустить shell-скрипт из терминала так, чтобы скрипт думал, что терминала нет?
На мой взгляд, самый простой способ – это использовать ssh с параметром ‘-T’, чтобы отключить псевдографический терминал.
ssh -T localhost "command"
Это выполнит команду без TTY.
См. страницу man по команде at(1).
at -f /path/to/script_or_command now +5 min
Или что-то похожее на (EOT – это Ctrl-D):
$ at 16:05
warning: commands will be executed using /bin/sh
at> source /my/environment/file
at> /path/to/script
at> <EOT>
job 1 at Mon Feb 14 16:05:00 2022
Чтобы лишить скрипт TTY, связывайте его стандартный ввод с отсутствием ввода, например:
yourscript < /dev/null
или
: | yourscript
Это, конечно, не полностью эмулирует среду cron
; например, переменные окружения будут другими.
Лучший тест для cron
– это просто создать временную задачу cron на 2 минуты от текущего времени, дождаться ее выполнения, обновить время, пока вы тестируете, и удалить ее позже.
Ответ или решение
Чтобы выполнить команду из терминала так, чтобы она исполнялась без TTY (терминального интерфейса), предпочтительно использовать различные методы, которые помогут создать среду, аналогичную той, в которой выполняется задача cron. Это особенно важно при тестировании скриптов, предназначенных для автоматического выполнения через cron, так как определенные команды могут требовать наличия терминала. Рассмотрим несколько подходов.
1. Использование ssh
с опцией -T
Одним из простейших способов запуска команды без TTY является использование ssh
с опцией -T
, которая отключает выделение псевдо-tty:
ssh -T localhost "ваша_команда"
Этот метод удобно применять для быстрого тестирования отдельных команд или скриптов, так как он моделирует окружение, в котором TTY отсутствует.
2. Использование at
для запуска команд
Команда at
позволяет запланировать выполнение команд или скриптов на определенное время и не использует TTY:
at -f /путь/к/вашему_скрипту now + 5 min
Или можно напрямую ввести команды через at
:
at 16:05
at> /путь/к/вашему_скрипту
at> <EOT> # Нажмите Ctrl+D
Данный метод полезен, если вы хотите увидеть, как скрипт будет работать в будущем времени, однако имейте в виду, что он все же будет выполнять команды через /bin/sh
.
3. Перенаправление ввода
Можно лишить скрипт TTY, перенаправив его стандартный ввод в /dev/null
:
ваш_скрипт < /dev/null
Или с помощью команды-пайпы:
: | ваш_скрипт
Это позволяет сохранить выполнение скрипта без ввода с терминала. Однако, это не полностью эмулирует окружение cron, и переменные среды могут быть другими.
4. Тестирование с использованием временных задач cron
Наиболее точный метод тестирования – это временное создание задачи cron. Вы можете создать задачу cron, которая будет выполнена через несколько минут и затем удалить её. Это позволяет вам увидеть выполнение вашего скрипта в реальных условиях:
-
Откройте редактор для редактирования cron задач с помощью команды:
crontab -e
-
Добавьте задачу:
* * * * * /путь/к/вашему_скрипту
-
Сохраните изменения и дождитесь выполнения вашей задачи.
-
По завершении теста удалите запись из crontab.
Заключение
Эти методы позволят вам эффективно тестировать ваши скрипты в среде, аналогичной cron, и помогут избежать проблем, связанных с отсутствием TTY. Подходите к тестированию ответственно, обдумывая детали реализации, чтобы минимизировать возможные ошибки при автоматическом запуске ваших скриптов в будущем. Открытый доступ к вашим скриптам может привести к ненужным проблемам, поэтому всегда тестируйте в контролируемой среде перед развертыванием.