Comment exécuter une fonction toutes les 5 minutes?

15

J'ai une fonction à exécuter toutes les 5 minutes. J'ai fait référence à la suite du codex:

<?php wp_schedule_event(time(), 'hourly', 'my_schedule_hook', $args); ?> 

Je veux exécuter cette fonction tous les 5 menus, quel que soit le moment de commencer. Comment est-ce que je peux cela?

Il indique également que le codex indique que cron sera exécuté lorsqu'un visiteur visitera le site. Existe-t-il un moyen d'exécuter le cron juste comme par minutes et sans attendre une visite?

disons que la fonction suivante doit être exécutée toutes les 5 minutes, alors comment puis-je faire cela en utilisant wp_schedule_event()ou wp_cron?

function run_evry_five_minutes(){
    // codes go here
}
Codeur stupide
la source
Vous feriez mieux d'examiner, par exemple, les services cron Linux ou cron tiers si vous avez besoin d'un intervalle et d'une précision aussi courts,
birgire
le site a un trafic important .. donc pas besoin de considérer l'intervalle de temps .. sûr qu'il sera déclenché toutes les 2 ou 3 minutes .. les clients préfèrent le faire depuisfunctions.php
Foolish Coder
il n'est pas possible de déclencher un fichier php sans que quelque chose ne tourne sur le serveur avec une minuterie.
Andrew Welch
fichier? nous parlons d'une fonction dans functions.php
Foolish Coder
Pensez-vous qu'un service de surveillance gratuit pourrait être le ping qui déclenche CRON? newrelic.com/server-monitoring
jgraup

Réponses:

28

Vous pouvez créer de nouveaux horaires via cron_schedules:

function my_cron_schedules($schedules){
    if(!isset($schedules["5min"])){
        $schedules["5min"] = array(
            'interval' => 5*60,
            'display' => __('Once every 5 minutes'));
    }
    if(!isset($schedules["30min"])){
        $schedules["30min"] = array(
            'interval' => 30*60,
            'display' => __('Once every 30 minutes'));
    }
    return $schedules;
}
add_filter('cron_schedules','my_cron_schedules');

Vous pouvez maintenant planifier votre fonction:

wp_schedule_event(time(), '5min', 'my_schedule_hook', $args);

Pour le planifier une seule fois, enveloppez-le dans une fonction et vérifiez avant de l'exécuter:

$args = array(false);
function schedule_my_cron(){
    wp_schedule_event(time(), '5min', 'my_schedule_hook', $args);
}
if(!wp_next_scheduled('my_schedule_hook',$args)){
    add_action('init', 'schedule_my_cron');
}

Notez le paramètre $ args! Ne pas spécifier le paramètre $ args dans wp_next_scheduled, mais avoir $ args pour wp_schedule_event, provoquera la planification d'un nombre presque infini du même événement (au lieu d'un seul).

Enfin, créez la fonction réelle que vous souhaitez exécuter:

function my_schedule_hook(){
    // codes go here
}

Je pense qu'il est important de mentionner que wp-cron vérifie le calendrier et exécute les travaux planifiés à chaque fois qu'une page est chargée.

Donc, si vous avez un site Web à faible trafic qui n'a qu'un seul visiteur par heure, wp-cron ne fonctionnera que lorsque ce visiteur naviguera sur votre site (une fois par heure). Si vous avez un site à fort trafic avec des visiteurs qui demandent une page toutes les secondes, wp-cron sera déclenché toutes les secondes, provoquant une charge supplémentaire sur le serveur.

La solution consiste à désactiver wp-cron et à le déclencher via une véritable tâche cron dans l'intervalle de temps de la tâche wp-cron planifiée qui se répète le plus rapidement (5 min dans votre cas).

Lucas Rolff explique le problème et donne la solution en détail.

Comme alternative, vous pouvez utiliser un service tiers gratuit comme UptimeRobot pour interroger votre site (et déclencher wp-cron) toutes les 5 minutes, si vous ne souhaitez pas désactiver wp-cron et le déclencher via un véritable travail cron.

Johano Fierra
la source
2

Si votre site reçoit un trafic important, vous pouvez essayer set_transient()de l'exécuter (très approximativement) toutes les 5 minutes, par exemple:

function run_every_five_minutes() {
    // Could probably do with some logic here to stop it running if just after running.
    // codes go here
}

if ( ! get_transient( 'every_5_minutes' ) ) {
    set_transient( 'every_5_minutes', true, 5 * MINUTE_IN_SECONDS );
    run_every_five_minutes();

    // It's better use a hook to call a function in the plugin/theme
    //add_action( 'init', 'run_every_five_minutes' );
}
bonger
la source
Eh bien, euh, ouais?! ...
bonger
ouais., il ne fonctionne pas .. Je l' ai utilisé le code suivant dans functions.phplorsqu'une marque de visite de la page, une mise à jour sera faite à une table dans ma base de données .. function run_evry_five_minutes() { $homepage = file_get_contents('link to visit'); echo $homepage; }. Mais la table DB n'est pas mise à jour même après 6 minutes.
Foolish Coder
Je ne sais pas pourquoi cela ne fonctionne pas pour vous, mais y penser en utilisant simplement get_transient()/ set_transient()sans les trucs cron est beaucoup plus logique, beaucoup plus simple, mettra à jour la réponse ...
bonger
@bonger est-ce une bonne alternative pour wp_schedule_event ()?
Marko Kunic
@ MarkoKunić Je ne sais pas pour être honnête, je ne l'ai pas essayé ... cela n'a été proposé que comme solution de contournement mais si vous l'essayez, faites-le nous savoir ...! (La réponse de Johano Fierra semble bonne wordpress.stackexchange.com/a/216121/57034 )
bonger
2

Vous pouvez le déclencher lors de l'activation du plugin au lieu de chaque appel de plugin:

//Add a utility function to handle logs more nicely.
if ( ! function_exists('write_log')) {
    function write_log ( $log )  {
        if ( is_array( $log ) || is_object( $log ) ) {
            error_log( print_r( $log, true ) );
        } else {
            error_log( $log );
        }
    }
}

/**
 * Do not let plugin be accessed directly
 **/
if ( ! defined( 'ABSPATH' ) ) {
    write_log( "Plugin should not be accessed directly!" );
    exit; // Exit if accessed directly
}

/**
 * -----------------------------------------------------------------------------------------------------------
 * Do not forget to trigger a system call to wp-cron page at least each 30mn.
 * Otherwise we cannot be sure that trigger will be called.
 * -----------------------------------------------------------------------------------------------------------
 * Linux command:
 * crontab -e
 * 30 * * * * wget http://<url>/wp-cron.php
 */

/**
 * Add a custom schedule to wp.
 * @param $schedules array The  existing schedules
 *
 * @return mixed The existing + new schedules.
 */
function woocsp_schedules( $schedules ) {
    write_log("Creating custom schedule.");
    if ( ! isset( $schedules["10s"] ) ) {
        $schedules["10s"] = array(
            'interval' => 10,
            'display'  => __( 'Once every 10 seconds' )
        );
    }

    write_log("Custom schedule created.");
    return $schedules;
}

//Add cron schedules filter with upper defined schedule.
add_filter( 'cron_schedules', 'woocsp_schedules' );

//Custom function to be called on schedule triggered.
function scheduleTriggered() {
    write_log( "Scheduler triggered!" );
}
add_action( 'woocsp_cron_delivery', 'scheduleTriggered' );

// Register an activation hook to perform operation only on plugin activation
register_activation_hook(__FILE__, 'woocsp_activation');
function woocsp_activation() {
    write_log("Plugin activating.");

    //Trigger our method on our custom schedule event.
    if ( ! wp_get_schedule( 'woocsp_cron_delivery' ) ) {
        wp_schedule_event( time(), '10s', 'woocsp_cron_delivery' );
    }

    write_log("Plugin activated.");
}

// Deactivate scheduled events on plugin deactivation.
register_deactivation_hook(__FILE__, 'woocsp_deactivation');
function woocsp_deactivation() {
    write_log("Plugin deactivating.");

    //Remove our scheduled hook.
    wp_clear_scheduled_hook('woocsp_cron_delivery');

    write_log("Plugin deactivated.");
}
Régis Ramillien
la source
1

Je crains qu'à part attendre que quelqu'un visite votre site qui exécute une fonction, la seule autre option consiste à configurer un travail cron sur votre serveur en utilisant quelque chose comme ceci /programming/878600/how -to-create-cronjob-using-bash ou si vous avez une interface de style cpanel sur votre serveur, il y a parfois une interface pour la configurer.

Andrew Welch
la source
ouais,., je comprends que .. J'ai déjà des crons créés à partir de cPnael .. mais maintenant j'essaie d'exécuter une fonction à partir de functions.phpparce que lorsque la fonction est dans un pluginou dans functions.phpnous ne pouvons pas demander aux clients de configurer un cron à partir de cpanel sur leur propre ..
Foolish Coder
1

Le plugin Cronjob Scheduler vous permet d'exécuter des tâches fréquentes de manière fiable et en temps opportun sans que personne n'ait à visiter votre site, tout ce dont vous avez besoin est d'au moins 1 action et d'un calendrier Unix Crontab.

Il est très facile à utiliser et très flexible. Vous créez votre propre fonction et définissez une action en son sein. Ensuite, vous pouvez choisir votre action dans le menu du plugin et la déclencher à tout moment.

Marco
la source
0

J'ai une solution possible en utilisant une fonction de planification et une fonction récursive WP Ajax.

  1. Créer un événement de planification de 60 minutes pour exécuter une fonction
  2. Cette fonction déclenchera une fonction récursive en utilisant Ajax via file_get_contents()
  3. La fonction ajax aura un compteur sur la base de données avec un nombre total de 60 (pour chaque minute dans l'heure).
  4. Cette fonction ajax vérifiera votre compteur pour:

Si le compteur est supérieur ou égal à 60, il réinitialisera le compteur et attendra la prochaine tâche cron.

Si le compteur est multiple de 5 (donc toutes les 5 minutes), il exécutera la fonction souhaitée

Et, en plus des conditions, il dormira pendant 59 secondes sleep(59);(en supposant que votre fonction soit rapide). Après le sommeil, il se déclenchera à file_get_contents()nouveau.

Choses importantes à noter:

  1. Créer un moyen d'interrompre le processus (c'est-à-dire vérifier une valeur sur la base de données)
  2. Créez un moyen d'empêcher 2 processus en même temps
  3. Sur file_get_contents, définissez la limite de temps sur l'en-tête à 2 ou 3 secondes, sinon le serveur peut avoir divers processus n'attendant rien
  4. Vous voudrez peut-être utiliser le set_time_limit(90);pour essayer d'empêcher le serveur d'interrompre votre fonction avant la mise en veille

C'est une solution, pas une bonne, et elle peut être bloquée par le serveur. À l'aide d'un cron externe, vous pouvez définir une fonction simple et le serveur utilisera les ressources une fois toutes les 5 minutes. En utilisant cette solution, le serveur utilisera des ressources dessus tout le temps.

Bruno Cantuaria
la source
0

La réponse de @ johano explique correctement comment configurer un intervalle personnalisé pour le travail cron WP. La deuxième question est cependant sans réponse, qui est de savoir comment exécuter un cron toutes les minutes:

  1. Dans le fichier wp-config.php, ajoutez le code suivant:

    define('DISABLE_WP_CRON', true);
  2. Ajouter un travail cron ( crontab -esous unix / linux):

    1 * * * * wget -q -O - http://example.com/wp-cron.php?doing_wp_cron

La première partie (étape 1) désactivera le travail cron interne WordPress. La deuxième partie (étape 2) exécutera manuellement le travail cron WordPress toutes les minutes.

Avec la réponse de @ Johano (comment exécuter une tâche toutes les 5 minutes) et la mienne (comment exécuter manuellement le cron), vous devriez être en mesure d'atteindre votre objectif.

Mike
la source