Sunday, November 10, 2019

Scheduling job every 5 min

In salesforce, with UI, we can schedule the job on daily bases, and using cron expression we can do hourly. There is no facility to run the job every minute, or every 5 minutes. However salesforce allows to start the job a few seconds from now or a few minutes from now. We can use that hack to run the job every 5 minutes.

E.g. below : during the execute call, we can reschedule the job, which will abort existing job and create new job based on frequency provided.


/**
 * Created by Chintan Shah on 11/10/2019.
 */

public with sharing class MasterScheduler implements Schedulable  {

    private static final Integer BATCH_FREQUENCY_IN_MINUTES = 5; // ideally it should goto custom settings.
    private static final String JOB_NAME = 'MasterScheduler';

    public void execute(SchedulableContext schedulableContext) {
        System.debug('MasterScheduler.execute : ');
        rescheduleJob( JOB_NAME, BATCH_FREQUENCY_IN_MINUTES );
    }

    public static void rescheduleJob(String jobName, Integer batchFrequencyMinutes) {
        System.debug('MasterScheduler.rescheduleJob : jobName ' + jobName + ' batchFrequencyMinutes ' + batchFrequencyMinutes );
        abortJobByName(jobName);
        Datetime dt = system.now().addMinutes(batchFrequencyMinutes);
        String cronExpression = '0 ' + dt.minute() + ' ' + dt.hour() + ' ' + dt.day() + ' ' + dt.month() + ' ? ' + ' ' + dt.year();
        System.debug('MasterScheduler.rescheduleJob : cronExpression ' + cronExpression );
        System.schedule(jobName, cronExpression, new MasterScheduler());
    }

    public static void abortJobByName(String jobName) {
        System.debug('MasterScheduler.abortJobByName : jobName ' + jobName );
        List<CronTrigger> cronTriggers = [select id, TimesTriggered, NextFireTime, CronExpression, PreviousFireTime, StartTime, EndTime from CronTrigger];
        for(CronTrigger cronTrigger : cronTriggers ) {
            abortJobById(cronTrigger.Id);
        }
    }

    public static void abortJobById(String jobId) {
        System.debug('MasterScheduler.abortJobById : jobId ' + jobId );
        System.abortJob(jobId);
    }


}


We can start the job from anonymous block:


new MasterScheduler().execute(null);

This will run the job every 5 minutes. This is not best practice as we might be over using salesforce cloud resources, but it can come handy for certain situations.

No comments: