如何以编程方式设置Cron作业?

时间:2014-05-08 14:33:27

标签: php wordpress curl cron

是否可以通过编程方式设置CRON JOB?使用PHP php_curl扩展名?我有以下代码:

function wp_cron_control_call_cron( $blog_address ) {
    $cron_url = $blog_address . '/wp-cron.php?doing_wp_cron';
    $ch = curl_init( $cron_url );
    curl_setopt( $ch, CURLOPT_RETURNTRANSFER, 0 );
    curl_setopt( $ch, CURLOPT_TIMEOUT, '3' );
    $result = curl_exec( $ch );
    curl_close( $ch );
    return $result;
}

无论如何以编程方式在设定的时间间隔内执行此操作?我不是想手动在cPanel中设置CRONTAB或类似的东西。如果可能的话,我希望能够用实际代码完成。这可能吗? curl_setopt中是否有设置可以执行此操作?或者其他一些方式?如果重要的话,使用PHP 5.4.16。

10 个答案:

答案 0 :(得分:4)

How to enable CURL extension

wordpress WP-Cron-Control

Managing Cron Jobs with PHP

每30分钟执行一次cron作业

  

* / 30 * * * * /home/ramesh/backup.sh

注意:以同样的方式,每10分钟使用* / 10,每15分钟使用* / 15,每30分钟使用* / 30等。

  

WordPress Cron间隔

<?php

// Add a new interval of a week
// See http://codex.wordpress.org/Plugin_API/Filter_Reference/cron_schedules

add_filter( 'cron_schedules', 'myprefix_add_weekly_cron_schedule' );
function myprefix_add_weekly_cron_schedule( $schedules ) {
    $schedules['weekly'] = array(
        'interval' => 604800, // 1 week in seconds
        'display'  => __( 'Once Weekly' ),
    );

    return $schedules;
}

// Schedule an action if it's not already scheduled


if ( ! wp_next_scheduled( 'myprefix_my_cron_action' ) ) {
    wp_schedule_event( time(), 'weekly', 'myprefix_my_cron_action' );
}

// Hook into that action that'll fire weekly


add_action( 'myprefix_my_cron_action', 'myprefix_function_to_run' );
function myprefix_function_to_run() {
    // Add some code here
}

?>

完整源代码(将其保存到任何PHP文件并添加到插件文件夹并激活)

<强>功能

wp_schedule_event($time, $interval, $hook, $args);
$time:it Contain TimeStamp Format or when the execute the Event is set Here.time must be in UNIX Time stamp Format.

$interval: it Define When Schedule recoours. Schedule Must Be (hourly,twicedaily,daily)

$hook: name of hoo


<?php
/* 
    Plugin Name:Cron-Job Example
    Version: 1.0
    Author: ravipatel
    Description: Simple Cron-Job Example
    */ 
    register_activation_hook( __FILE__, 'cron_schedule_activate' ); // When Plugin Activate Set Cron-Job
    function cron_schedule_activate()
    {
        wp_schedule_event( time(), 'hourly', 'cron_simple_example_hook' );   //Set Function and Set Schedule as Per Your Requirement
    }
    add_action( 'cron_simple_example_hook', 'cron_simple_example' );    //Add Action

    function cron_simple_example()
    {
        //Add Here Curl Function to submit Data to Site You Want
        $ch = curl_init();
        curl_setopt($ch,CURLOPT_POST,1);
        curl_setopt($ch,CURLOPT_URL,"Your URL");
        curl_setopt($ch,CURLOPT_HEADER,0);
        curl_setopt($ch,CURLOPT_RETURNTRANSFER,1);
        curl_setopt($ch,CURLOPT_TIMEOUT,40);
        curl_setopt($ch,CURLOPT_POSTFIELDS,"POST Parameter Detail");
        curl_exec($ch);
        curl_close($ch);
    }
?>

答案 1 :(得分:4)

为什么不使用cPanel API v2?

cPanel Inc创建了一个Client XML API,猜测是什么..它使用cURL来调用API。

首先获取xmlapi.php文件,现在在xmlapi.php中搜索这些行:

private $port               =   '2087';
private $protocol       =   'https';

为了使其能够在没有root访问权限的情况下使用cPanel帐户,请将$port更改为2083(HTTPS)或2082(HTTP),显然,如果您正在使用HTTP-Port,请更改$protocol到http。

cPanel API有Cron module documentation,您可以删除,添加甚至编辑CronJob。

使用示例

列出所有CronJob:

require_once 'xmlapi.php';

/*
 *  Instanciate the class, setting up username/password/IP
 *  @ip - cPanel server IP, if this script is on the cPanel server replace $ip by $ip = getenv('REMOTE_HOST');
 *  @account - string - your cPanel username
 *  @pass - string - your cPanel password
 */

$ip = '127.0.0.1';
$account = 'username';
$pass = "password";
$xmlapi = new xmlapi($ip, $account, $pass);

/*
 * Just to be sure that XML-API will use the correct port and protocol
 * @set_port(port); change port to 2082 if it isn't redirected to HTTPS and/or using HTTP protocol, else.. use 2083
 * @set_protocol(protocol); change protocol to http if your sever accept HTTP else put the protocol to https
 * @set_output(format); change to XML if you want the result output w/ XML, JSON if you want the result output w/ JSON
 */
$xmlapi->set_port('2083');
$xmlapi->set_protocol('https');
$xmlapi->set_output("json");
$xmlapi->set_debug(1);

/*
 * @api2_query(account, module, function, params)
 */
print $xmlapi->api2_query($account, "Cron", "listcron");

例如,在CronJob中使用一行,它将返回:

{"cpanelresult":{"data":[{"day":"1","minute":"1","hour":"1","count":1,"command_htmlsafe":"/usr/bin/php5","command":"/usr/bin/php5","weekday":"1","month":"1","linekey":"7209fe24c876a729b42a929692c62ce3"},{"count":2}],"apiversion":2,"module":"Cron","event":{"result":1},"func":"listcron"}}

创建一个CronJob

require_once 'xmlapi.php';

/*
 *  Instanciate the class, setting up username/password/IP
 *  @ip - cPanel server IP, if this script is on the cPanel server replace $ip by $ip = getenv('REMOTE_HOST');
 *  @account - string - your cPanel username
 *  @pass - string - your cPanel password
 */

$ip = '127.0.0.1';
$account = 'username';
$pass = "password";
$xmlapi = new xmlapi($ip, $account, $pass);

/*
 * Just to be sure that XML-API will use the correct port and protocol
 * @set_port(port); change port to 2082 if it isn't redirected to HTTPS and/or using HTTP protocol, else.. use 2083
 * @set_protocol(protocol); change protocol to http if your sever accept HTTP else put the protocol to https
 * @set_output(format); change to XML if you want the result output w/ XML, JSON if you want the result output w/ JSON
 */
$xmlapi->set_port('2083');
$xmlapi->set_protocol('https');
$xmlapi->set_output("json");
$xmlapi->set_debug(1);

/*
 *  @command string - The command, script, or program you wish for your cronjob to execute.
 *  @day int - The day on which you would like this crontab entry to run. Wildcards and any acceptable input to a crontab time expression line are allowed here.
 *  @hour int - The hour at which you would like this crontab entry to run. Wildcards and any acceptable input to a crontab time expression line are allowed here.
 *  @minute int - The minute at which you would like this crontab entry to run. Wildcards and any acceptable input to a crontab time expression line are allowed here.
 *  @month int - The month you would like this crontab entry to run. Wildcards and any acceptable input to a crontab time expression line are allowed here.
 *  @weekday int - The weekday on which you would like this crontab entry to run. Wildcards and any acceptable input to a crontab time expression line is allowed here. Acceptable values range from 0 to 6, where 0 represents Sunday and 6 represents Saturday.
 */

$command = "/usr/bin/php cron.php";
$day = "1";
$hour = "1";
$minute = "1";
$month = "1";
$weekday = "1";

/*
 * @api2_query(account, module, function, params)
 */
print $xmlapi->api2_query($account, "Cron", "add_line", array(
    "command"=>$command,
    "day"=>$day,
    "hour"=>$hour,
    "minute"=>$minute,
    "month"=>$month,
    "weekday"=>$weekday
));

显然,它会让你回答:

{"cpanelresult":{"module":"Cron","event":{"result":1},"apiversion":2,"data":[{"statusmsg":"crontab installed","status":1,"linekey":"9b0c93fe238a185e4aa78752a49a0718"}],"func":"add_line"}}

删除CronJob

在解释如何删除CronJob之前,您必须知道要删除的CronJob行。如果您选中&#34;列出所有CronJob&#34;在响应部分,您可能会看到JSON响应中的计数,正是这样:

[{"day":"1","minute":"1","hour":"1","count":1,"command_htmlsafe":"/usr/bin/php5","command":"/usr/bin/php5","weekday":"1","month":"1","linekey":"7209fe24c876a729b42a929692c62ce3"},{"count":2}]

确切的行是"count":1之后的"hour":1和最新"count":2,正如您所理解的那样,该行是...... 第一次(做得很好的sherlock)。

现在我们可以使用与Curl :: remove_line相同的脚本:

require_once 'xmlapi.php';

/*
 *  Instanciate the class, setting up username/password/IP
 *  @ip - cPanel server IP, if this script is on the cPanel server replace $ip by $ip = getenv('REMOTE_HOST');
 *  @account - string - your cPanel username
 *  @pass - string - your cPanel password
 */

$ip = '127.0.0.1';
$account = 'username';
$pass = "password";
$xmlapi = new xmlapi($ip, $account, $pass);

/*
 * Just to be sure that XML-API will use the correct port and protocol
 * @set_port(port); change port to 2082 if it isn't redirected to HTTPS and/or using HTTP protocol, else.. use 2083
 * @set_protocol(protocol); change protocol to http if your sever accept HTTP else put the protocol to https
 * @set_output(format); change to XML if you want the result output w/ XML, JSON if you want the result output w/ JSON
 */
$xmlapi->set_port('2083');
$xmlapi->set_protocol('https');
$xmlapi->set_output("json");
$xmlapi->set_debug(1);

/*
 * @api2_query(account, module, function, params)
 */
print $xmlapi->api2_query($account, "Cron", "remove_line", array(
    "line" => "1"
));

输出:

{"cpanelresult":{"module":"Cron","data":[{"status":1,"statusmsg":"crontab installed"}],"func":"remove_line","apiversion":2,"event":{"result":1}}}

编辑CronJob

重新您需要linekey 行号(称为commandnumber)才能编辑一行,代码完全是除了有一个linekey和line params之外,检查lineline的Cron :: listcron响应,例如:

[{"day":"1","minute":"1","hour":"1","count":1,"command_htmlsafe":"/usr/bin/php5","command":"/usr/bin/php5","weekday":"1","month":"1","linekey":"7209fe24c876a729b42a929692c62ce3"},{"count":2}]

linekey param是7209fe24c876a729b42a929692c62ce3而commandnumber是1(请参阅此处的计数:"hour":"1","count":1

有代码:

require_once 'xmlapi.php';

/*
 *  Instanciate the class, setting up username/password/IP
 *  @ip - cPanel server IP, if this script is on the cPanel server replace $ip by $ip = getenv('REMOTE_HOST');
 *  @account - string - your cPanel username
 *  @pass - string - your cPanel password
 */

$ip = '127.0.0.1';
$account = 'username';
$pass = "password";
$xmlapi = new xmlapi($ip, $account, $pass);

/*
 * Just to be sure that XML-API will use the correct port and protocol
 * @set_port(port); change port to 2082 if it isn't redirected to HTTPS and/or using HTTP protocol, else.. use 2083
 * @set_protocol(protocol); change protocol to http if your sever accept HTTP else put the protocol to https
 * @set_output(format); change to XML if you want the result output w/ XML, JSON if you want the result output w/ JSON
 */
$xmlapi->set_port('2083');
$xmlapi->set_protocol('https');
$xmlapi->set_output("json");
$xmlapi->set_debug(1);

/*
 *  @command string - The command, script, or program you wish for your cronjob to execute.
 *  @commandnumber int - The line of the cron entry to be edited, as reported by listcron. If this is not specified, linekey (see below) must be specified.
 *  @linekey int - The linekey for the entry to be edited, as reported by listcron. If this is not specified, commandnumber (see above) must be specified.
 *  @day int - The day on which you would like this crontab entry to run. Wildcards and any acceptable input to a crontab time expression line are allowed here.
 *  @hour int - The hour at which you would like this crontab entry to run. Wildcards and any acceptable input to a crontab time expression line are allowed here.
 *  @minute int - The minute at which you would like this crontab entry to run. Wildcards and any acceptable input to a crontab time expression line are allowed here.
 *  @month int - The month you would like this crontab entry to run. Wildcards and any acceptable input to a crontab time expression line are allowed here.
 *  @weekday int - The weekday on which you would like this crontab entry to run. Wildcards and any acceptable input to a crontab time expression line is allowed here. Acceptable values range from 0 to 6, where 0 represents Sunday and 6 represents Saturday.
 */

$command = "/usr/bin/php cron.php";
$commandnumber = "1";
$linekey = "7209fe24c876a729b42a929692c62ce3";
$day = "1";
$hour = "2";
$minute = "1";
$month = "1";
$weekday = "1";

/*
 * @api2_query(account, module, function, params)
 */

print $xmlapi->api2_query($account, "Cron", "edit_line", array(
    "command"=>$command,
    "commandnumber"=>$commandnumber,
    "linekey"=>$linekey,
    "day"=>$day,
    "hour"=>$hour,
    "minute"=>$minute,
    "month"=>$month,
    "weekday"=>$weekday
));

PS:如果你使用linekey,你可以将命令行留空,反之亦然。

我说得很简单..但是有很多可能使用POST请求等。

libssh2方式

我找到了一种方法来使用libssh2,checkout here

shell_exec方式

唯一的缺点是共享托管甚至是正确的网站管理员都不会启用shell功能但是......如果启用了,你应该检查here @ajreal提供的解决方案,但它还取决于用户crontab ..

希望这有助于你!

答案 2 :(得分:2)

您可以添加以下php代码:

$mycronjob = "0 * * * * /home/website.com/my.php";

$output = shell_exec('echo "$mycronjob" | crontab -');

您可以根据需要修改$ mycronjob值。

答案 3 :(得分:1)

要在系统上设置“cron作业”,可以通过添加特定格式的新行来修改crontab文件。

来自Wikipedia

# * * * * *  command to execute
# ┬ ┬ ┬ ┬ ┬
# │ │ │ │ │
# │ │ │ │ │
# │ │ │ │ └───── day of week (0 - 7) (0 to 6 are Sunday to Saturday, or use names; 7 is Sunday, the same as 0)
# │ │ │ └────────── month (1 - 12)
# │ │ └─────────────── day of month (1 - 31)
# │ └──────────────────── hour (0 - 23)
# └───────────────────────── min (0 - 59)

所以每30分钟执行一次工作

*/30 * * * * php myscript.php?param1=test

要将此字符串转换为cron作业,需要将其添加到crontab文件中,通过脚本编写quite a few方式people have done this。一旦找到自己喜欢的,就可以使用PHP来执行脚本。

要通过PHP执行此操作,您可以利用shell_exec()函数

$output = shell_exec('SCRIPT GOES HERE');

答案 4 :(得分:1)

尝试这样的事情:

<?php
// ...
$scriptPath = '/path/of/the/phpscript/';
$dayOfWeek = date('w', time());
$hour = date('H', time());
$minute = date('i', time());
$srtCron = "$minute $hour * * $dayOfWeek php $scriptPath";
shell_exec("(crontab -l ; echo $srtCron)| crontab -");
// ...

请记住$ srtCron是:

* * * * *
| | | | |
| | | | ----- Day of week (0 - 7) (Sunday=0 or 7)
| | | ------- Month (1 - 12)
| | --------- Day of month (1 - 31)
| ----------- Hour (0 - 23)
------------- Minute (0 - 59)

一些参考:

Add Jobs To cron Under Linux or UNIX

Appending to crontab with a shell script

答案 5 :(得分:1)

以编程方式从PHP编辑crontab既困难又痛苦。我给你的建议很简单。

  1. 在每分钟运行的crontab中添加1个条目。这个cron将执行PHP脚本。它将是主要的切入点(见第3点)
  2. 创建一个简单的MySQL表,您可以在其中添加/删除/编辑PHP中的条目。此表必须是cron系统字段的副本(列示例:日,月,周,小时,分钟和“要执行的脚本”)
  3. 创建一个连接到MySQL数据库的cron.php脚本(对于第1点)并检查列表(第2点)是否有当前要执行的当前分钟。如果是这样,那么你可以shell_exec()。
  4. 现在你要编辑一个cron?只需编辑你的Mysql表(手动或从PHP脚本)。它应该解决你所有的问题。

答案 6 :(得分:0)

这只是一个例子 你可以访问How can I programmatically create a new cron job?更好地了解命令, 并了解你可以去的玉米 Running a simple shell script as a cronjob

答案 7 :(得分:0)

PHP创建Cronjob

<?php
  $output = shell_exec('crontab -l'); // <- thats an L right there
  file_put_contents('/tmp/crontab.txt', $output . '* * * * * NEW_CRON' . PHP_EOL);
  echo exec('crontab /tmp/crontab.txt');
?>

PHP删除Cronjob

<?php
  echo exec('crontab -r');
?>

这将删除整个 crontab文件。

答案 8 :(得分:0)

你可以试试这个:

ignore_user_abort(1);
ini_set('max_execution_time',0);
$startingtime=date();
for($i=0;$i<1;){
if(date() > $startingtime+[time for cron job]){

CODE TO EXECUTE

}
else{
sleep($startingtime+[time for cron job]-date());
}
}

答案 9 :(得分:-1)

WordPress是否已经内置了伪cron功能?函数wp_schedule_event()似乎在WordPress API中处理您正在描述的内容:

  

安排一个将由WordPress动作核心执行的钩子   在您指定的特定时间间隔内。该动作将在何时触发   如果预定的时间已过,有人会访问您的WordPress网站。   有关挂钩列表,请参阅插件API。

以下是如何设置包含wp_next_scheduled()的小时活动的示例:

add_action( 'wp', 'prefix_setup_schedule' );
/**
 * On an early action hook, check if the hook is scheduled - if not, schedule it.
 */
function prefix_setup_schedule() {
    if ( ! wp_next_scheduled( 'prefix_hourly_event' ) ) {
        wp_schedule_event( time(), 'hourly', 'prefix_hourly_event');
    }
}


add_action( 'prefix_hourly_event', 'prefix_do_this_hourly' );
/**
 * On the scheduled action hook, run a function.
 */
function prefix_do_this_hourly() {
    // do something every hour
}

因此,使用您的示例代码,这应该有效:

add_action( 'wp', 'prefix_setup_schedule' );
/**
 * On an early action hook, check if the hook is scheduled - if not, schedule it.
 */
function prefix_setup_schedule() {
    if ( ! wp_next_scheduled( 'prefix_hourly_event' ) ) {
        wp_schedule_event( time(), 'hourly', 'prefix_hourly_event');
    }
}


add_action( 'prefix_hourly_event', 'wp_cron_control_call_cron' );
/**
 * On the scheduled action hook, run a function.
 */
function wp_cron_control_call_cron( $blog_address ) {
    $cron_url = $blog_address . '/wp-cron.php?doing_wp_cron';
    $ch = curl_init( $cron_url );
    curl_setopt( $ch, CURLOPT_RETURNTRANSFER, 0 );
    curl_setopt( $ch, CURLOPT_TIMEOUT, '3' );
    $result = curl_exec( $ch );
    curl_close( $ch );
    return $result;
}

此外,您可以通过简单地在某处存储时间戳来在普通PHP中执行类似的操作。在DB字段中,或者可能在存储在缓存目录或tmp目录中的文件中。然后只需在每次页面加载时检查该文件 - 例如 - 如果页面加载的时间超出了您检查的时间跨度,请运行任务。

或者不是PHP页面加载,你实际上可以每分钟运行一个真正的cron作业 - 例如 - 它会加载一个PHP页面,然后根据你的需要进行delta比较逻辑。