diff --git a/demos/main/src/main/java/com/google/android/exoplayer2/demo/DemoApplication.java b/demos/main/src/main/java/com/google/android/exoplayer2/demo/DemoApplication.java index 9b72df8d98..560a9be58a 100644 --- a/demos/main/src/main/java/com/google/android/exoplayer2/demo/DemoApplication.java +++ b/demos/main/src/main/java/com/google/android/exoplayer2/demo/DemoApplication.java @@ -101,10 +101,12 @@ public class DemoApplication extends Application { new DownloaderConstructorHelper(getDownloadCache(), buildHttpDataSourceFactory()); downloadManager = new DownloadManager( + this, new File(getDownloadDirectory(), DOWNLOAD_ACTION_FILE), new DefaultDownloaderFactory(downloaderConstructorHelper), MAX_SIMULTANEOUS_DOWNLOADS, - DownloadManager.DEFAULT_MIN_RETRY_COUNT); + DownloadManager.DEFAULT_MIN_RETRY_COUNT, + DownloadManager.DEFAULT_REQUIREMENTS); downloadTracker = new DownloadTracker( /* context= */ this, diff --git a/demos/main/src/main/java/com/google/android/exoplayer2/demo/DownloadTracker.java b/demos/main/src/main/java/com/google/android/exoplayer2/demo/DownloadTracker.java index 08ecdf3be7..559bbcef0f 100644 --- a/demos/main/src/main/java/com/google/android/exoplayer2/demo/DownloadTracker.java +++ b/demos/main/src/main/java/com/google/android/exoplayer2/demo/DownloadTracker.java @@ -41,6 +41,7 @@ import com.google.android.exoplayer2.offline.DownloadService; import com.google.android.exoplayer2.offline.DownloadState; import com.google.android.exoplayer2.offline.ProgressiveDownloadHelper; import com.google.android.exoplayer2.offline.StreamKey; +import com.google.android.exoplayer2.scheduler.Requirements; import com.google.android.exoplayer2.source.TrackGroupArray; import com.google.android.exoplayer2.source.dash.offline.DashDownloadHelper; import com.google.android.exoplayer2.source.hls.offline.HlsDownloadHelper; @@ -159,6 +160,14 @@ public class DownloadTracker implements DownloadManager.Listener { // Do nothing. } + @Override + public void onRequirementsStateChanged( + DownloadManager downloadManager, + Requirements requirements, + @Requirements.RequirementFlags int notMetRequirements) { + // Do nothing. + } + // Internal methods private void loadTrackedActions() { diff --git a/library/core/src/main/java/com/google/android/exoplayer2/offline/DownloadManager.java b/library/core/src/main/java/com/google/android/exoplayer2/offline/DownloadManager.java index c8c02d4980..8932140a34 100644 --- a/library/core/src/main/java/com/google/android/exoplayer2/offline/DownloadManager.java +++ b/library/core/src/main/java/com/google/android/exoplayer2/offline/DownloadManager.java @@ -28,12 +28,15 @@ import static com.google.android.exoplayer2.offline.DownloadState.STATE_STOPPED; import static com.google.android.exoplayer2.offline.DownloadState.STOP_FLAG_DOWNLOAD_MANAGER_NOT_READY; import static com.google.android.exoplayer2.offline.DownloadState.STOP_FLAG_STOPPED; +import android.content.Context; import android.os.ConditionVariable; import android.os.Handler; import android.os.HandlerThread; import android.os.Looper; import android.support.annotation.Nullable; import com.google.android.exoplayer2.C; +import com.google.android.exoplayer2.scheduler.Requirements; +import com.google.android.exoplayer2.scheduler.RequirementsWatcher; import com.google.android.exoplayer2.util.Assertions; import com.google.android.exoplayer2.util.Log; import java.io.File; @@ -74,18 +77,35 @@ public final class DownloadManager { * @param downloadManager The reporting instance. */ void onIdle(DownloadManager downloadManager); + + /** + * Called when the download requirements state changed. + * + * @param downloadManager The reporting instance. + * @param requirements Requirements needed to be met to start downloads. + * @param notMetRequirements {@link Requirements.RequirementFlags RequirementFlags} that are not + * met, or 0. + */ + void onRequirementsStateChanged( + DownloadManager downloadManager, + Requirements requirements, + @Requirements.RequirementFlags int notMetRequirements); } /** The default maximum number of simultaneous downloads. */ public static final int DEFAULT_MAX_SIMULTANEOUS_DOWNLOADS = 1; /** The default minimum number of times a download must be retried before failing. */ public static final int DEFAULT_MIN_RETRY_COUNT = 5; + /** The default requirement is that the device has network connectivity. */ + public static final Requirements DEFAULT_REQUIREMENTS = + new Requirements(Requirements.NETWORK_TYPE_ANY, false, false); private static final String TAG = "DownloadManager"; private static final boolean DEBUG = false; private final int maxActiveDownloads; private final int minRetryCount; + private final Context context; private final ActionFile actionFile; private final DownloaderFactory downloaderFactory; private final ArrayList downloads; @@ -99,31 +119,43 @@ public final class DownloadManager { private boolean initialized; private boolean released; @DownloadState.StopFlags private int stickyStopFlags; + private RequirementsWatcher requirementsWatcher; /** * Constructs a {@link DownloadManager}. * + * @param context Any context. * @param actionFile The file in which active actions are saved. * @param downloaderFactory A factory for creating {@link Downloader}s. */ - public DownloadManager(File actionFile, DownloaderFactory downloaderFactory) { + public DownloadManager(Context context, File actionFile, DownloaderFactory downloaderFactory) { this( - actionFile, downloaderFactory, DEFAULT_MAX_SIMULTANEOUS_DOWNLOADS, DEFAULT_MIN_RETRY_COUNT); + context, + actionFile, + downloaderFactory, + DEFAULT_MAX_SIMULTANEOUS_DOWNLOADS, + DEFAULT_MIN_RETRY_COUNT, + DEFAULT_REQUIREMENTS); } /** * Constructs a {@link DownloadManager}. * + * @param context Any context. * @param actionFile The file in which active actions are saved. * @param downloaderFactory A factory for creating {@link Downloader}s. * @param maxSimultaneousDownloads The maximum number of simultaneous downloads. * @param minRetryCount The minimum number of times a download must be retried before failing. + * @param requirements The requirements needed to be met to start downloads. */ public DownloadManager( + Context context, File actionFile, DownloaderFactory downloaderFactory, int maxSimultaneousDownloads, - int minRetryCount) { + int minRetryCount, + Requirements requirements) { + this.context = context.getApplicationContext(); this.actionFile = new ActionFile(actionFile); this.downloaderFactory = downloaderFactory; this.maxActiveDownloads = maxSimultaneousDownloads; @@ -146,10 +178,30 @@ public final class DownloadManager { listeners = new CopyOnWriteArraySet<>(); actionQueue = new ArrayDeque<>(); + watchRequirements(requirements); loadActions(); logd("Created"); } + /** + * Sets the requirements needed to be met to start downloads. + * + * @param requirements Need to be met to start downloads. + */ + public void setRequirements(Requirements requirements) { + Assertions.checkState(!released); + if (requirements.equals(requirementsWatcher.getRequirements())) { + return; + } + requirementsWatcher.stop(); + notifyListenersRequirementsStateChange(watchRequirements(requirements)); + } + + /** Returns the requirements needed to be met to start downloads. */ + public Requirements getRequirements() { + return requirementsWatcher.getRequirements(); + } + /** * Adds a {@link Listener}. * @@ -278,6 +330,9 @@ public final class DownloadManager { } setStopFlags(STOP_FLAG_DOWNLOAD_MANAGER_NOT_READY); released = true; + if (requirementsWatcher != null) { + requirementsWatcher.stop(); + } final ConditionVariable fileIOFinishedCondition = new ConditionVariable(); fileIOHandler.post(fileIOFinishedCondition::open); fileIOFinishedCondition.block(); @@ -346,6 +401,15 @@ public final class DownloadManager { } } + private void notifyListenersRequirementsStateChange( + @Requirements.RequirementFlags int notMetRequirements) { + logdFlags("Not met requirements are changed", notMetRequirements); + for (Listener listener : listeners) { + listener.onRequirementsStateChanged( + DownloadManager.this, requirementsWatcher.getRequirements(), notMetRequirements); + } + } + private void loadActions() { fileIOHandler.post( () -> { @@ -420,6 +484,18 @@ public final class DownloadManager { } } + @Requirements.RequirementFlags + private int watchRequirements(Requirements requirements) { + requirementsWatcher = new RequirementsWatcher(context, new RequirementListener(), requirements); + @Requirements.RequirementFlags int notMetRequirements = requirementsWatcher.start(); + if (notMetRequirements == 0) { + startDownloads(); + } else { + stopDownloads(); + } + return notMetRequirements; + } + private static final class Download { private final String id; @@ -693,4 +769,20 @@ public final class DownloadManager { return Math.min((errorCount - 1) * 1000, 5000); } } + + private class RequirementListener implements RequirementsWatcher.Listener { + @Override + public void requirementsMet(RequirementsWatcher requirementsWatcher) { + startDownloads(); + notifyListenersRequirementsStateChange(0); + } + + @Override + public void requirementsNotMet( + RequirementsWatcher requirementsWatcher, + @Requirements.RequirementFlags int notMetRequirements) { + stopDownloads(); + notifyListenersRequirementsStateChange(notMetRequirements); + } + } } diff --git a/library/core/src/main/java/com/google/android/exoplayer2/offline/DownloadService.java b/library/core/src/main/java/com/google/android/exoplayer2/offline/DownloadService.java index 3031a032db..d424ed5ef0 100644 --- a/library/core/src/main/java/com/google/android/exoplayer2/offline/DownloadService.java +++ b/library/core/src/main/java/com/google/android/exoplayer2/offline/DownloadService.java @@ -25,8 +25,8 @@ import android.os.Looper; import android.support.annotation.Nullable; import android.support.annotation.StringRes; import com.google.android.exoplayer2.scheduler.Requirements; -import com.google.android.exoplayer2.scheduler.RequirementsWatcher; import com.google.android.exoplayer2.scheduler.Scheduler; +import com.google.android.exoplayer2.util.Assertions; import com.google.android.exoplayer2.util.Log; import com.google.android.exoplayer2.util.NotificationUtil; import com.google.android.exoplayer2.util.Util; @@ -43,10 +43,6 @@ public abstract class DownloadService extends Service { /** Starts a download service, adding a new {@link DownloadAction} to be executed. */ public static final String ACTION_ADD = "com.google.android.exoplayer.downloadService.action.ADD"; - /** Reloads the download requirements. */ - public static final String ACTION_RELOAD_REQUIREMENTS = - "com.google.android.exoplayer.downloadService.action.RELOAD_REQUIREMENTS"; - /** Like {@link #ACTION_INIT}, but with {@link #KEY_FOREGROUND} implicitly set to true. */ private static final String ACTION_RESTART = "com.google.android.exoplayer.downloadService.action.RESTART"; @@ -70,20 +66,16 @@ public abstract class DownloadService extends Service { private static final String TAG = "DownloadService"; private static final boolean DEBUG = false; - // Keep the requirements helper for each DownloadService as long as there are downloads (and the - // process is running). This allows downloads to resume when there's no scheduler. It may also - // allow downloads the resume more quickly than when relying on the scheduler alone. - private static final HashMap, RequirementsHelper> - requirementsHelpers = new HashMap<>(); - private static final Requirements DEFAULT_REQUIREMENTS = - new Requirements(Requirements.NETWORK_TYPE_ANY, false, false); + // Keep DownloadManagerListeners for each DownloadService as long as there are downloads (and the + // process is running). This allows DownloadService to restart when there's no scheduler. + private static final HashMap, DownloadManagerHelper> + downloadManagerListeners = new HashMap<>(); private final @Nullable ForegroundNotificationUpdater foregroundNotificationUpdater; private final @Nullable String channelId; private final @StringRes int channelName; private DownloadManager downloadManager; - private DownloadManagerListener downloadManagerListener; private int lastStartId; private boolean startedInForeground; private boolean taskRemoved; @@ -227,9 +219,16 @@ public abstract class DownloadService extends Service { NotificationUtil.createNotificationChannel( this, channelId, channelName, NotificationUtil.IMPORTANCE_LOW); } - downloadManager = getDownloadManager(); - downloadManagerListener = new DownloadManagerListener(); - downloadManager.addListener(downloadManagerListener); + Class clazz = getClass(); + DownloadManagerHelper downloadManagerHelper = downloadManagerListeners.get(clazz); + if (downloadManagerHelper == null) { + downloadManagerHelper = + new DownloadManagerHelper( + getApplicationContext(), getDownloadManager(), getScheduler(), clazz); + downloadManagerListeners.put(clazz, downloadManagerHelper); + } + downloadManager = downloadManagerHelper.downloadManager; + downloadManagerHelper.attachService(this); } @Override @@ -264,22 +263,11 @@ public abstract class DownloadService extends Service { } } break; - case ACTION_RELOAD_REQUIREMENTS: - stopWatchingRequirements(); - break; default: Log.e(TAG, "Ignoring unrecognized action: " + intentAction); break; } - Requirements requirements = getRequirements(); - if (requirements.checkRequirements(this)) { - downloadManager.startDownloads(); - } else { - downloadManager.stopDownloads(); - } - maybeStartWatchingRequirements(requirements); - if (downloadManager.isIdle()) { stop(); } @@ -295,11 +283,12 @@ public abstract class DownloadService extends Service { @Override public void onDestroy() { logd("onDestroy"); + DownloadManagerHelper downloadManagerHelper = downloadManagerListeners.get(getClass()); + boolean unschedule = downloadManager.getDownloadCount() <= 0; + downloadManagerHelper.detachService(this, unschedule); if (foregroundNotificationUpdater != null) { foregroundNotificationUpdater.stopPeriodicUpdates(); } - downloadManager.removeListener(downloadManagerListener); - maybeStopWatchingRequirements(); } /** DownloadService isn't designed to be bound. */ @@ -311,9 +300,7 @@ public abstract class DownloadService extends Service { /** * Returns a {@link DownloadManager} to be used to downloaded content. Called only once in the - * life cycle of the service. The service will call {@link DownloadManager#startDownloads()} and - * {@link DownloadManager#stopDownloads} as necessary when requirements returned by {@link - * #getRequirements()} are met or stop being met. + * life cycle of the process. */ protected abstract DownloadManager getDownloadManager(); @@ -324,14 +311,6 @@ public abstract class DownloadService extends Service { */ protected abstract @Nullable Scheduler getScheduler(); - /** - * Returns requirements for downloads to take place. By default the only requirement is that the - * device has network connectivity. - */ - protected Requirements getRequirements() { - return DEFAULT_REQUIREMENTS; - } - /** * Should be overridden in the subclass if the service will be run in the foreground. * @@ -363,32 +342,16 @@ public abstract class DownloadService extends Service { // Do nothing. } - private void maybeStartWatchingRequirements(Requirements requirements) { - if (downloadManager.getDownloadCount() == 0) { - return; - } - Class clazz = getClass(); - RequirementsHelper requirementsHelper = requirementsHelpers.get(clazz); - if (requirementsHelper == null) { - requirementsHelper = new RequirementsHelper(this, requirements, getScheduler(), clazz); - requirementsHelpers.put(clazz, requirementsHelper); - requirementsHelper.start(); - logd("started watching requirements"); - } - } - - private void maybeStopWatchingRequirements() { - if (downloadManager.getDownloadCount() > 0) { - return; - } - stopWatchingRequirements(); - } - - private void stopWatchingRequirements() { - RequirementsHelper requirementsHelper = requirementsHelpers.remove(getClass()); - if (requirementsHelper != null) { - requirementsHelper.stop(); - logd("stopped watching requirements"); + private void notifyDownloadStateChange(DownloadState downloadState) { + onDownloadStateChanged(downloadState); + if (foregroundNotificationUpdater != null) { + if (downloadState.state == DownloadState.STATE_DOWNLOADING + || downloadState.state == DownloadState.STATE_REMOVING + || downloadState.state == DownloadState.STATE_RESTARTING) { + foregroundNotificationUpdater.startPeriodicUpdates(); + } else { + foregroundNotificationUpdater.update(); + } } } @@ -420,33 +383,6 @@ public abstract class DownloadService extends Service { return new Intent(context, clazz).setAction(action); } - private final class DownloadManagerListener implements DownloadManager.Listener { - @Override - public void onInitialized(DownloadManager downloadManager) { - maybeStartWatchingRequirements(getRequirements()); - } - - @Override - public void onDownloadStateChanged( - DownloadManager downloadManager, DownloadState downloadState) { - DownloadService.this.onDownloadStateChanged(downloadState); - if (foregroundNotificationUpdater != null) { - if (downloadState.state == DownloadState.STATE_DOWNLOADING - || downloadState.state == DownloadState.STATE_REMOVING - || downloadState.state == DownloadState.STATE_RESTARTING) { - foregroundNotificationUpdater.startPeriodicUpdates(); - } else { - foregroundNotificationUpdater.update(); - } - } - } - - @Override - public final void onIdle(DownloadManager downloadManager) { - stop(); - } - } - private final class ForegroundNotificationUpdater implements Runnable { private final int notificationId; @@ -494,58 +430,87 @@ public abstract class DownloadService extends Service { } } - private static final class RequirementsHelper implements RequirementsWatcher.Listener { + private static final class DownloadManagerHelper implements DownloadManager.Listener { private final Context context; - private final Requirements requirements; - private final @Nullable Scheduler scheduler; + private final DownloadManager downloadManager; + @Nullable private final Scheduler scheduler; private final Class serviceClass; - private final RequirementsWatcher requirementsWatcher; + @Nullable private DownloadService downloadService; - private RequirementsHelper( + private DownloadManagerHelper( Context context, - Requirements requirements, + DownloadManager downloadManager, @Nullable Scheduler scheduler, Class serviceClass) { this.context = context; - this.requirements = requirements; + this.downloadManager = downloadManager; this.scheduler = scheduler; this.serviceClass = serviceClass; - requirementsWatcher = new RequirementsWatcher(context, this, requirements); - } - - public void start() { - requirementsWatcher.start(); - } - - public void stop() { - requirementsWatcher.stop(); + downloadManager.addListener(this); if (scheduler != null) { + Requirements requirements = downloadManager.getRequirements(); + setSchedulerEnabled(/* enabled= */ !requirements.checkRequirements(context), requirements); + } + } + + public void attachService(DownloadService downloadService) { + Assertions.checkState(this.downloadService == null); + this.downloadService = downloadService; + } + + public void detachService(DownloadService downloadService, boolean unschedule) { + Assertions.checkState(this.downloadService == downloadService); + this.downloadService = null; + if (unschedule) { scheduler.cancel(); } } @Override - public void requirementsMet(RequirementsWatcher requirementsWatcher) { - try { - notifyService(); - } catch (Exception e) { - /* If we can't notify the service, don't stop the scheduler. */ - return; - } - if (scheduler != null) { - scheduler.cancel(); + public void onInitialized(DownloadManager downloadManager) { + // Do nothing. + } + + @Override + public void onDownloadStateChanged( + DownloadManager downloadManager, DownloadState downloadState) { + if (downloadService != null) { + downloadService.notifyDownloadStateChange(downloadState); } } @Override - public void requirementsNotMet(RequirementsWatcher requirementsWatcher) { - try { - notifyService(); - } catch (Exception e) { - /* Do nothing. The service isn't running anyway. */ + public final void onIdle(DownloadManager downloadManager) { + if (downloadService != null) { + downloadService.stop(); + } + } + + @Override + public void onRequirementsStateChanged( + DownloadManager downloadManager, + Requirements requirements, + @Requirements.RequirementFlags int notMetRequirements) { + boolean requirementsMet = notMetRequirements == 0; + if (downloadService == null && requirementsMet) { + try { + Intent intent = getIntent(context, serviceClass, DownloadService.ACTION_INIT); + context.startService(intent); + } catch (IllegalStateException e) { + /* startService fails if the app is in the background then don't stop the scheduler. */ + return; + } } if (scheduler != null) { + setSchedulerEnabled(/* enabled= */ !requirementsMet, requirements); + } + } + + private void setSchedulerEnabled(boolean enabled, Requirements requirements) { + if (!enabled) { + scheduler.cancel(); + } else { String servicePackage = context.getPackageName(); boolean success = scheduler.schedule(requirements, servicePackage, ACTION_RESTART); if (!success) { @@ -553,15 +518,5 @@ public abstract class DownloadService extends Service { } } } - - private void notifyService() throws Exception { - Intent intent = getIntent(context, serviceClass, DownloadService.ACTION_INIT); - try { - context.startService(intent); - } catch (IllegalStateException e) { - /* startService will fail if the app is in the background and the service isn't running. */ - throw new Exception(e); - } - } } } diff --git a/library/core/src/main/java/com/google/android/exoplayer2/scheduler/Requirements.java b/library/core/src/main/java/com/google/android/exoplayer2/scheduler/Requirements.java index 4019d1ae70..77630a4543 100644 --- a/library/core/src/main/java/com/google/android/exoplayer2/scheduler/Requirements.java +++ b/library/core/src/main/java/com/google/android/exoplayer2/scheduler/Requirements.java @@ -155,16 +155,14 @@ public final class Requirements { * @return Whether the requirements are met. */ public boolean checkRequirements(Context context) { - return checkNetworkRequirements(context) - && checkChargingRequirement(context) - && checkIdleRequirement(context); + return getNotMetRequirements(context) == 0; } /** - * Returns the requirement flags that are not met, or 0. + * Returns {@link RequirementFlags} that are not met, or 0. * * @param context Any context. - * @return The requirement flags that are not met, or 0. + * @return RequirementFlags that are not met, or 0. */ @RequirementFlags public int getNotMetRequirements(Context context) { @@ -285,4 +283,20 @@ public final class Requirements { + (isIdleRequired() ? ",idle" : "") + '}'; } + + @Override + public boolean equals(Object o) { + if (this == o) { + return true; + } + if (o == null || getClass() != o.getClass()) { + return false; + } + return requirements == ((Requirements) o).requirements; + } + + @Override + public int hashCode() { + return requirements; + } } diff --git a/library/core/src/main/java/com/google/android/exoplayer2/scheduler/RequirementsWatcher.java b/library/core/src/main/java/com/google/android/exoplayer2/scheduler/RequirementsWatcher.java index fded95614c..686f19d161 100644 --- a/library/core/src/main/java/com/google/android/exoplayer2/scheduler/RequirementsWatcher.java +++ b/library/core/src/main/java/com/google/android/exoplayer2/scheduler/RequirementsWatcher.java @@ -55,8 +55,12 @@ public final class RequirementsWatcher { * requirements are not met. * * @param requirementsWatcher Calling instance. + * @param notMetRequirements {@link Requirements.RequirementFlags RequirementFlags} that are not + * met, or 0. */ - void requirementsNotMet(RequirementsWatcher requirementsWatcher); + void requirementsNotMet( + RequirementsWatcher requirementsWatcher, + @Requirements.RequirementFlags int notMetRequirements); } private static final String TAG = "RequirementsWatcher"; @@ -66,7 +70,7 @@ public final class RequirementsWatcher { private final Requirements requirements; private DeviceStatusChangeReceiver receiver; - private int notMetRequirements; + @Requirements.RequirementFlags private int notMetRequirements; private CapabilityValidatedCallback networkCallback; private Handler handler; @@ -85,8 +89,11 @@ public final class RequirementsWatcher { /** * Starts watching for changes. Must be called from a thread that has an associated {@link * Looper}. Listener methods are called on the caller thread. + * + * @return Initial {@link Requirements.RequirementFlags RequirementFlags} that are not met, or 0. */ - public void start() { + @Requirements.RequirementFlags + public int start() { Assertions.checkNotNull(Looper.myLooper()); handler = new Handler(); @@ -115,6 +122,7 @@ public final class RequirementsWatcher { receiver = new DeviceStatusChangeReceiver(); context.registerReceiver(receiver, filter, null, handler); logd(this + " started"); + return notMetRequirements; } /** Stops watching for changes. */ @@ -162,6 +170,7 @@ public final class RequirementsWatcher { } private void checkRequirements() { + @Requirements.RequirementFlags int notMetRequirements = requirements.getNotMetRequirements(context); if (this.notMetRequirements == notMetRequirements) { logd("notMetRequirements hasn't changed: " + notMetRequirements); @@ -173,7 +182,7 @@ public final class RequirementsWatcher { listener.requirementsMet(this); } else { logd("stop job"); - listener.requirementsNotMet(this); + listener.requirementsNotMet(this, notMetRequirements); } } diff --git a/library/core/src/test/java/com/google/android/exoplayer2/offline/DownloadManagerTest.java b/library/core/src/test/java/com/google/android/exoplayer2/offline/DownloadManagerTest.java index 5902ac894a..283d343e63 100644 --- a/library/core/src/test/java/com/google/android/exoplayer2/offline/DownloadManagerTest.java +++ b/library/core/src/test/java/com/google/android/exoplayer2/offline/DownloadManagerTest.java @@ -21,6 +21,7 @@ import static org.junit.Assert.fail; import android.net.Uri; import com.google.android.exoplayer2.C; import com.google.android.exoplayer2.offline.DownloadState.State; +import com.google.android.exoplayer2.scheduler.Requirements; import com.google.android.exoplayer2.testutil.DummyMainThread; import com.google.android.exoplayer2.testutil.RobolectricUtil; import com.google.android.exoplayer2.testutil.TestDownloadManagerListener; @@ -426,7 +427,12 @@ public class DownloadManagerTest { () -> { downloadManager = new DownloadManager( - actionFile, downloaderFactory, maxActiveDownloadTasks, MIN_RETRY_COUNT); + RuntimeEnvironment.application, + actionFile, + downloaderFactory, + maxActiveDownloadTasks, + MIN_RETRY_COUNT, + new Requirements(0)); downloadManagerListener = new TestDownloadManagerListener(downloadManager, dummyMainThread); downloadManager.startDownloads(); diff --git a/library/dash/src/test/java/com/google/android/exoplayer2/source/dash/offline/DownloadManagerDashTest.java b/library/dash/src/test/java/com/google/android/exoplayer2/source/dash/offline/DownloadManagerDashTest.java index ccccb20ccb..28040ec538 100644 --- a/library/dash/src/test/java/com/google/android/exoplayer2/source/dash/offline/DownloadManagerDashTest.java +++ b/library/dash/src/test/java/com/google/android/exoplayer2/source/dash/offline/DownloadManagerDashTest.java @@ -30,6 +30,7 @@ import com.google.android.exoplayer2.offline.DownloadAction; import com.google.android.exoplayer2.offline.DownloadManager; import com.google.android.exoplayer2.offline.DownloaderConstructorHelper; import com.google.android.exoplayer2.offline.StreamKey; +import com.google.android.exoplayer2.scheduler.Requirements; import com.google.android.exoplayer2.testutil.DummyMainThread; import com.google.android.exoplayer2.testutil.FakeDataSet; import com.google.android.exoplayer2.testutil.FakeDataSource; @@ -241,11 +242,13 @@ public class DownloadManagerDashTest { Factory fakeDataSourceFactory = new FakeDataSource.Factory().setFakeDataSet(fakeDataSet); downloadManager = new DownloadManager( + RuntimeEnvironment.application, actionFile, new DefaultDownloaderFactory( new DownloaderConstructorHelper(cache, fakeDataSourceFactory)), /* maxSimultaneousDownloads= */ 1, - /* minRetryCount= */ 3); + /* minRetryCount= */ 3, + new Requirements(0)); downloadManagerListener = new TestDownloadManagerListener(downloadManager, dummyMainThread); diff --git a/library/dash/src/test/java/com/google/android/exoplayer2/source/dash/offline/DownloadServiceDashTest.java b/library/dash/src/test/java/com/google/android/exoplayer2/source/dash/offline/DownloadServiceDashTest.java index adae0d7b04..bf32b65ba7 100644 --- a/library/dash/src/test/java/com/google/android/exoplayer2/source/dash/offline/DownloadServiceDashTest.java +++ b/library/dash/src/test/java/com/google/android/exoplayer2/source/dash/offline/DownloadServiceDashTest.java @@ -30,6 +30,7 @@ import com.google.android.exoplayer2.offline.DownloadManager; import com.google.android.exoplayer2.offline.DownloadService; import com.google.android.exoplayer2.offline.DownloaderConstructorHelper; import com.google.android.exoplayer2.offline.StreamKey; +import com.google.android.exoplayer2.scheduler.Requirements; import com.google.android.exoplayer2.scheduler.Scheduler; import com.google.android.exoplayer2.testutil.DummyMainThread; import com.google.android.exoplayer2.testutil.FakeDataSet; @@ -117,11 +118,13 @@ public class DownloadServiceDashTest { actionFile.delete(); final DownloadManager dashDownloadManager = new DownloadManager( + RuntimeEnvironment.application, actionFile, new DefaultDownloaderFactory( new DownloaderConstructorHelper(cache, fakeDataSourceFactory)), /* maxSimultaneousDownloads= */ 1, - /* minRetryCount= */ 3); + /* minRetryCount= */ 3, + new Requirements(0)); downloadManagerListener = new TestDownloadManagerListener(dashDownloadManager, dummyMainThread); dashDownloadManager.startDownloads(); diff --git a/testutils_robolectric/src/main/java/com/google/android/exoplayer2/testutil/TestDownloadManagerListener.java b/testutils_robolectric/src/main/java/com/google/android/exoplayer2/testutil/TestDownloadManagerListener.java index 8216b881f3..2109cceda8 100644 --- a/testutils_robolectric/src/main/java/com/google/android/exoplayer2/testutil/TestDownloadManagerListener.java +++ b/testutils_robolectric/src/main/java/com/google/android/exoplayer2/testutil/TestDownloadManagerListener.java @@ -20,6 +20,7 @@ import static com.google.common.truth.Truth.assertThat; import android.os.ConditionVariable; import com.google.android.exoplayer2.offline.DownloadManager; import com.google.android.exoplayer2.offline.DownloadState; +import com.google.android.exoplayer2.scheduler.Requirements; import java.util.HashMap; import java.util.concurrent.ArrayBlockingQueue; import java.util.concurrent.CountDownLatch; @@ -82,6 +83,12 @@ public final class TestDownloadManagerListener implements DownloadManager.Listen } } + @Override + public void onRequirementsStateChanged( + DownloadManager downloadManager, Requirements requirements, int notMetRequirements) { + // Do nothing. + } + /** * Blocks until all remove and download tasks are complete and throws an exception if there was an * error.