Planification de tâches à l’aide du planificateur Apex
Objectifs de formation
Vidéo de démonstration Trail Together
Vous souhaitez être guidé pas à pas pendant que vous travaillez sur cette étape ? Regardez cette vidéo qui fait partie de la série Trail Together sur Trailhead Live.
(Ce clip commence à 1 h 09 min 53 s, au cas où vous voudriez revenir en arrière et regarder à nouveau le début de l’étape.)
Apex planifié
Le planificateur Apex permet de reporter l’exécution afin de planifier des classes Apex à une heure spécifique. Cette fonctionnalité est idéale pour les tâches de maintenance quotidiennes ou hebdomadaires qui utilisent un Apex par lot. Pour tirer parti du planificateur, écrivez une classe Apex qui implémente l’interface Schedulable
, puis planifiez son exécution à une heure spécifique.
Syntaxe d’un code Apex planifié
Pour invoquer l’exécution de classes Apex à une heure spécifique, commencez par implémenter l’interface Schedulable
pour la classe. Planifiez ensuite l’exécution d’une instance de la classe à une heure spécifique en utilisant la méthode System.schedule()
.
public class SomeClass implements Schedulable { public void execute(SchedulableContext ctx) { // awesome code here } }
La classe implémente l’interface Schedulable
et doit implémenter la seule méthode que cette interface contient, à savoir la méthode execute()
.
Le paramètre de cette méthode est un objet SchedulableContext
. Une fois la classe planifiée, un objet CronTrigger
est créé qui représente la tâche planifiée. Il fournit une méthode getTriggerId()
qui renvoie l’ID d’un objet API CronTrigger
.
Exemple de code
La classe ci-dessous interroge les opportunités ouvertes qui auraient dû être fermées à la date courante, et crée une tâche dans chaque opportunité pour rappeler à son propriétaire de la mettre à jour.
public class RemindOpptyOwners implements Schedulable { public void execute(SchedulableContext ctx) { List<Opportunity> opptys = [SELECT Id, Name, OwnerId, CloseDate FROM Opportunity WHERE IsClosed = False AND CloseDate < TODAY]; // Create a task for each opportunity in the list TaskUtils.remindOwners(opptys); } }
Vous pouvez planifier l’exécution de votre classe par programmation ou depuis l’interface utilisateur du planificateur Apex.
Utilisation de la méthode System.Schedule
Une fois la classe implémentée avec l’interface Schedulable
, utilisez la méthode System.schedule()
pour l’exécuter. La méthode System.schedule()
utilise le fuseau horaire de l’utilisateur pour définir toutes les planifications, mais elle est exécutée en mode système. Cela signifie que toutes les classes sont exécutées, que l’utilisateur soit autorisé à les exécuter ou non.
La méthode System.schedule()
inclut trois arguments : le nom de la tâche, une expression CRON qui représente la date et l’heure d’exécution planifiée de la tâche, et l’instance d’une classe qui implémente l’interface Schedulable
.
RemindOpptyOwners reminder = new RemindOpptyOwners(); // Seconds Minutes Hours Day_of_month Month Day_of_week optional_year String sch = '20 30 8 10 2 ?'; String jobID = System.schedule('Remind Opp Owners', sch, reminder);
Pour plus d’informations sur l’expression CRON utilisée pour la planification, reportez-vous à la section « Using the System.Schedule Method » dans Apex Scheduler.
Planification d’une tâche depuis l’interface utilisateur
- Dans Configuration, saisissez
Apex
dans la case Recherche rapide, puis sélectionnez Classes Apex. - Cliquez sur Planifier Apex.
- Saisissez le nom de la tâche, par exemple
Rappel d’opportunité quotidienne.
- Cliquez sur le bouton de recherche en regard de la classe Apex, puis saisissez le caractère générique
*
pour obtenir la liste de toutes les classes qui peuvent être planifiées. Dans les résultats de recherche, cliquez sur le nom de votre classe planifiée. - Sélectionnez la fréquence
Hebdomadaire
ouMensuelle
, puis définissez la fréquence souhaitée. - Sélectionnez les dates de début et de fin, et une date de début préférée.
- Cliquez sur Enregistrer.
Test d’une méthode Apex planifiée
Comme avec les autres méthodes asynchrones que nous avons présentées, avec la méthode Apex planifiée vous devez vous assurer que la tâche planifiée est terminée avant de tester les résultats. Pour cela, utilisez de nouveau startTest()
et stopTest()
avec la méthode System.schedule()
pour vérifier que le traitement est terminé avant de poursuivre votre test.
@IsTest private class RemindOppyOwnersTest { // Dummy CRON expression: midnight on March 15. // Because this is a test, job executes // immediately after Test.stopTest(). public static String CRON_EXP = '0 0 0 15 3 ? 2042'; @IsTest static void testScheduledJob() { // Create some out of date Opportunity records List<Opportunity> opptys = new List<Opportunity>(); Date closeDate = Date.today().addDays(-7); for (Integer i=0; i<10; i++) { Opportunity o = new Opportunity( Name = 'Opportunity ' + i, CloseDate = closeDate, StageName = 'Prospecting' ); opptys.add(o); } insert opptys; // Get the IDs of the opportunities we just inserted Map<Id, Opportunity> opptyMap = new Map<Id, Opportunity>(opptys); List<Id> opptyIds = new List<Id>(opptyMap.keySet()); Test.startTest(); // Schedule the test job String jobId = System.schedule('ScheduledApexTest', CRON_EXP, new RemindOpptyOwners()); // Verify the scheduled job has not run yet. List<Task> lt = [SELECT Id FROM Task WHERE WhatId IN :opptyIds]; System.assertEquals(0, lt.size(), 'Tasks exist before job has run'); // Stopping the test will run the job synchronously Test.stopTest(); // Now that the scheduled job has executed, // check that our tasks were created lt = [SELECT Id FROM Task WHERE WhatId IN :opptyIds]; System.assertEquals(opptyIds.size(), lt.size(), 'Tasks were not created'); } }
À retenir
- Vous pouvez avoir seulement 100 tâches Apex planifiées à la fois et le nombre maximal d’exécutions Apex planifiées par période de 24 heures est limité. Pour en savoir plus, suivez le lien Execution Governors and Limits de la section Ressources.
- Si vous envisagez de planifier une tâche à partir d’un déclencheur, soyez extrêmement prudent(e). Assurez-vous que le nombre de tâches planifiées ajoutées par le déclencheur ne dépasse pas la limite.
- Les appels externes de service Web synchrones ne sont pas pris en charge depuis une méthode Apex planifiée. Pour exécuter des appels externes, définissez un appel asynchrone en le plaçant dans une méthode annotée avec
@future(callout=true)
, puis appelez cette méthode à partir d’une méthode Apex planifiée. Cependant, si votre méthode Apex planifiée exécute une tâche par lot, les appels externes sont pris en charge depuis la classe par lot.