cronのPATH設定はどこにありますか?

cronのPATH設定はどこにありますか?

Cronはcrontabユーザーのパスを使用しませんが、独自のパスを持っています。PATH=/foo/barcrontabの先頭に追加すると簡単に変更できます。一般的な回避策は、常にcronが実行するコマンドの絶対パスを使用することです。しかし、cronのデフォルトPATHはどこで定義されていますか?

Archシステム(cronie 1.5.1-1)で次のコンテンツでcrontabを作成し、Ubuntu 16.04.3 LTSシステムでテストしてみたところ、同じ結果が出ました。

$ crontab -l
* * * * * echo "$PATH" > /home/terdon/fff

出力される内容は次のとおりです。

$ cat fff
/usr/bin:/bin

しかし、なぜ?デフォルトシステムのフルパスが設定されていますが、/etc/profile他のディレクトリも含まれています。

$ grep PATH= /etc/profile
PATH="/usr/local/sbin:/usr/local/bin:/usr/bin"

/etc/environment関連する他のコンテンツがないか、/etc/profile.dcronが別のファイルを読み取ることができると思います。

$ grep PATH= /etc/profile.d/* /etc/environment
/etc/profile.d/jre.sh:export PATH=${PATH}:/usr/lib/jvm/default/bin
/etc/profile.d/mozilla-common.sh:export MOZ_PLUGIN_PATH="/usr/lib/mozilla/plugins"
/etc/profile.d/perlbin.sh:[ -d /usr/bin/site_perl ] && PATH=$PATH:/usr/bin/site_perl
/etc/profile.d/perlbin.sh:[ -d /usr/lib/perl5/site_perl/bin ] && PATH=$PATH:/usr/lib/perl5/site_perl/bin
/etc/profile.d/perlbin.sh:[ -d /usr/bin/vendor_perl ] && PATH=$PATH:/usr/bin/vendor_perl
/etc/profile.d/perlbin.sh:[ -d /usr/lib/perl5/vendor_perl/bin ] && PATH=$PATH:/usr/lib/perl5/vendor_perl/bin
/etc/profile.d/perlbin.sh:[ -d /usr/bin/core_perl ] && PATH=$PATH:/usr/bin/core_perl

当然、どのファイルにも関連性がなく、/etc/skelどのファイルにも設定されていません。/etc/cron*

$ grep PATH /etc/cron* /etc/cron*/*
grep: /etc/cron.d: Is a directory
grep: /etc/cron.daily: Is a directory
grep: /etc/cron.hourly: Is a directory
grep: /etc/cron.monthly: Is a directory
grep: /etc/cron.weekly: Is a directory
/etc/cron.d/0hourly:PATH=/sbin:/bin:/usr/sbin:/usr/bin

それでは、cronユーザーcrontabセットのデフォルトのPATHはどこにありますか?独自にハードコードされていますかcron?これに関する一種の設定ファイルを読みませんか?

答え1

ハードコードされています。ソースコード(このリンクは現在Debianへのものですcron- さまざまな実装を考えると、cron1つを選択するのは難しいですが、他のものも似ています):

#ifndef _PATH_DEFPATH
# define _PATH_DEFPATH "/usr/bin:/bin"
#endif

cronデフォルトパスは設定ファイルから読み込まれません。その理由は、すでにすべてのcronjobで使用されているパス指定をサポートしているため、PATH=他の場所でデフォルトを指定する必要がないためです。 (ハードコーディングされたデフォルト値を使用する作業項目のパスを指定する他の項目がない場合.)

答え2

PATHStephen Kittの回答に加えて、Ubuntuでcronを設定するための設定ファイルがあります。cron 無視するハードコーディングされたデフォルト値を使用しますPATH(またはPATHcrontab自体で設定します)。ファイルは/etc/environment.Note cronPAMの設定です。

$ cat /etc/pam.d/cron
...   
# Read environment variables from pam_env's default files, /etc/environment
# and /etc/security/pam_env.conf.
session       required   pam_env.so

# In addition, read system locale information
session       required   pam_env.so envfile=/etc/default/locale
...

これは確認が簡単です。/etc/environmentたとえば、変数を追加してfoo=barcronjobとして実行し、出力に表示される内容を確認します。env > /tmp/foofoo=bar


しかし、なぜ?デフォルトのシステムフルパスは/ etc / profileに設定されていますが、他のディレクトリも含まれています。

$ grep PATH= /etc/profile
PATH="/usr/local/sbin:/usr/local/bin:/usr/bin"

これはArch Linuxでは本当ですが、Ubuntuではデフォルト設定が 。ファイルが既存のファイルに追加されるPATHことです。/etc/environment/etc/profile.dPATH~/.pam_environmentアーチモーション関連のバグ

残念ながら、/etc/pam.d/cron読み取りは含まれません~/.pam_environment。奇妙なことは、/etc/pam.d/atd する次のファイルが含まれます。

$ cat /etc/pam.d/atd
#
# The PAM configuration file for the at daemon
#

@include common-auth
@include common-account
session    required   pam_loginuid.so
@include common-session-noninteractive
session    required   pam_limits.so
session    required   pam_env.so user_readenv=1

...しかし、渡されたコマンドは、明らかatにタスクが作成されたときに利用可能な環境を継承しますat(たとえば、env -i /usr/bin/at ...きれいな環境でタスクを実行しているように見えます)。

/etc/pam.d/cronhasを修正してもuser_readenv=1何も起こらないようで、 の変数も~/.pam_environment大丈夫になり始めます(PATHもちろんは除く)。


全体として、cronの環境変数を設定するのは面倒です。最高の場所は作業仕様自体のようです。これは、継承された環境変数cronがソースコードを読み取らずに無視することを決定できるかどうかわからないためです。

関連情報