Hoe zorg je ervoor dat CRON de juiste PATH’s oproept

Ik probeer cron de juiste PATH’s aan te roepen. Wanneer ik een Python-script vanuit shell uitvoer, werkt het script prima omdat het de PATH’s gebruikt die in bashrc zijn ingesteld, maar als ik cron gebruik, worden niet alle PATH’s vanuit bashrc gebruikt. Is er een bestand waarin ik de PATH’s kan invoeren voor cron zoals bashrc of een manier om de PATH’s vanuit bashrc aan te roepen?

Sorry, ik denk niet dat ik dit correct heb verwoord, ik kan het juiste script laten uitvoeren (wat betekent dat het PATH naar het script in crontab hier niet het probleem is), alleen wanneer dat script wordt uitgevoerd, voer ik een build uit en dit gebruikt de PATH’s die zijn ingesteld in .bashrc. Wanneer ik het script uitvoer terwijl ik ben ingelogd, worden de .bashrcPATH’s binnengehaald. Omdat cron niet in een shell draait, zegt het dat het niet .bashrc. Is er een manier om dit in te voeren zonder een bash-script-wrapper te hoeven schrijven?


Antwoord 1, autoriteit 100%

Ik heb /etc/crontabgebruikt. Ik gebruikte vien voerde de PATH’s in die ik nodig had in dit bestand en voerde het uit als root. De normale crontab overschrijft PATH’s die je hebt ingesteld. Een goede tutorial over hoe u dit moet doen.

Het systeembrede cron-bestand ziet er als volgt uit:

This has the username field, as used by /etc/crontab.
# /etc/crontab: system-wide crontab
# Unlike any other crontab you don't have to run the `crontab'
# command to install the new version when you edit this file.
# This file also has a username field, that none of the other crontabs do.
SHELL=/bin/sh
PATH=/usr/local/sbin:/usr/local/bin:/sbin:/bin:/usr/sbin:/usr/bin
# m h dom mon dow user   command
42 6 * * *   root    run-parts --report /etc/cron.daily
47 6 * * 7   root    run-parts --report /etc/cron.weekly
52 6 1 * *   root    run-parts --report /etc/cron.monthly
01 01 * * 1-5 root python /path/to/file.py

Antwoord 2, autoriteit 26%

Hoogstwaarschijnlijk draait cron in een zeer schaarse omgeving. Controleer de omgevingsvariabelen die cron gebruikt door een dummy-taak toe te voegen die envnaar een bestand als dit dumpt:

* * * * * env > env_dump.txt

Vergelijk dat met de uitvoer van envin een normale shell-sessie.

Je kunt je eigen omgevingsvariabelen toevoegen aan de lokale crontab door ze bovenaan je crontab te definiëren.

Hier is een snelle oplossing om $PATHtoe te voegen aan de huidige crontab:

# echo PATH=$PATH > tmp.cron
# echo >> tmp.cron
# crontab -l >> tmp.cron
# crontab tmp.cron

De resulterende crontab zal lijken op het antwoord van chrissygormley, met PATH gedefinieerd vóór de crontab-regels.


Antwoord 3, autoriteit 12%

Je moet volledige paden in je crontabzetten. Dat is de veiligste optie.
Als je dat niet wilt doen, kun je een wrapper-script om je programma’s plaatsen en daar het PATH instellen.

bijv.

01 01 * * * command

wordt:

01 01 * * * /full/path/to/command

Ook alles dat vanuit cronwordt aangeroepen, moet zeer voorzichtig zijn met de programma’s die het uitvoert en waarschijnlijk zijn eigen keuze instellen voor de variabele PATH.

BEWERKEN:

Als je niet weet waar het commando is dat je wilt uitvoeren which <command>vanuit je shell en het zal je het pad vertellen.

EDIT2:

Dus als uw programma eenmaal draait, moet u als eerste PATHen elke andere vereiste variabele (bijv. LD_LIBRARY_PATH) instellen op de waarden die vereist zijn voor de script om uit te voeren.
In plaats van na te denken over hoe je de cron-omgeving kunt aanpassen om het geschikter te maken voor je programma/script, zorg je ervoor dat je script de gegeven omgeving aankan door een geschikte omgeving in te stellen wanneer het wordt gestart.


Antwoord 4, autoriteit 9%

Het toevoegen van een PATH-definitie aan de gebruikerscrontab met de juiste waarden zal helpen…
Ik heb de mijne gevuld met deze regel bovenaan (na opmerkingen en vóór cron-jobs):

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

En het is genoeg om al mijn scripts te laten werken… Voeg daar eventueel een aangepast pad toe.


Antwoord 5, autoriteit 8%

PATH instellen vlak voor de opdrachtregel in mijn crontab werkte voor mij:

* * * * * PATH=$PATH:/usr/local/bin:/path/to/some/thing

Antwoord 6, autoriteit 8%

Laat uw variabelen voor u werken, dit geeft toegang tot t

Definieer je PATH in /etc/profile.d/*.sh

Systeembrede omgevingsvariabelen

Bestanden met de extensie .sh in de directory /etc/profile.d worden uitgevoerd wanneer een bash-aanmeldingsshell wordt ingevoerd (bijvoorbeeld wanneer u inlogt vanaf de console of via ssh), evenals door de DisplayManager tijdens de desktopsessie laadt.

U kunt bijvoorbeeld het bestand /etc/profile.d/myenvvars.sh maken en variabelen als volgt instellen:

export JAVA_HOME=/usr/lib/jvm/jdk1.7.0
export PATH=$PATH:$JAVA_HOME/bin

Voer crontab uit met login-optie!

CRONTAB voert script of commando uit met omgevingsvariabelen

0 9 * * * cd /var/www/vhosts/foo/crons/; bash -l -c 'php -f ./download.php'
0 9 * * * cd /var/www/vhosts/foo/crons/; bash -l -c download.sh

Antwoord 7, autoriteit 6%

Probleem

Je script werkt als je het vanaf de console uitvoert, maar mislukt in cron.

Oorzaak

Je crontab heeft niet de juiste padvariabelen (en mogelijk shell)

Oplossing

Voeg je huidige shell toe en pad naar de crontab

Script om het voor je te doen

#!/bin/bash
#
# Date: August 22, 2013
# Author: Steve Stonebraker
# File: add_current_shell_and_path_to_crontab.sh
# Description: Add current user's shell and path to crontab
# Source: http://brakertech.com/add-current-path-to-crontab
# Github: hhttps://github.com/ssstonebraker/braker-scripts/blob/master/working-scripts/add_current_shell_and_path_to_crontab.sh
# function that is called when the script exits (cleans up our tmp.cron file)
function finish { [ -e "tmp.cron" ] && rm tmp.cron; }
#whenver the script exits call the function "finish"
trap finish EXIT
########################################
# pretty printing functions
function print_status { echo -e "\x1B[01;34m[*]\x1B[0m $1"; }
function print_good { echo -e "\x1B[01;32m[*]\x1B[0m $1"; }
function print_error { echo -e "\x1B[01;31m[*]\x1B[0m $1"; }
function print_notification { echo -e "\x1B[01;33m[*]\x1B[0m $1"; }
function printline { 
  hr=-------------------------------------------------------------------------------------------------------------------------------
  printf '%s\n' "${hr:0:${COLUMNS:-$(tput cols)}}"
}
####################################
# print message and exit program
function die { print_error "$1"; exit 1; }
####################################
# user must have at least one job in their crontab
function require_gt1_user_crontab_job {
        crontab -l &> /dev/null
        [ $? -ne 0 ] && die "Script requires you have at least one user crontab job!"
}
####################################
# Add current shell and path to user's crontab
function add_shell_path_to_crontab {
    #print info about what's being added
    print_notification "Current SHELL: ${SHELL}"
    print_notification "Current PATH: ${PATH}"
    #Add current shell and path to crontab
    print_status "Adding current SHELL and PATH to crontab \nold crontab:"
    printline; crontab -l; printline
    #keep old comments but start new crontab file
    crontab -l | grep "^#" > tmp.cron
    #Add our current shell and path to the new crontab file
    echo -e "SHELL=${SHELL}\nPATH=${PATH}\n" >> tmp.cron 
    #Add old crontab entries but ignore comments or any shell or path statements
    crontab -l | grep -v "^#" | grep -v "SHELL" | grep -v "PATH" >> tmp.cron
    #load up the new crontab we just created
    crontab tmp.cron
    #Display new crontab
    print_good "New crontab:"
    printline; crontab -l; printline
}
require_gt1_user_crontab_job
add_shell_path_to_crontab

Bron

https://github.com/ssstonebraker/ braker-scripts/blob/master/working-scripts/add_current_shell_and_path_to_crontab.sh

Voorbeelduitvoer

add_curent_shell_and_path_to_crontab.sh voorbeelduitvoer


Antwoord 8

De standaardomgeving voor cron-taken is erg schaars en kan erg verschillen van de omgeving waarin u uw python-scripts ontwikkelt. Voor een script dat in cron kan worden uitgevoerd, moet elke omgeving waarvan u afhankelijk bent expliciet worden ingesteld. Neem in het cron-bestand zelf volledige paden op naar uitvoerbare python-bestanden en naar uw python-scripts.


Antwoord 9

Op mijn AIX pikt cron zijn omgevingsvariabelen op uit /etc/environment en negeert wat is ingesteld in het .profile.

Bewerken: ik heb ook een aantal Linux-boxen van verschillende leeftijden uitgecheckt en deze lijken dit bestand ook te hebben, dus dit is waarschijnlijk niet AIX-specifiek.

Ik heb dit gecontroleerd met behulp van de cron-suggestie van joemaller en de uitvoer gecontroleerd voor en na het bewerken van de PATH-variabele in /etc/environment.


Antwoord 10

Als u niet op verschillende plaatsen dezelfde bewerkingen wilt uitvoeren, doet u dit ongeveer:

* * * * * . /home/username/.bashrc && yourcommand all of your args

De . spatie en dan het pad naar .bashrc en de && commando zijn de magie daar om je omgevingsveranderingen in de running bash-shell te krijgen. Als je echt wilt dat de shell bash is, is het ook een goed idee om een ​​regel in je crontab te hebben:

SHELL=/bin/bash

Ik hoop dat het iemand helpt!


Antwoord 11

@Trevino: uw antwoord heeft me geholpen mijn probleem op te lossen. Echter, voor een beginner, proberen een stapsgewijze benadering te geven.

  1. Verkrijg uw huidige installatie van java via $ echo $JAVA_HOME
  2. $ crontab -e
  3. * * * * * echo $PATH– dit laat je begrijpen wat de PATH-waarde is die momenteel door crontab wordt gebruikt. Voer crontab uit en pak de $PATH-waarde die door crontab wordt gebruikt.
  4. Bewerk nu crontab opnieuw om het gewenste Java-bin-pad in te stellen: a) crontab -e; b) PATH=<value of $JAVA_HOME>/bin:/usr/bin:/bin(het is een voorbeeldpad); c) nu uw geplande taak/script zoals */10 * * * * sh runMyJob.sh &; d) verwijder echo $PATHuit crontab omdat het nu niet nodig is.

Antwoord 12

Stel het vereiste PATH in uw cron in

crontab -e

Bewerken: druk op i

PATH=/usr/local/bin:/usr/local/:or_whatever
10 * * * * your_command

Opslaan en afsluiten :wq


Antwoord 13

De eenvoudigste oplossing die ik heb gevonden, ziet er als volgt uit:

* * * * * root su -l -c command

Dit voorbeeld roept suaan als rootgebruiker en start de shell met de volledige omgeving van de gebruiker, inclusief $PATH, ingesteld alsof ze waren ingelogd. Het werkt hetzelfde op verschillende distributies, is betrouwbaarder dan het sourcen van .bashrc (wat niet voor mij heeft gewerkt) en vermijdt het hardcoderen van specifieke paden, wat een probleem kan zijn als je een voorbeeld of setup-tool levert en niet weet welke distro of bestandsindeling op het systeem van de gebruiker.

U kunt ook de gebruikersnaam opgeven na suals u een andere gebruiker dan root wilt, maar u moet waarschijnlijk de parameter rootvóór sucommando, aangezien dit ervoor zorgt dat suvoldoende rechten heeft om over te schakelen naar elke gebruiker die u opgeeft.


Antwoord 14

Ik weet dat dit al beantwoord is, maar ik dacht dat hij voor sommigen nuttig zou zijn. Ik had een soortgelijk probleem dat ik onlangs heb opgelost (hier gevonden) en hier zijn de hoogtepunten van de stappen die ik heb genomen om deze vraag te beantwoorden:

  1. zorg ervoor dat je de variabelen hebt die je nodig hebt in PYTHONPATH (te vinden hier en hier en voor meer info hier) in de .profile of .bash_profile voor elke shell waarin je je script wilt testen om er zeker van te zijn dat het werkt .

  2. bewerk je crontab om de mappen op te nemen die nodig zijn om je script in een cron-job uit te voeren (hier en hier te vinden)

    a) zorg ervoor dat u de hoofdmap opneemt in de PATH-variabele (.) zoals hier wordt uitgelegd (als u een uitvoerbaar bestand uitvoert met uw opdracht, moet het de hoofdmap kunnen vinden of de map waarin het uitvoerbare bestand is opgeslagen) en waarschijnlijk deze (/sbin:/bin:/usr/sbin:/usr/bin)

  3. maak in je crontab-bestand een cronjob die de map zal veranderen in de map waar je het script eerder met succes hebt uitgevoerd (d.w.z. Gebruikers/gebruiker/Documenten/foo)

    a) Dit ziet er als volgt uit:

    * * * * cd /Users/user/Documents/foo; bar -l doSomething -v 
    

Antwoord 15

Mocht je webmingebruiken, dan zijn dit de stappen om de PATHwaarde in te stellen:

System
  -> Scheduled Cron Jobs
       -> Create a new environment variable
            -> For user: <Select the user name>
            -> Variable name: PATH
            -> Value: /usr/bin:/bin:<your personal path>
            -> Add environment variable: Before all Cron jobs for user

Other episodes