Запуск задания cron вручную и сразу

(Я уже прочитал Как проверить новый скрипт cron ? .)

У меня есть конкретная проблема (задание cron не запускается или не запускается должным образом), но проблема в целом: я хотел бы отлаживать скрипты, которые выполняются. Я знаю, что я могу настроить строку * * * * * crontab, но это не вполне удовлетворительное решение. Я хотел бы иметь возможность запускать задание cron из командной строки, как если бы cron выполнял его (тот же пользователь, одни и те же переменные среды и т. Д.). Есть ли способ сделать это? Чтобы подождать 60 секунд, чтобы проверить изменения скрипта, это не практично.

93 голоса | спросил Pistos 18 32009vEurope/Moscow11bEurope/MoscowWed, 18 Nov 2009 16:55:43 +0300 2009, 16:55:43

12 ответов


72

Вот что я сделал, и, похоже, он работает в этой ситуации. По крайней мере, это показывает мне ошибку, в то время как выполняется из командной строки, поскольку пользователь не показывает ошибку.


Шаг 1 : я временно помещаю эту строку в crontab пользователя:

* * * * *   /usr/bin/env > /home/username/tmp/cron-env

затем вытащил его после того, как файл был записан.

Шаг 2 . Сделал себе небольшой скрипт bas-as-cron bash, содержащий:

#!/bin/bash
/usr/bin/env -i $(cat /home/username/tmp/cron-env) "[email protected]"

Итак, как пользователь, о котором идет речь, я смог

run-as-cron /the/problematic/script --with arguments --and parameters

Это решение, очевидно, может быть расширено, чтобы использовать sudo или такие для большей гибкости.

Надеюсь, что это поможет другим.

ответил Pistos 18 32009vEurope/Moscow11bEurope/MoscowWed, 18 Nov 2009 17:40:20 +0300 2009, 17:40:20
32

Я представляю решение на основе ответа Pistos, но без недостатков.

  • Добавьте следующую строку в crontab, например. используя crontab -e

    * * * * *  /usr/bin/env > /home/username/cron-env
    
  • Создайте сценарий оболочки, который выполняет команду в той же среде, где выполняются задания cron:

    #!/bin/sh
    
    . "$1"
    exec /usr/bin/env -i "$SHELL" -c ". $1; $2"
    

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

run-as-cron <cron-environment> <command>

например.

run-as-cron /home/username/cron-env 'echo $PATH'

Обратите внимание, что второй аргумент нужно указывать, если для этого требуется аргумент. Первая строка скрипта загружает оболочку POSIX в качестве интерпретатора. Вторая строка содержит файл среды cron. Это необходимо для загрузки правильной оболочки, которая хранится в переменной окружения SHELL. Затем он загружает пустую среду (чтобы предотвратить утечку переменных среды в новую оболочку), запускает ту же оболочку, которая используется для cronjobs и загружает переменные среды cron. Наконец, команда выполнена.

ответил Marco 24 thEurope/Moscowp30Europe/Moscow09bEurope/MoscowTue, 24 Sep 2013 22:46:53 +0400 2013, 22:46:53
14

Поскольку crontab не выполняет эту работу, вы можете манипулировать ее содержимым:

crontab -l | grep -v '^#' | cut -f 6- -d ' ' | while read CMD; do eval $CMD; done

Что он делает:

  • перечисляет задания crontab
  • удалить строки комментариев
  • удалить конфигурацию crontab
  • затем запустите их один за другим.
ответил Django Janny 19 PM000000110000004831 2013, 23:45:48
5

По умолчанию с большинством дефолтных демонах cron, которые я видел, просто нет возможности сообщить cron, чтобы он работал прямо здесь прямо сейчас. Если вы используете anacron, возможно, я думаю, что для запуска отдельного экземпляра на переднем плане.

Если ваши сценарии не работают должным образом, вы не принимаете во внимание, что

  • скрипт работает как конкретный пользователь
  • cron имеет ограниченную среду (наиболее очевидным проявлением этого является другой путь).

Из crontab (5):

  

Установлены несколько переменных среды   автоматически с помощью cron (8)   демон. SHELL установлен в /bin /sh и   LOGNAME и HOME установлены с   /etc /passwd линии crontab   владелец. Для параметра PATH установлено значение «/usr /bin: /bin».   HOME, SHELL и PATH могут быть   переопределение настроек в   кронтаб; LOGNAME является пользователем, что   работа выполняется, и может не быть   изменилось.

В общем, PATH - самая большая проблема, поэтому вам нужно:

  • Явно установить PATH внутри скрипта во время тестирования в /usr /bin: /bin. Вы можете сделать это в bash с помощью export PATH = "/usr /bin: /bin"
  • Явно установить правильный PATH, который вы хотите в верхней части crontab. например PATH = "/usr /bin: /bin: /usr /local /bin: /usr /sbin: /sbin"

Если вам нужно запустить скрипт как другой пользователь без оболочки (например, www-data), используйте sudo:

sudo -u www-data /path/to/crontab-script.sh

Первое, что нужно проверить перед всем этим, конечно, состоит в том, что ваш скрипт фактически выполняет то, что он должен делать из командной строки. Если вы не можете запустить его из командной строки, это, очевидно, не будет работать с cron.

ответил Philip Reynolds 18 32009vEurope/Moscow11bEurope/MoscowWed, 18 Nov 2009 17:27:26 +0300 2009, 17:27:26
1

Ну, пользователь такой же, как тот, который вы вложили в запись crontab (или чей crontab вы положили его поочередно), так что это не проблема. crontab (5) должен предоставить вам список переменных окружения, есть только несколько.

ответил womble 18 32009vEurope/Moscow11bEurope/MoscowWed, 18 Nov 2009 17:04:39 +0300 2009, 17:04:39
1

В большинстве crontab, например, например, vixie-cron вы можете поместить переменные в самом crontab, как это, а затем использовать /usr /bin /env, чтобы проверить, работает ли это. Таким образом, вы можете заставить свой скрипт работать в crontab, как только вы узнаете, что случилось с сценарием run-as-cron.

SHELL=/bin/bash
LANG=en
FASEL=BLA

* * * * *   /usr/bin/env > /home/username/cron-env
ответил Marc Elser 27 +03002014-10-27T09:52:54+03:00312014bEurope/MoscowMon, 27 Oct 2014 09:52:54 +0300 2014, 09:52:54
1

Сценарий Марко по какой-то причине не работал для меня. У меня не было времени на отладку, поэтому я написал скрипт Python, который делает то же самое. Это длиннее, но: во-первых, это работает для меня, а во-вторых, мне легче понять. Измените «/tmp /cron-env» на место, где вы сохранили среду. Вот он:

#!/usr/bin/env python
from __future__ import division, print_function

import sys
import os

def main():
    if len(sys.argv) != 2 or sys.argv[1] in ('-h', '--help'):
        print("Usage: {} CMD\n"
              "Run a command as cron would. Note that CMD must be quoted to be only one argument."
              .format(sys.argv[0]))
        sys.exit(1)
    _me, cmd = sys.argv
    env = dict(line.strip().split('=', 1) for line in open('/tmp/cron-env'))
    sh = env['SHELL']
    os.execvpe(sh, [sh, '-c', cmd], env)

if __name__ == '__main__':
    main()
ответил Noam 24 WedEurope/Moscow2014-12-24T11:48:26+03:00Europe/Moscow12bEurope/MoscowWed, 24 Dec 2014 11:48:26 +0300 2014, 11:48:26
1

Решение Marco не сработало для меня, но работает скрипт python от Noam. Вот небольшая модификация сценария Марко, которая заставила его работать для меня:

#!/bin/sh
. "$1"
exec /usr/bin/env -i "$SHELL" -c "set -a;. $1; $2"

Добавленные переменные экспорта set -a, определенные в скрипте $ 1, и сделали его доступным для команды $ 2

p.s. Питон Noam работал, потому что он «экспортировал» среду в дочерний процесс.

ответил Bill 11 Mayam15 2015, 08:05:59
0

Я никогда не нашел способ запуска заданий cron вручную, но этот файл предлагает установить ту же среду, что и cronjob, и запустить скрипт вручную.

ответил oneodd1 18 32009vEurope/Moscow11bEurope/MoscowWed, 18 Nov 2009 17:07:22 +0300 2009, 17:07:22
0

вы можете запрограммировать задание для запуска в следующую минуту:)

ответил AdrP 23 rdEurope/Moscowp30Europe/Moscow09bEurope/MoscowMon, 23 Sep 2013 17:52:25 +0400 2013, 17:52:25
0

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

sudo su  # (assuming it's run as root, if not switch to the user you want it to run as)
cd  # Switch to home folder
sh <full-path/my-shell-script>

Это определенно выделит некоторые проблемы, если не все.

ответил Matthew Wilcoxson 4 PMpWed, 04 Apr 2018 20:16:31 +030016Wednesday 2018, 20:16:31
-2

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

second, minute, hour, day, * ? *

Например, если вы хотите запустить сегодня (9/20/2016) в 16:30.

0 30 16 20 * ? *

Удостоверьтесь, что вы изменили свое задание cron позже, поскольку это будет работать 20-го числа каждого месяца.

ответил codergal 20 thEurope/Moscowp30Europe/Moscow09bEurope/MoscowTue, 20 Sep 2016 23:24:20 +0300 2016, 23:24:20

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

Популярные теги

security × 330linux × 316macos × 2827 × 268performance × 244command-line × 241sql-server × 235joomla-3.x × 222java × 189c++ × 186windows × 180cisco × 168bash × 158c# × 142gmail × 139arduino-uno × 139javascript × 134ssh × 133seo × 132mysql × 132