2

Working on an android app, I am using FirebaseJobDispatcher to run a job after every 1 minute.

Problem

As soon as i run the app, job executes and then executes after every 1 minute.

Question

Why is onStartJob called immediately when the job is scheduled? Why is it not waiting 1 minute before executing? What am i doing wrong?

Code

public static void scheduleReminders(Context context) {

   Driver driver = new GooglePlayDriver(context);
   FirebaseJobDispatcher dispatcher = new FirebaseJobDispatcher(driver);

   Job job = dispatcher.newJobBuilder()
                    .setService(ReminderJobService.class)
                    .setTag(JOB_TAG)
                    .setConstraints(Constraint.ON_ANY_NETWORK)
                    .setLifetime(Lifetime.FOREVER)
                    .setRecurring(true)
                    .setReplaceCurrent(true)
                    .setRetryStrategy(RetryStrategy.DEFAULT_EXPONENTIAL)
                    .setTrigger(Trigger.executionWindow(60, 65))
                    .build();

   dispatcher.mustSchedule(job);
}

scheduleReminders function is called from onCreate method of the main activity.

  • AFAICT, the `executionWindow()` is merely a hint. The underlying engine being used, based on the driver, may not support all possible values. – CommonsWare Jan 25 '19 at 13:12

1 Answers1

0

The source code of Trigger contains:

  /**
   * Creates a new ExecutionWindow based on the provided time interval.
   *
   * @param windowStart The earliest time (in seconds) the job should be considered eligible to run.
   *     Calculated from when the job was scheduled (for new jobs) or last run (for recurring jobs).
   * @param windowEnd The latest time (in seconds) the job should be run in an ideal world.
   *     Calculated in the same way as {@code windowStart}.
   * @throws IllegalArgumentException if the provided parameters are too restrictive.
   */

Since you are scheduling a recurring job (.setRecurring(true)), the window start time will be since the job was last run, which may cause issues if you're rescheduling a job from a minute ago with no changes, although setReplaceCurrent(true) should avoid the problem.

The more likely cause (as @CommonsWare said) is these triggers aren't perfectly accurate, they're when you'd like the OS to schedule your job, not when it'll actually run. The in an ideal world phrase in the comment above is key!

A way to increase the likelihood of execution happening at the correct time is to increase the window of opportunity the OS has, e.g 50 & 100 seconds instead of 60 & 65. Alternatively if you need something at an exact time, perhaps an Alarm is a better approach.

Jake Lee
  • 7,549
  • 8
  • 45
  • 86