Cronjobs из Centos в Ubuntu, с трудом

Я перевожу свои VPS-серверы из Centos в Ubuntu. Из-за сообщества (jeej мой первый вопрос к этому сообществу).

У меня cronjobs отлично работают на моих Centos VPS, как это:

01 22 * * * source /home/crawler2/env/bin/activate && cd /home/crawler2/project_spiderrooy && scrapy crawl spiderrooy > /home/crawler2/logs/spiderrooy_log_$(date '+\%Y-\%m-\%d').txt 2>&1

Пробовал это в помете на моем Ubuntu VPS, но это не сработало. Найдите фрагмент в сети (здесь где-то, что bash и dash работают по-разному, поэтому пробовал это:

01 22 * * * "$(command -v bash)" 'source /home/crawler1/env/bin/activate && cd /home/crawler1/project_spiderrooy && scrapy crawl spiderrooy > /home/crawler1/online/flask/static/logs/spiderrooy_log_$(date '+\%Y-\%m-\%d').txt 2>&1'

также не работает, пробовал без записи журнала и все еще не работает. Команды вручную делают работа.

sudo grep CRON / var / log / syslog:

Jan 13 12:11:01 crawler2 CRON[2906]: (crawler2) CMD (-v bash)"  'source /home/crawler2/env/bin/activate && cd /home/crawler2/project_spiderahridderkerk && scrapy crawl spiderahridderkerk')
Jan 13 12:11:01 crawler2 CRON[2905]: (CRON) info (No MTA installed, discarding output)

При всех моих изменениях я никогда не получаю записанный файл журнала или команду, даже без записи журнала logwrite без даты.

Вопрос, как мне запустить этот centos cron в Ubuntu, с датой logwrite и как остановить дерьмо без установленного MTA?

Спасибо.

0
задан 13 January 2018 в 14:46

2 ответа

Вы должны выполнить все, что после $(command -v bash), как команду bash (bash -c ...), в противном случае все это будет рассматриваться как файл (ы) для интерпретации bash.

Do:

"$(command -v bash)" -c 'source ...'

Итак, в crontab:

01 22 * * * "$(command -v bash)" -c 'source ...'
0
ответ дан 13 January 2018 в 14:46

Основная проблема заключается в том, что source представляет собой Bashism - что является проблемой в Ubuntu, потому что оболочкой по умолчанию для cron является /bin/sh - и это разрешает оболочку dash.

Лучший способ справиться с этим зависит от ряда факторов ИМХО. Исправление, которое вы нашли в другом месте, используя command -v bash для явного запуска вашей команды с (полностью квалифицированной) оболочкой bash, является одним из вариантов (хотя, как отмечалось в ответе heemayl , вы пропустили -c перед строкой команды на основе записи системного журнала

Jan 13 12:11:01 crawler2 CRON[2906]: (crawler2) CMD (-v bash)"  'source /home/crawler2/env/bin/activate && cd /home/crawler2/project_spiderahridderkerk && scrapy crawl spiderahridderkerk')

фактически выглядит больше как ваша запись в crontab была

01 22 * * * "($command -v bash)" source /home/crawler1/env/bin/activate && cd /home/crawler1/project_spiderrooy && scrapy crawl spiderrooy > /home/crawler1/online/flask/static/logs/spiderrooy_log_$(date '+\%Y-\%m-\%d').txt 2>&1'

такая, что ($command -v bash) расширилась до ( -v bash), что попытался выполнить -v bash также в подоболочке, вместо того, чтобы запустить command -v bash внутри подстановки команд).

На практике маловероятно (учитывая довольно ограниченный аргумент cron по умолчанию), что обычный bash будет разрешать что-то отличное от $(command -v bash), поэтому IMHO plain bash -c '. . .' или /bin/bash -c '. . .' также будут приемлемы .

В комментариях вы отметили, что вашим собственным решением было добавить SHELL=/bin/bash - лично у меня нет проблем с этим: если вас беспокоят издержки bash по сравнению с dash, вы всегда можете ограничить область действия конкретной записью или группой записи, например,

# default shell
*/3 * * * * /bin/echo "Job 1 run with \$SHELL=$SHELL" >> $HOME/crontab.log

SHELL=/bin/bash
*/5 * * * * /bin/echo "Job 2 run with \$SHELL=$SHELL" >> $HOME/crontab.log

SHELL=/bin/sh
*/7 * * * * /bin/echo "Job 3 run with \$SHELL=$SHELL" >> $HOME/crontab.log

приводит к

$ tail -f ~/crontab.log
Job 1 run with $SHELL=/bin/sh
Job 3 run with $SHELL=/bin/sh
Job 2 run with $SHELL=/bin/bash
Job 1 run with $SHELL=/bin/sh
Job 1 run with $SHELL=/bin/sh
Job 2 run with $SHELL=/bin/bash
Job 3 run with $SHELL=/bin/sh

Наконец, если /home/crawler1/env/bin/activate на самом деле является сценарием POSIX (или его можно сделать относительно легко), а остальные команды в вашей работе являются либо двоичными исполняемыми файлами, либо сценариев со своими собственными действительными строками shebang, тогда вы можете просто изменить команду source на ее эквивалент POSIX ., чтобы все выполнялось в оболочке по умолчанию dash.

1
ответ дан 13 January 2018 в 14:46

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

Похожие вопросы: