2011-07-01 78 views
11

如果我在命令行中鍵入crontab -l我可以看到下面一行:如何使用PHP啓動/停止cronjob?

# * * * * * /usr/bin/php /home/user/every_minute_script.php 

開始這個的cronjob,我需要編輯使用crontab -e命令文件,在開始時刪除註釋字符該行,保存編輯後的文件,然後退出編輯器。

stop這個cronjob,同樣的步驟,但是在行首添加註釋字符。

我想要使用PHP腳本而不是手動編輯文件來達到完全相同的效果。

+0

注意:您並未開始/停止作業(您的修改不會影響已經運行的作業),您只需設置它是否會在下次啓動。 – Piskvor

+0

是的。也許有更好的方法來寫這個問題。而不是啓動/停止,也許激活/停用? –

+0

這看起來像http://stackoverflow.com/questions/4421020/use-php-to-create-edit-and-delete-crontab-jobs – ben

回答

10

我做了一些研究和found in a forum,以下消息:

呼叫 「crontab -e命令」 設置爲一個PHP腳本 的EDITOR 環境變量。該腳本可以修改 文件,並在其退出crontab時將 重新讀取並更新文件。

所以,我嘗試了一些,它的工作。我將粘貼下面的工作代碼:

#!/usr/bin/php 
<?php 

$on = "* * * * * /usr/bin/php /home/user/every_minute_script.php\n"; 
$off = "# * * * * * /usr/bin/php /home/user/every_minute_script.php\n"; 

$param = isset($argv[1]) ? $argv[1] : ''; 
$filename = isset($argv[2]) ? $argv[2] : ''; 

if ($param == 'activate') 
{ 
    shell_exec('export EDITOR="/home/user/cron.php on"; crontab -e'); 
} 
elseif($param == 'deactivate') 
{ 
    shell_exec('export EDITOR="/home/user/cron.php off"; crontab -e'); 
} 
elseif(in_array($param, array('on', 'off'))) 
{ 
    if (!is_writable($filename)) 
     exit(); 

    $crontab = file($filename); 
    $key = array_search($param == 'on' ? $off : $on, $crontab); 

    if ($key === false) 
     exit(); 

    $crontab[$key] = $param == 'on' ? $on : $off; 
    sleep(1); 
    file_put_contents($filename, implode('', $crontab)); 
} 

exit(); 

?> 

正因爲如此,我們有一個名爲cron.php單個腳本位於/home/user文件夾,設置爲可執行文件(chmod a+x cron.php)和命令行調用(PHP-CLI) 。後來我會調整它從網絡運行,這是我的意圖。

用法:./cron.php activate使cronjob和./cron.php deactivate禁用它。

腳本正確地設置環境變量EDITOR(自身),然後調用crontab -e,這在其再調用編輯器(也就是現在的相同cron.php腳本)通過臨時crontab文件位置作爲參數。然後,找到並更改正確的crontab行,並保存修改的版本,替換臨時文件。當腳本退出時,crontab將會更新。

這正是我想要的,並符合我的需求。

其他答案很好,可能適合不同的需求和場景,我想感謝每個人的貢獻。

+0

當我執行./cron.php激活我越來越'?php:沒有這樣的文件或目錄錯誤 – Hunt

+0

@Hunt:確保你使用有效的路徑和文件名...你需要改變'/ home/user '爲一條現存的道路 –

2

把你的停止/啓動條件在every_minute_script.php

if($condition == false) { 
    exit(); 
} 
+0

聽起來不錯,我想過了。問題是我需要輸出cronjob給我(不能使用/ dev/null)。在我的設置中,即使在PHP腳本開始時出現「退出」,我也會收到一封電子郵件(每分鐘!)... –

+0

@J。 Bruni:我們所做的是使用包裝器:'* * * * * /x/y/z/blah.sh&>/dev/null';而blah.sh是一個腳本,它運行實際的工作,得到它的輸出,並郵寄,除非沒有輸出。 – Piskvor

+0

@J。布魯尼 - 我以爲只有一封電子郵件,如果有腳本輸出的話? –

2

開始,你可以放置某種邏輯在every_minute_script.php開始,檢查標誌,看它是否應該做些什麼嗎?這樣它可以起飛,然後在沒有工作要做的時候快速停下來。

或者對您而言效率太低?

+0

我剛剛評論過亞當的回答(與你的相似)。這個想法很好,也許是很多場景的最終答案。就我而言,如果可能的話,我寧願不運行'every_minute_script.php'。 –

+0

您可以按照@Piskvor建議的內容做一些事情,只有在腳本實際運行併產生輸出時才發送電子郵件? –

6

Here's一個非常酷的教程,用PHP創建這種功能。

7

而不是crontab中(這是微妙的,動不動就發脾氣)編程搞亂,我建議讓您的every_minute_script.php內檢查:

if (!file_exists('/your/path/run_every_minute_script')) { 
    exit; 
} 

這樣,腳本仍然會開始每分鐘,但如果不滿足條件(/your/path/run_every_minute_script不存在),它將立即終止而不作進一步處理。

(當然,你也可以有替代不同的條件,例如,檢查權限等數據庫)


如果需要輸出郵寄,您可以使用一個包裝腳本。 crontab的:

* * * * * /your/path/wrapper.sh > /dev/null 2> /dev/null 

這個腳本,然後運行該作業正確,收集它的輸出和錯誤,如果這些不爲空,郵寄出來(注意,您也可以使包裝腳本里面的檢查;我們沒有,因爲它依賴於數據庫)。

+0

我喜歡這個解決方案。比搞亂crontab更優雅。 – jahackbeth