web-dev-qa-db-fra.com

Crontab n'exécute pas mon script python

Mon script python ne fonctionne pas sous ma crontab.

J'ai placé ceci dans le script python en haut:
#!/usr/bin/python

J'ai essayé de faire ceci:
chmod a+x myscript.py

Ajouté à ma crontab -e:


    Shell=/bin/bash
    PATH=/sbin:/bin:/usr/sbin:/usr/bin
    MAILTO=""

* * * * * /home/me/project/myscript.py
 </ code>

Mon fichier/var/log/cron dit:
Sep 21 11:53:02 163-dhcp /USR/SBIN/CROND[2489]: (me) CMD (/home/me/project/myscript.py)

Mais mon script ne fonctionne pas car lorsque je vérifie ma base de données SQL, rien n’a changé. Si je le lance directement dans le terminal, comme ceci:

python /home/me/project/myscript.py

J'obtiens le résultat correct.

C'est le myscript.py:

#!/usr/bin/python

import sqlite3

def main():
    con = sqlite3.connect("test.db")

    with con:

        cur = con.cursor()

        cur.execute("CREATE TABLE IF NOT EXISTS testtable(Id INTEGER PRIMARY KEY, Name TEXT)")

        cur.execute("INSERT INTO testtable(Name) VALUES ('BoB')")

        cur.execute("SELECT * FROM testtable")

        print cur.fetchall()


if __== "__main__":
    main()

EDIT: Selon les commentaires: Oui, /usr/bin/python existe. Je peux aussi exécuter le script python directement en utilisant simplement /home/me/project/myscript.py. /usr/bin/python /home/me/project/myscript.py fonctionne. Donc je ne crois pas que ce soit la cause?

24
user1636922

Qu'est-ce qui se passe quand vous tapez 

/home/me/project/myscript.py dans le shell?

Pouvez-vous explicitement utiliser /usr/bin/python dans votre commande crontbb?

Pouvez-vous utiliser un chemin absolu vers votre test.db ou cd vers le bon répertoire puis exécuter votre script python?

Ceci est utile pour avoir des instructions de débogage dans votre python et enregistrer certaines données. Crontab peut être très difficile à déboguer.

19
dm03514

Il est possible que le script ne démarre pas car il ne peut pas localiser l'interpréteur python. L’environnement Crontab peut être très différent de l’environnement Shell que vous utilisez. Les chemins de recherche peuvent être très différents ..__ En outre, vous testez votre script en démarrant l'interpréteur python de manière explicite, tandis que vous vous attendez à ce que la crontab ne lance que le script . J'ai mis cette ligne en haut de mes scripts python: # !/bin/env python. Cette ligne vous aidera à localiser l’interpréteur, quel que soit le répertoire dans lequel il est installé, dans la mesure où il figure dans le chemin de recherche.

13
shargors

Il y a beaucoup de demi-réponses sur Internet, alors j'ai pensé capturer cette information pour sauver du temps à quelqu'un d'autre.

Premièrement, cronjob fait un mauvais travail pour vous dire où cela échoue. Je recommande d’envoyer la sortie stderr dans un fichier journal comme celui-ci:

Commande Crontab:

# m h  dom mon dow   command
* * * * * /path/to/your_file.sh >> out.txt  2>&1

Comme il est probable que la commande soit exécutée en tant qu'utilisateur, vérifiez le répertoire d'origine du fichier journal. Notez que ce script s'exécute toutes les minutes, ce qui est utile pour le débogage. 

Le problème suivant est que vous avez probablement un problème de chemin ... car le script tente probablement de s’exécuter à partir de votre répertoire personnel. Ce script définit le répertoire en cours, le répertorie en fichier, puis exécute votre programme.

Essaye ça :

Fichier de script

#!/bin/sh
cd "$(dirname "$0")";
CWD="$(pwd)"
echo $CWD
python your_python_file.py

J'espère que cela économise du temps de débogage à quelqu'un d'autre !!! 

6
JJSanDiego

Généralement, les problèmes de type crontab de ce type sont dus au fait que la variable d'environnement PATH est plus restrictive/différente de celle de l'environnement PATH de votre utilisateur normal. Puisque votre shell utilise l’environnement PATH pour trouver l’exécutable (par exemple,/usr/bin/python se trouve dans/usr/bin lorsque vous tapez "python" à l’invite du shell), lorsque PATH ne contient pas les emplacements communs, bin ou/usr/sbin, votre travail cron échouera. Cela m'a mordu plusieurs fois. La solution simple consiste simplement à définir explicitement le PATH vous-même près du haut de votre fichier crontab, avant toute commande qui en a besoin. Donc, éditez simplement la crontab comme d'habitude et ajoutez quelque chose comme ceci près du sommet (si votre binaire n'est pas dans l'un des chemins ci-dessous, vous devrez l'ajouter après deux points):

PATH=/usr/local/bin:/usr/bin:/usr/local/sbin:/usr/sbin

Sinon, utilisez simplement des chemins absolus vers vos fichiers binaires et vos scripts dans crontab.

3
JJC

Si vous utilisez anaconda pour python, le chemin à utiliser sera le suivant:

/home/username/anaconda3/bin/python test.py
2
Inder

J'ai eu le même problème. Malgré le fait que le script exécuté manuellement fonctionnait, dans crontab aucune des options mentionnées ci-dessus ne fonctionnait du tout. J'ai déplacé mon script de/home/user/répertoire_script/vers/opt/scripts/et cela a commencé à fonctionner. La cause possible du problème doit être l’accès (en lecture) aux autorisations du sous-dossier situé dans le répertoire de base.

2
charkh

Le moyen le plus simple de gérer cela consiste à ajouter le chemin de votre installation python à PATH en haut du script Shell. Quelque chose comme:

#!/usr/bin/env bash
export PATH="{path to your python installation}:$PATH"
python {python_file_name}.py

Comme @Shargors a dit que vous pouvez le tester en 

env -i /bin/bash --noprofile --norc
1
Hamed Moghaddam

Essaye ça 

* * * * * cd <directory_where_python_file_is> && bin/app etc/app_defaults.yaml

Il y a un problème de chemin avec cron. Ainsi, lorsque vous accédez à un répertoire contenant un fichier python, cron fonctionne à merveille!

1
Taras Vaskiv

C'est généralement parce que le python utilisé par crontab est différent de celui que vous utilisez dans Shell ... La solution la plus simple consiste à:

  1. récupérez le python que vous utilisez dans le shell:

$ which python # it may be "python3" or something else /usr/bin/python

  1. utilisez ce python spécifique dans le fichier crontab:

* * * * * /usr/bin/python test.py

Je souhaite également mentionner que l'utilisation de env -i /bin/bash --noprofile --norc dans le shell vous permet de disposer du même environnement que celui utilisé par crontab, ce qui est extrêmement utile pour le débogage.

1
Brian

Parfois, je suis confronté au même problème. Quoi que j'essaye quelque chose comme conseillé ici, je ne peux pas obtenir le résultat.

Je commence donc à écrire le script bash "trigger" comme suit (appelons-le trigger.sh):

#!/bin/bash

/full_path/python_script.py

Et j'appelle trigger.sh depuis crontab et tout va bien.

EDIT: Bien sûr, n'oubliez pas de faire ce qui suit (donnez le droit d'exécution):

$chmod +x python_script.py
$chmod +x trigger.sh
0
Brainiac
  • Est-ce que l'utilisateur cron (où le script échoue) et l'utilisateur terminal (lorsque le script réussit) sont identiques? 
  • Pouvez-vous rediriger la sortie du travail vers un fichier comme indiqué dans Cron Job Log - How to Log? . Nous pourrions voir si cela aide. 
0
Veerabahu

Essayez de mettre dans votre crontab:

* * * * * python /path/to/your/script.py

plutôt que

* * * * * /path/to/your/script.py

De plus, la ligne Shebang est #!/usr/bin/env python dans certains environnements. env ​​est un exécutable, et vous devez savoir où il se trouve avec "$ which env".

0
xbello

Tandis que les réponses ici définissent clairement le problème et la solution, je voulais ajouter une autre réponse qui m'aidait. 

Si votre script python appelle une base de données, assurez-vous de pouvoir vous connecter correctement à la base de données dans l'enveloppe cron (pour identifier l'enveloppe cron -> https://askubuntu.com/questions/23009/reasons-why- crontab ne fonctionne pas ). J'avais un fichier qui s'exécutait à partir du Shell, mais pas en tant que crontab, sauf si je me connectais à la base de données en tant que racine à partir du script python. 

0
Minnow