summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorHerbert Reiter <46045854+damoasda@users.noreply.github.com>2021-02-07 17:57:09 +0100
committerGitHub <noreply@github.com>2021-02-07 17:57:09 +0100
commit60968089ae4afe13ba48d64346ea39c542ad457b (patch)
tree6a8d9bbf36d1e9aced4fcf533a6b47c4c565fdbf
parentded779d0c9b884fae3b78347f7b8a09069730785 (diff)
downloadAntennaPod-60968089ae4afe13ba48d64346ea39c542ad457b.zip
Refactoring: Remove ClientConfig.automaticDownloadAlgorithm (#4924)
-rw-r--r--app/src/androidTest/java/de/test/antennapod/storage/AutoDownloadTest.java24
-rw-r--r--app/src/main/java/de/danoeh/antennapod/config/ClientConfigurator.java5
-rw-r--r--core/src/free/java/de/danoeh/antennapod/core/ClientConfig.java3
-rw-r--r--core/src/main/java/de/danoeh/antennapod/core/storage/APDownloadAlgorithm.java103
-rw-r--r--core/src/main/java/de/danoeh/antennapod/core/storage/AutomaticDownloadAlgorithm.java90
-rw-r--r--core/src/main/java/de/danoeh/antennapod/core/storage/DBTasks.java18
-rw-r--r--core/src/play/java/de/danoeh/antennapod/core/ClientConfig.java3
7 files changed, 113 insertions, 133 deletions
diff --git a/app/src/androidTest/java/de/test/antennapod/storage/AutoDownloadTest.java b/app/src/androidTest/java/de/test/antennapod/storage/AutoDownloadTest.java
index 1d2e3d9e8..e74cf49b7 100644
--- a/app/src/androidTest/java/de/test/antennapod/storage/AutoDownloadTest.java
+++ b/app/src/androidTest/java/de/test/antennapod/storage/AutoDownloadTest.java
@@ -3,13 +3,13 @@ package de.test.antennapod.storage;
import android.content.Context;
import androidx.annotation.NonNull;
import androidx.test.core.app.ApplicationProvider;
-import de.danoeh.antennapod.core.ClientConfig;
import de.danoeh.antennapod.core.feed.FeedItem;
import de.danoeh.antennapod.core.feed.FeedMedia;
import de.danoeh.antennapod.core.preferences.PlaybackPreferences;
import de.danoeh.antennapod.core.preferences.UserPreferences;
import de.danoeh.antennapod.core.storage.AutomaticDownloadAlgorithm;
import de.danoeh.antennapod.core.storage.DBReader;
+import de.danoeh.antennapod.core.storage.DBTasks;
import de.danoeh.antennapod.core.util.playback.PlaybackServiceStarter;
import de.test.antennapod.EspressoTestUtils;
import de.test.antennapod.ui.UITestUtils;
@@ -29,8 +29,7 @@ public class AutoDownloadTest {
private Context context;
private UITestUtils stubFeedsServer;
-
- private AutomaticDownloadAlgorithm automaticDownloadAlgorithmOrig;
+ private StubDownloadAlgorithm stubDownloadAlgorithm;
@Before
public void setUp() throws Exception {
@@ -39,16 +38,19 @@ public class AutoDownloadTest {
stubFeedsServer = new UITestUtils(context);
stubFeedsServer.setup();
- automaticDownloadAlgorithmOrig = ClientConfig.automaticDownloadAlgorithm;
-
EspressoTestUtils.clearPreferences();
EspressoTestUtils.clearDatabase();
UserPreferences.setAllowMobileStreaming(true);
+
+ // Setup: enable automatic download
+ // it is not needed, as the actual automatic download is stubbed.
+ stubDownloadAlgorithm = new StubDownloadAlgorithm();
+ DBTasks.setDownloadAlgorithm(stubDownloadAlgorithm);
}
@After
public void tearDown() throws Exception {
- ClientConfig.automaticDownloadAlgorithm = automaticDownloadAlgorithmOrig;
+ DBTasks.setDownloadAlgorithm(new AutomaticDownloadAlgorithm());
EspressoTestUtils.tryKillPlaybackService();
stubFeedsServer.tearDown();
}
@@ -74,11 +76,6 @@ public class AutoDownloadTest {
FeedItem item0 = queue.get(0);
FeedItem item1 = queue.get(1);
- // Setup: enable automatic download
- // it is not needed, as the actual automatic download is stubbed.
- StubDownloadAlgorithm stubDownloadAlgorithm = new StubDownloadAlgorithm();
- ClientConfig.automaticDownloadAlgorithm = stubDownloadAlgorithm;
-
// Actual test
// Play the first one in the queue
playEpisode(item0);
@@ -92,11 +89,10 @@ public class AutoDownloadTest {
} catch (ConditionTimeoutException cte) {
long actual = stubDownloadAlgorithm.getCurrentlyPlayingAtDownload();
fail("when auto download is triggered, the next episode should be playing: ("
- + item1.getId() + ", " + item1.getTitle() + ") . "
+ + item1.getId() + ", " + item1.getTitle() + ") . "
+ "Actual playing: (" + actual + ")"
);
}
-
}
private void playEpisode(@NonNull FeedItem item) {
@@ -111,7 +107,7 @@ public class AutoDownloadTest {
.until(() -> item.getMedia().getId() == PlaybackPreferences.getCurrentlyPlayingFeedMediaId());
}
- private static class StubDownloadAlgorithm implements AutomaticDownloadAlgorithm {
+ private static class StubDownloadAlgorithm extends AutomaticDownloadAlgorithm {
private long currentlyPlaying = -1;
@Override
diff --git a/app/src/main/java/de/danoeh/antennapod/config/ClientConfigurator.java b/app/src/main/java/de/danoeh/antennapod/config/ClientConfigurator.java
index 7a5cf431f..f01047705 100644
--- a/app/src/main/java/de/danoeh/antennapod/config/ClientConfigurator.java
+++ b/app/src/main/java/de/danoeh/antennapod/config/ClientConfigurator.java
@@ -2,21 +2,20 @@ package de.danoeh.antennapod.config;
import de.danoeh.antennapod.BuildConfig;
import de.danoeh.antennapod.core.ClientConfig;
-import de.danoeh.antennapod.core.storage.APDownloadAlgorithm;
/**
* Configures the ClientConfig class of the core package.
*/
class ClientConfigurator {
- private ClientConfigurator(){}
+ private ClientConfigurator() {
+ }
static {
ClientConfig.USER_AGENT = "AntennaPod/" + BuildConfig.VERSION_NAME;
ClientConfig.applicationCallbacks = new ApplicationCallbacksImpl();
ClientConfig.downloadServiceCallbacks = new DownloadServiceCallbacksImpl();
ClientConfig.playbackServiceCallbacks = new PlaybackServiceCallbacksImpl();
- ClientConfig.automaticDownloadAlgorithm = new APDownloadAlgorithm();
ClientConfig.castCallbacks = new CastCallbackImpl();
}
}
diff --git a/core/src/free/java/de/danoeh/antennapod/core/ClientConfig.java b/core/src/free/java/de/danoeh/antennapod/core/ClientConfig.java
index 8fd1df35c..5f7e6baaf 100644
--- a/core/src/free/java/de/danoeh/antennapod/core/ClientConfig.java
+++ b/core/src/free/java/de/danoeh/antennapod/core/ClientConfig.java
@@ -9,7 +9,6 @@ import de.danoeh.antennapod.core.preferences.SleepTimerPreferences;
import de.danoeh.antennapod.core.preferences.UsageStatistics;
import de.danoeh.antennapod.core.preferences.UserPreferences;
import de.danoeh.antennapod.core.service.download.AntennapodHttpClient;
-import de.danoeh.antennapod.core.storage.AutomaticDownloadAlgorithm;
import de.danoeh.antennapod.core.storage.PodDBAdapter;
import de.danoeh.antennapod.core.util.NetworkUtils;
import de.danoeh.antennapod.core.util.gui.NotificationUtils;
@@ -33,8 +32,6 @@ public class ClientConfig {
public static PlaybackServiceCallbacks playbackServiceCallbacks;
- public static AutomaticDownloadAlgorithm automaticDownloadAlgorithm;
-
public static CastCallbacks castCallbacks;
private static boolean initialized = false;
diff --git a/core/src/main/java/de/danoeh/antennapod/core/storage/APDownloadAlgorithm.java b/core/src/main/java/de/danoeh/antennapod/core/storage/APDownloadAlgorithm.java
deleted file mode 100644
index 061d6cf3f..000000000
--- a/core/src/main/java/de/danoeh/antennapod/core/storage/APDownloadAlgorithm.java
+++ /dev/null
@@ -1,103 +0,0 @@
-package de.danoeh.antennapod.core.storage;
-
-import android.content.Context;
-import android.util.Log;
-
-import java.util.ArrayList;
-import java.util.Iterator;
-import java.util.List;
-
-import de.danoeh.antennapod.core.feed.FeedFilter;
-import de.danoeh.antennapod.core.feed.FeedItem;
-import de.danoeh.antennapod.core.feed.FeedPreferences;
-import de.danoeh.antennapod.core.preferences.UserPreferences;
-import de.danoeh.antennapod.core.util.NetworkUtils;
-import de.danoeh.antennapod.core.util.PowerUtils;
-
-/**
- * Implements the automatic download algorithm used by AntennaPod. This class assumes that
- * the client uses the APEpisodeCleanupAlgorithm.
- */
-public class APDownloadAlgorithm implements AutomaticDownloadAlgorithm {
- private static final String TAG = "APDownloadAlgorithm";
-
- /**
- * Looks for undownloaded episodes in the queue or list of new items and request a download if
- * 1. Network is available
- * 2. The device is charging or the user allows auto download on battery
- * 3. There is free space in the episode cache
- * This method is executed on an internal single thread executor.
- *
- * @param context Used for accessing the DB.
- * @return A Runnable that will be submitted to an ExecutorService.
- */
- @Override
- public Runnable autoDownloadUndownloadedItems(final Context context) {
- return () -> {
-
- // true if we should auto download based on network status
- boolean networkShouldAutoDl = NetworkUtils.autodownloadNetworkAvailable()
- && UserPreferences.isEnableAutodownload();
-
- // true if we should auto download based on power status
- boolean powerShouldAutoDl = PowerUtils.deviceCharging(context)
- || UserPreferences.isEnableAutodownloadOnBattery();
-
- // we should only auto download if both network AND power are happy
- if (networkShouldAutoDl && powerShouldAutoDl) {
-
- Log.d(TAG, "Performing auto-dl of undownloaded episodes");
-
- List<FeedItem> candidates;
- final List<FeedItem> queue = DBReader.getQueue();
- final List<FeedItem> newItems = DBReader.getNewItemsList(0, Integer.MAX_VALUE);
- candidates = new ArrayList<>(queue.size() + newItems.size());
- candidates.addAll(queue);
- for (FeedItem newItem : newItems) {
- FeedPreferences feedPrefs = newItem.getFeed().getPreferences();
- FeedFilter feedFilter = feedPrefs.getFilter();
- if (!candidates.contains(newItem) && feedFilter.shouldAutoDownload(newItem)) {
- candidates.add(newItem);
- }
- }
-
- // filter items that are not auto downloadable
- Iterator<FeedItem> it = candidates.iterator();
- while (it.hasNext()) {
- FeedItem item = it.next();
- if (!item.isAutoDownloadable() || item.getFeed().isLocalFeed()) {
- it.remove();
- }
- }
-
- int autoDownloadableEpisodes = candidates.size();
- int downloadedEpisodes = DBReader.getNumberOfDownloadedEpisodes();
- int deletedEpisodes = UserPreferences.getEpisodeCleanupAlgorithm()
- .makeRoomForEpisodes(context, autoDownloadableEpisodes);
- boolean cacheIsUnlimited =
- UserPreferences.getEpisodeCacheSize() == UserPreferences.getEpisodeCacheSizeUnlimited();
- int episodeCacheSize = UserPreferences.getEpisodeCacheSize();
-
- int episodeSpaceLeft;
- if (cacheIsUnlimited || episodeCacheSize >= downloadedEpisodes + autoDownloadableEpisodes) {
- episodeSpaceLeft = autoDownloadableEpisodes;
- } else {
- episodeSpaceLeft = episodeCacheSize - (downloadedEpisodes - deletedEpisodes);
- }
-
- FeedItem[] itemsToDownload = candidates.subList(0, episodeSpaceLeft)
- .toArray(new FeedItem[episodeSpaceLeft]);
-
- if (itemsToDownload.length > 0) {
- Log.d(TAG, "Enqueueing " + itemsToDownload.length + " items for download");
-
- try {
- DownloadRequester.getInstance().downloadMedia(false, context, false, itemsToDownload);
- } catch (DownloadRequestException e) {
- e.printStackTrace();
- }
- }
- }
- };
- }
-}
diff --git a/core/src/main/java/de/danoeh/antennapod/core/storage/AutomaticDownloadAlgorithm.java b/core/src/main/java/de/danoeh/antennapod/core/storage/AutomaticDownloadAlgorithm.java
index dbb77e19c..f8b643ccf 100644
--- a/core/src/main/java/de/danoeh/antennapod/core/storage/AutomaticDownloadAlgorithm.java
+++ b/core/src/main/java/de/danoeh/antennapod/core/storage/AutomaticDownloadAlgorithm.java
@@ -1,11 +1,28 @@
package de.danoeh.antennapod.core.storage;
import android.content.Context;
+import android.util.Log;
-public interface AutomaticDownloadAlgorithm {
+import java.util.ArrayList;
+import java.util.Iterator;
+import java.util.List;
+
+import de.danoeh.antennapod.core.feed.FeedFilter;
+import de.danoeh.antennapod.core.feed.FeedItem;
+import de.danoeh.antennapod.core.feed.FeedPreferences;
+import de.danoeh.antennapod.core.preferences.UserPreferences;
+import de.danoeh.antennapod.core.util.NetworkUtils;
+import de.danoeh.antennapod.core.util.PowerUtils;
+
+/**
+ * Implements the automatic download algorithm used by AntennaPod. This class assumes that
+ * the client uses the {@link EpisodeCleanupAlgorithm}.
+ */
+public class AutomaticDownloadAlgorithm {
+ private static final String TAG = "DownloadAlgorithm";
/**
- * Looks for undownloaded episodes and request a download if
+ * Looks for undownloaded episodes in the queue or list of new items and request a download if
* 1. Network is available
* 2. The device is charging or the user allows auto download on battery
* 3. There is free space in the episode cache
@@ -14,5 +31,72 @@ public interface AutomaticDownloadAlgorithm {
* @param context Used for accessing the DB.
* @return A Runnable that will be submitted to an ExecutorService.
*/
- Runnable autoDownloadUndownloadedItems(Context context);
+ public Runnable autoDownloadUndownloadedItems(final Context context) {
+ return () -> {
+
+ // true if we should auto download based on network status
+ boolean networkShouldAutoDl = NetworkUtils.autodownloadNetworkAvailable()
+ && UserPreferences.isEnableAutodownload();
+
+ // true if we should auto download based on power status
+ boolean powerShouldAutoDl = PowerUtils.deviceCharging(context)
+ || UserPreferences.isEnableAutodownloadOnBattery();
+
+ // we should only auto download if both network AND power are happy
+ if (networkShouldAutoDl && powerShouldAutoDl) {
+
+ Log.d(TAG, "Performing auto-dl of undownloaded episodes");
+
+ List<FeedItem> candidates;
+ final List<FeedItem> queue = DBReader.getQueue();
+ final List<FeedItem> newItems = DBReader.getNewItemsList(0, Integer.MAX_VALUE);
+ candidates = new ArrayList<>(queue.size() + newItems.size());
+ candidates.addAll(queue);
+ for (FeedItem newItem : newItems) {
+ FeedPreferences feedPrefs = newItem.getFeed().getPreferences();
+ FeedFilter feedFilter = feedPrefs.getFilter();
+ if (!candidates.contains(newItem) && feedFilter.shouldAutoDownload(newItem)) {
+ candidates.add(newItem);
+ }
+ }
+
+ // filter items that are not auto downloadable
+ Iterator<FeedItem> it = candidates.iterator();
+ while (it.hasNext()) {
+ FeedItem item = it.next();
+ if (!item.isAutoDownloadable() || item.getFeed().isLocalFeed()) {
+ it.remove();
+ }
+ }
+
+ int autoDownloadableEpisodes = candidates.size();
+ int downloadedEpisodes = DBReader.getNumberOfDownloadedEpisodes();
+ int deletedEpisodes = UserPreferences.getEpisodeCleanupAlgorithm()
+ .makeRoomForEpisodes(context, autoDownloadableEpisodes);
+ boolean cacheIsUnlimited =
+ UserPreferences.getEpisodeCacheSize() == UserPreferences.getEpisodeCacheSizeUnlimited();
+ int episodeCacheSize = UserPreferences.getEpisodeCacheSize();
+
+ int episodeSpaceLeft;
+ if (cacheIsUnlimited || episodeCacheSize >= downloadedEpisodes + autoDownloadableEpisodes) {
+ episodeSpaceLeft = autoDownloadableEpisodes;
+ } else {
+ episodeSpaceLeft = episodeCacheSize - (downloadedEpisodes - deletedEpisodes);
+ }
+
+ FeedItem[] itemsToDownload = candidates.subList(0, episodeSpaceLeft)
+ .toArray(new FeedItem[episodeSpaceLeft]);
+
+ if (itemsToDownload.length > 0) {
+ Log.d(TAG, "Enqueueing " + itemsToDownload.length + " items for download");
+
+ try {
+ DownloadRequester.getInstance().downloadMedia(false, context, false, itemsToDownload);
+ } catch (DownloadRequestException e) {
+ e.printStackTrace();
+ }
+ }
+ }
+ };
+ }
}
diff --git a/core/src/main/java/de/danoeh/antennapod/core/storage/DBTasks.java b/core/src/main/java/de/danoeh/antennapod/core/storage/DBTasks.java
index ec39e7144..48a3f574a 100644
--- a/core/src/main/java/de/danoeh/antennapod/core/storage/DBTasks.java
+++ b/core/src/main/java/de/danoeh/antennapod/core/storage/DBTasks.java
@@ -6,7 +6,9 @@ import android.database.Cursor;
import android.os.Looper;
import android.text.TextUtils;
import android.util.Log;
-import de.danoeh.antennapod.core.ClientConfig;
+
+import androidx.annotation.VisibleForTesting;
+
import de.danoeh.antennapod.core.R;
import de.danoeh.antennapod.core.event.FeedItemEvent;
import de.danoeh.antennapod.core.event.FeedListUpdateEvent;
@@ -53,6 +55,8 @@ public final class DBTasks {
*/
private static final ExecutorService autodownloadExec;
+ private static AutomaticDownloadAlgorithm downloadAlgorithm = new AutomaticDownloadAlgorithm();
+
static {
autodownloadExec = Executors.newSingleThreadExecutor(r -> {
Thread t = new Thread(r);
@@ -278,7 +282,7 @@ public final class DBTasks {
}
/**
- * Looks for undownloaded episodes in the queue or list of unread items and request a download if
+ * Looks for non-downloaded episodes in the queue or list of unread items and request a download if
* 1. Network is available
* 2. The device is charging or the user allows auto download on battery
* 3. There is free space in the episode cache
@@ -289,9 +293,15 @@ public final class DBTasks {
*/
public static Future<?> autodownloadUndownloadedItems(final Context context) {
Log.d(TAG, "autodownloadUndownloadedItems");
- return autodownloadExec.submit(ClientConfig.automaticDownloadAlgorithm
- .autoDownloadUndownloadedItems(context));
+ return autodownloadExec.submit(downloadAlgorithm.autoDownloadUndownloadedItems(context));
+ }
+ /**
+ * For testing purpose only.
+ */
+ @VisibleForTesting(otherwise = VisibleForTesting.NONE)
+ public static void setDownloadAlgorithm(AutomaticDownloadAlgorithm newDownloadAlgorithm) {
+ downloadAlgorithm = newDownloadAlgorithm;
}
/**
diff --git a/core/src/play/java/de/danoeh/antennapod/core/ClientConfig.java b/core/src/play/java/de/danoeh/antennapod/core/ClientConfig.java
index 4b5e4d588..e8c2b1dcd 100644
--- a/core/src/play/java/de/danoeh/antennapod/core/ClientConfig.java
+++ b/core/src/play/java/de/danoeh/antennapod/core/ClientConfig.java
@@ -12,7 +12,6 @@ import de.danoeh.antennapod.core.preferences.SleepTimerPreferences;
import de.danoeh.antennapod.core.preferences.UsageStatistics;
import de.danoeh.antennapod.core.preferences.UserPreferences;
import de.danoeh.antennapod.core.service.download.AntennapodHttpClient;
-import de.danoeh.antennapod.core.storage.AutomaticDownloadAlgorithm;
import de.danoeh.antennapod.core.storage.PodDBAdapter;
import de.danoeh.antennapod.core.util.NetworkUtils;
import de.danoeh.antennapod.core.util.gui.NotificationUtils;
@@ -39,8 +38,6 @@ public class ClientConfig {
public static PlaybackServiceCallbacks playbackServiceCallbacks;
- public static AutomaticDownloadAlgorithm automaticDownloadAlgorithm;
-
public static CastCallbacks castCallbacks;
private static boolean initialized = false;