RetryConstraint.java
package com.birbit.android.jobqueue;
/**
* Created by {@link Job#shouldReRunOnThrowable(Throwable, int, int)}.
* <p>
* This object keeps additional data about handling job failures. You can simply use
* {@link #RETRY} or {@link #CANCEL} if you just want to retry or cancel a job. Alternatively,
* you can create your own instance where you can add a delay {@link #setNewDelayInMs(Long)} or
* change Job's prioritiy {@link #setNewPriority(Integer)}.
* <p>
* A common use case is exponentially backing off a Job and you can use
* {@link #createExponentialBackoff(int, long)} method to do that.
*/
@SuppressWarnings("WeakerAccess")
public class RetryConstraint {
public static final RetryConstraint RETRY = new ImmutableRetryConstraint(true);
public static final RetryConstraint CANCEL = new ImmutableRetryConstraint(false);
private boolean retry;
private Long newDelayInMs;
private Integer newPriority;
private boolean applyNewDelayToGroup = false;
public RetryConstraint(boolean retry) {
this.retry = retry;
}
public boolean shouldRetry() {
return retry;
}
/**
* Set whether the Job should be run again or cancelled.
*
* @param retry True if job should be retried, false if it should be cancelled
*/
public void setRetry(boolean retry) {
this.retry = retry;
}
public Long getNewDelayInMs() {
return newDelayInMs;
}
/**
* Sets a timeout until the Job is tried again.
*
* @param newDelayInMs The new delay in Ms from now before retrying the job
*/
public void setNewDelayInMs(Long newDelayInMs) {
this.newDelayInMs = newDelayInMs;
}
public Integer getNewPriority() {
return newPriority;
}
/**
* Updates the Job's priority.
*
* @param newPriority Gives a new priority to the job
*/
public void setNewPriority(Integer newPriority) {
this.newPriority = newPriority;
}
/**
* Creates a response that will exponentially back off the job.
*
* @param runCount The run count that was passed to
* {@link Job#shouldReRunOnThrowable(Throwable, int, int)}
* @param initialBackOffInMs The initial back off time. This will be the back off for the inital
* run and then it will exponentially grow from this number.
*
* @return A RetryContraint that will report exponential back off.
*/
public static RetryConstraint createExponentialBackoff(int runCount, long initialBackOffInMs) {
RetryConstraint constraint = new RetryConstraint(true);
constraint.setNewDelayInMs(initialBackOffInMs *
(long) Math.pow(2, Math.max(0, runCount - 1)));
return constraint;
}
/**
* Sets whether the delay in the constraint should be applied to the whole group.
* <p>
* Note that the delay will effect any Job that is added after this call until the delay ends.
* This will ensure that the Job execution order will be preserved.
* <p>
* If the job does not have a group id ({@link Job#getRunGroupId()}, calling this method has no
* effect.
* <p>
* The group delay is global so even after you cancel the jobs, it will still affect the group
* until delay times out.
*
* @param applyDelayToGroup Sets whether the delay should be applied to all jobs in this group.
*
*/
public void setApplyNewDelayToGroup(boolean applyDelayToGroup) {
this.applyNewDelayToGroup = applyDelayToGroup;
}
/**
* Returns whether the delay in this retry constraint will be applied to all jobs in this group.
*
* @return Whether the delay will be applied to all jobs in this group or not. Defaults to
* false.
*/
@SuppressWarnings("WeakerAccess")
public boolean willApplyNewDelayToGroup() {
return applyNewDelayToGroup;
}
static class ImmutableRetryConstraint extends RetryConstraint {
private static final String MESSAGE = "This object is immutable. Create a new one using the"
+ " constructor.";
public ImmutableRetryConstraint(boolean retry) {
super(retry);
}
@Override
public void setRetry(boolean retry) {
throw new IllegalStateException(MESSAGE);
}
@Override
public void setNewDelayInMs(Long newDelayInMs) {
throw new IllegalStateException(MESSAGE);
}
@Override
public void setNewPriority(Integer newPriority) {
throw new IllegalStateException(MESSAGE);
}
}
}