既存の環境変数を使用してcronコマンドを実行するにはどうすればよいですか?


114

既存の環境変数を使用してcronコマンドを実行するにはどうすればよいですか?

シェルプロンプトが表示されている場合はecho $ORACLE_HOME、パスを入力して取得できます。これは、環境変数の1つです~/.profile。ただし、~/.profilecronスクリプトがロードされないため、$ORACLE_HOME変数が設定されていないためスクリプトが失敗します。

、この質問の著者は、作成言及~/.cronfilecronのための変数を設定したプロファイルを、その後、彼は彼が彼に続けてスクリプトにすべての彼のcronコマンドをロードするための回避策ありません~/Cronディレクトリを。ファイルのよう~/.cronfileなものは良いアイデアのように聞こえますが、答えの残りの部分は少し扱いに​​くいようで、誰かが同じ結果を得る簡単な方法を教えてくれることを望んでいました。

スクリプトの開始時に次のようなものを追加できると思いますが、source ~/.profileそれは冗長になる可能性があるようです。

では、どのようにしてcronスクリプトに対話型シェルプロファイルから変数を読み込ませることができますか?


source ~/.profileプログラムへの追加はどのように冗長ですか?プログラムは、呼び出し側プログラムから環境を継承します。その呼び出しプログラムがシェルでない場合、子孫プログラムはどのようにして希望する環境を取得しますか?
アルセージュ

私はすでに同様の質問に対する回答をここに書いています。su -lルートまたは他の特定のユーザーの$ PATHを含む通常のログイン環境のセットアップに使用します。
tasket

回答:


141

コマンドを実行する前に、crontabでを追加し. $HOME/.profileます。例えば:

0 5 * * * . $HOME/.profile; /path/to/command/to/run

Cronシェルについて何も知りません。システムによって開始されるため、最小限の環境です。何かが必要な場合は、それを自分自身に持ち込む必要があります。


14
.スクリプトの前に何をしますか?(どうしたらいいかわかりませんman)。どうしてこれと違うのsource
cwd

25
.コマンドは、のために元のコマンドですsource。これらはシェル内では同等であり、特にcrontab内では入力が少し簡単です。詳細情報を取得help .するに^SHELL BUILTIN COMMANDSは、zshbuiltins type のマニュアルページで入力するbashか、トップにman 入力し. Running ます。`は、コマンドが組み込みコマンドであることを示します。
アルケージュ

9
Linuxディストリビューションによっては、変更する必要があります.profileすることによって.bash_profile.profileユーザーのホームディレクトリに存在するファイルを確認します。
フロスティZ

@Arcegeこれは私には機能しません(Fedora Core 21)。これは、シェルレベルが低下するためだと思われます。代わりに、あなたがそれを調達した場合に機能するのは何ですか。
リチャードT

3
動作していない場合は、cronスクリプトのSHELLがbashに設定されていないことが原因である可能性が高いため、期待どおりに実行されていません。
ダニエルファレル

40

私が簡単だと思うもう1つのオプションは、cronでスクリプトを実行し、スクリプトに環境を設定することです。

crontab -eファイルで:

SHELL=/bin/bash

*/1 * * * * $HOME/cron_job.sh

cron_job.shファイル内:

#!/bin/bash
source $HOME/.bash_profile
some_other_cmd

.bash_profileのソースの後のコマンドには、ログインしたかのように環境があります。


5
AWS Linux AMIで実行しているとき、cronが/bin/bashシェルとして使用されないということは私には思いもしませんでした。cd /path/to/project; source .vars手動で入力した場合にそのようなことが機能するのにFile not found、cronジョブに含めると失敗する()のはなぜだろうと思い続けました。私にとって重要なのはSHELL=/bin/bash、各cronジョブで使い慣れたbashコマンドを実際に使用できるように設定することでした。/bin/sh/(デフォルトのcronシェル、明らかに)は非常に制限されています。
ハートレーブロディ

個々の環境変数を指定できるように、cronの上部で環境ファイルを指定できないのは残念です。SystemdにはEnvironmentFileサービスユニットがあります。あまりにも悪いcronには類似したものがありません。
radtek

すべてのスクリプトですべてのcrontabで/ bin / bashを使用するように強制しますが、これはお勧めできません。また、cron行についても説明してください。* / 1 * * * * $ HOME / cron_job.sh…* / 1はWHATに適しています?!?1スターは、それが、これは、今、私はあなたが申し訳ありません...最高の言うことは非常に混乱している厄介な罪と信じているスマートコミュニティの答えとして、毎分/ 1の手段は、毎分実行されますが実行されることを意味します
THESorcerer

1
これは、例と呼ばれるものです。必要に応じて自由に調整するか、まったく使用しないでください。異なる人々のために異なるストローク。
ロバートブリシータ

4
場合$SHELL/bin/shsourceコマンドが存在しません。.代わりに使用してください。
メレ

18

私が見つけやすい別のオプションは、cronでスクリプトを実行し、bashにログインするよう指示することです(したがって、/etc/profile.d/...環境定義を使用します)

crontab -eファイル:

*/1 * * * * bash -l -c './cron_job.sh'
*/1 * * * * bash -l -c 'php -f ./cron_job.php'

のソースの後のコマンドには、.bash_profileログインしたかのように環境があります。


10

悪いアイデア。一般的な方法は、cronジョブから実行されるスクリプトに必要なすべての環境変数を具体的に設定することです。


@fpmurphyに同意します。これにより、セキュリティで保護されたプロセス環境も保証されます。cronから少数の変数のみを設定する場合は、/usr/bin/envコマンドを使用して変数を設定し、cronjobの環境プロセスとして機能できます。
ニキルマーリー

daemontools 'envdirも思い浮かびます。
sr_

6
私はすべてセキュリティのためですが、おそらくファイル~/.cronvarsを作成し、それをプロファイルとcronスクリプトに含めることができます。パスを変更するときに各ファイルのハードコードされたパスを維持するのは簡単ではないため、実行する各スクリプトで環境変数をハードコードしたくありません。そのように思えるので、必要な変数を一元化して、他の変数がロードされないようにします。
cwd

4

この構文は間違いなくあなたを助けます。構文はわかりませんが、機能します。Oracleは、Oracle Configuration Managerをcrontabにデプロイするときにこの構文を使用するため、これが正しいソリューションであると考えています。

0 5 * * * SOME_ENV_VAR=some_value some_command some_parameters

2

最近、cronジョブ全体をrootとして実行する必要があるが、同時に別のユーザーとしてサブコマンドを実行しなければならないケースに遭遇しました(そのユーザーの環境を調達する必要がありました)。私は次のアプローチで行った:

# m  h  dom  mon  dow  user  command
*/5  *   *    *    *   root  (sudo -i -u <the user> command-to-be-run-as-user) && command-to-be-run-as-root

重要な部分は、別のログインシェルで指定されたコマンドを実行するため-iに渡される引数ですsudo(これは、ユーザーのドットファイルが取得されることを意味します)。

PS:user列は/etc/crontab/etc/cron.d/*ファイルでのみ利用可能であることに注意してください。


1

私のために働いた解決策は、ここで説明されています

ラッパースクリプトを作成し、これを呼び出して. ~/.cronfile、必要な処理を行います。このスクリプトは、cronによって起動されます。

では~/.cronfileもしあなたのcronジョブのための環境を指定します。


1

はい、「よく知られている回避策」を使用できます(そのうちのいくつかがリストされています)。これは誰もがそれが安っぽいことを知っているという別の言い方ですが、一部の人々はこれを「セキュリティ機能」と呼んでいます。無駄な時間は無駄ではありませんでした。これはQWERTYキーボードに相当するcronです。

元々の理由はパフォーマンスのためだったのではないかと思われます。1分に1回実行されるスクリプトはrcスクリプトを読むのに時間を費やさないでしょう。また、もともとcronは実際にはまったく設定可能ではなかったため、デフォルトが実際に唯一のオプションでした。

ユーザーが愚かなシェルの体操を行う代わりに、cronがインタラクティブシェルの環境を引き継ぐための簡単な構成や方法がないため、セキュリティが追加されません。最新のマシンでは、毎分実行される膨大な量のジョブがない限り、一般に目に見えるほどのパフォーマンスの向上はありません。

Unixカルチャーは失敗します。私の愚見で。:-)


1
「追加のセキュリティはありません。」それは真実ではありません。見てみましょうCVE-2011-1095CVE-2008-4304、およびCVE-2010-3847を

ところで、私はあなたの答えを断りました。私は通常、新参者の答えを落とさないようにしますが、セキュリティは私にとって重要です。反対票を間違った方法で受け取らないでください。セキュリティに関する部分に加えて、あなたの答えは素晴らしく、賛成に値するでしょう。必要に応じて、ここで回答を編集できます。

これらのいずれも、cronが対話型フラグが設定されたシェルを使用することとは関係ありません。これは純粋なFUDです。残念ながら、私はあなたの下票を下票できません。これは炎のように思えるかもしれませんが、4輪を装着するセキュリティ上の問題があるため、3輪の車の方が良いと考えると非常にイライラします。そうではありません。四輪車を追加することを忘れてしまったので、人々は三輪車に乗ったばかりです。
オースティンS.

別の言い方をすれば、他の回答者が提案した意図された余分なフープのいずれかが使用されている場合、彼らはあなたが言及した穴のいずれにもアクセスできないのですか?「* * * * * exec bash -i -c LOCALE = .......」
オースティンS.

これは暴言のようです。私はそれが質問にどこで答えているかさえ全くわかりません。セキュリティ部分@EvanTeitelmanが削除されたとしても、質問に答えないので、なぜそれが賛成票に値するのかわかりません。
ワイルドカード


1

プロファイルを設定する代わりに、私が助けたのはを設定することPATHでした。一部のコマンドは、cronスクリプトでは使用できないため、使用できませんでしたPATH

ENVIRONMENT=prod
PATH=/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin
*/30 * * * * /opt/myscript1.sh
*/30 * * * * /opt/myscript2.sh
*/30 * * * * /opt/myscript3.sh

PATHコマンドのパスを設定することは私を助けました。テンプレートを使用して、後でテンプレート化を解除できる場合は、

ENVIRONMENT={{ENVIRONMENT}}
PATH={{PATH}}
*/30 * * * * /opt/myscript1.sh
*/30 * * * * /opt/myscript2.sh
*/30 * * * * /opt/myscript3.sh

各アイテムに変数を渡すのは面倒です。


-1

置いた 。~/.dbus/session-bus/*目的のスクリプトの上部にある:)


1
U&L SEへようこそ。読者の利益になるように、回答をさらに広げてください。
ラメシュ14
弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.