web-dev-qa-db-ja.com

cronがジョブを実行するときの「作業ディレクトリ」とは何ですか?

コマンドラインから実行すると機能するスクリプトがありますが、cronを使用してスケジュールすると、ファイルやコマンドが見つからないというエラーが発生します。私の質問は2つあります。

  1. crontab -eを使用してcronジョブをスケジュールすると、権限のベースとして自分のユーザーIDが使用されますか?または、ある種のcronユーザーIDとそれに関連する権限を使用していますか?

  2. Cronジョブが起動したとき、作業ディレクトリは何ですか?実行するスクリプトを指定したディレクトリですか、それとも別のディレクトリですか?

これが私のcronジョブです:

15 7 * * * /home/xxxx/Documents/Scripts/email_ip_script.sh

実際のスクリプトは次のとおりです。

vIP_ADDR="`curl automation.whatismyip.com/n09230945.asp`"
echo "$vIP_ADDR"
sed "s/IPADDR/$vIP_ADDR/g" template.txt > emailmsg.txt
ssmtp [email protected] < emailmsg.txt

mailによって生成されたcronメッセージを表示すると、次のエラーが表示されます。

sed: can't read template.txt: No such file or directory
/home/xxxx/Documents/Scripts/email_ip_script.sh: line 15: ssmtp: command not found

template.txtは見つかりませんが、スクリプトと同じディレクトリにあります。 ssmtpも実行できませんが、ユーザーとしては実行できます。これを適切に機能させるには何が欠けていますか?

182

追加 cd /home/xxxx/Documents/Scripts/ジョブをそのディレクトリで実行する場合。 cronがその特定のディレクトリに移動する理由はありません。 Cronはホームディレクトリでコマンドを実行します。

ssmtpについては、デフォルトのPATHにない可能性があります。 Cronのデフォルトパスは実装に依存しているので、manページを確認してください。ただし、ssmtp/usr/sbinこれはデフォルトのPATHではなく、ルートのみです。

PATH=/usr/local/bin:/usr/bin:/bin:/usr/local/sbin:/usr/sbin:/sbin
15 7 * * * cd /home/xxxx/Documents/Scripts && ./email_ip_script.sh

Cronjobがbashスクリプトの場合、以下はCDでスクリプトの場所に移動します(cron定義で絶対パスを使用していると想定しています)。

cd "$(dirname "$0")";
25
Hugo

質問1に答えるには、crontab -e自分のユーザーとして、ジョブはそのユーザーのcrontabでスケジュールされ、そのユーザーの権限で実行されます。

ただし、ジョブが非対話型シェルで実行されること、つまり、$ PATHがコマンドラインからスクリプトを実行するときの$ PATHと異なる場合があることを考慮する必要があります。

特にat/cronなどでスケジュールする場合は、スクリプトで常にフルパスを使用するのが最善です。

また、表示される問題を正確に回避するために、すべてのファイルへのフルパスを使用することをお勧めします。

競合状態やその他のセキュリティ問題を防ぐには、mktempを使用して、読み取るファイルがスクリプトの外部で変更されていないことを確認する必要もあります。

したがって、スクリプトを次のように変更します。

vIP_ADDR="`curl automation.whatismyip.com/n09230945.asp`"
echo "$vIP_ADDR"
mail_msg=`/bin/mktemp`
/bin/sed "s/IPADDR/$vIP_ADDR/g" /home/xxxx/Documents/Scripts/template.txt > $mailmsg
/path/to/ssmtp [email protected] < $mailmsg
/bin/rm $mailmsg
16
Bram

cronは、各ユーザーのスケジュールされたジョブをそのユーザーとして実行します。これで、ホームディレクトリを基準にしてスクリプトを実行することができます。

別の場所から実行する必要がある場合は、スクリプトでcdを使用してその場所に移動します。

ssmtpは、おそらくcronのデフォルトのPATHにはありません(ほとんどのプラットフォームでは、設計により非常に狭く設定されています)。スクリプトでssmtpへの完全パスを指定するか、a)すべてのスクリプトで使用できるcrontabファイル、またはb)各スクリプトでPATHを明示的に設定できます。

7
D_Bye

チェック this スレッドを使用して、cronの環境を簡単に見つける方法を確認します。これは、インタラクティブシェルで使用するよりもはるかに少ない方法です。何も設定されていないと想定し、自分で明示的に設定するのが最善です。

3
jippie

ジョブの実行におけるcronのデフォルトの作業ディレクトリはホームディレクトリであり、通常は/home/your-user-name

@Kusalanandaの優れたコメントを採用。

一部の人々はそれをほのめかしたりリンクしたりしましたが、私のディストリビューションのmanドキュメントでそれを見つけることができないので見つけるための最良の方法は、これをcronに追加することです

* * * * * echo $PATH > /tmp/lolcronjobs

私の場合、ubuntuはデフォルトで/usr/bin:/binいくつかの問題が発生しました。

0
mschuett