mirror of
https://github.com/samsonjs/media.git
synced 2026-04-27 15:07:40 +00:00
Remove DownloadConstructorHelper
Something that helps a constructor always seemed a bit strange. It's now possible to use CacheDataSource.Factory directly instead. PiperOrigin-RevId: 307661930
This commit is contained in:
parent
722a5b2279
commit
4abaaf138c
19 changed files with 198 additions and 266 deletions
|
|
@ -60,8 +60,6 @@
|
||||||
`DecoderVideoRenderer` and `DecoderAudioRenderer` respectively, and
|
`DecoderVideoRenderer` and `DecoderAudioRenderer` respectively, and
|
||||||
generalized to work with `Decoder` rather than `SimpleDecoder`.
|
generalized to work with `Decoder` rather than `SimpleDecoder`.
|
||||||
* Add media item based playlist API to Player.
|
* Add media item based playlist API to Player.
|
||||||
* Update `CachedContentIndex` to use `SecureRandom` for generating the
|
|
||||||
initialization vector used to encrypt the cache contents.
|
|
||||||
* Remove deprecated members in `DefaultTrackSelector`.
|
* Remove deprecated members in `DefaultTrackSelector`.
|
||||||
* Add `Player.DeviceComponent` and implement it for `SimpleExoPlayer` so
|
* Add `Player.DeviceComponent` and implement it for `SimpleExoPlayer` so
|
||||||
that the device volume can be controlled by player.
|
that the device volume can be controlled by player.
|
||||||
|
|
@ -108,8 +106,15 @@
|
||||||
`OfflineLicenseHelper`
|
`OfflineLicenseHelper`
|
||||||
([#7078](https://github.com/google/ExoPlayer/issues/7078)).
|
([#7078](https://github.com/google/ExoPlayer/issues/7078)).
|
||||||
* Remove generics from DRM components.
|
* Remove generics from DRM components.
|
||||||
* Downloads: Merge downloads in `SegmentDownloader` to improve overall
|
* Downloads and caching:
|
||||||
download speed ([#5978](https://github.com/google/ExoPlayer/issues/5978)).
|
* Merge downloads in `SegmentDownloader` to improve overall download
|
||||||
|
speed ([#5978](https://github.com/google/ExoPlayer/issues/5978)).
|
||||||
|
* Replace `CacheDataSinkFactory` and `CacheDataSourceFactory` with
|
||||||
|
`CacheDataSink.Factory` and `CacheDataSource.Factory` respectively.
|
||||||
|
* Remove `DownloadConstructorHelper` and use `CacheDataSource.Factory`
|
||||||
|
directly instead.
|
||||||
|
* Update `CachedContentIndex` to use `SecureRandom` for generating the
|
||||||
|
initialization vector used to encrypt the cache contents.
|
||||||
* DASH:
|
* DASH:
|
||||||
* Merge trick play adaptation sets (i.e., adaptation sets marked with
|
* Merge trick play adaptation sets (i.e., adaptation sets marked with
|
||||||
`http://dashif.org/guidelines/trickmode`) into the same `TrackGroup` as
|
`http://dashif.org/guidelines/trickmode`) into the same `TrackGroup` as
|
||||||
|
|
|
||||||
|
|
@ -22,18 +22,14 @@ import com.google.android.exoplayer2.database.DatabaseProvider;
|
||||||
import com.google.android.exoplayer2.database.ExoDatabaseProvider;
|
import com.google.android.exoplayer2.database.ExoDatabaseProvider;
|
||||||
import com.google.android.exoplayer2.offline.ActionFileUpgradeUtil;
|
import com.google.android.exoplayer2.offline.ActionFileUpgradeUtil;
|
||||||
import com.google.android.exoplayer2.offline.DefaultDownloadIndex;
|
import com.google.android.exoplayer2.offline.DefaultDownloadIndex;
|
||||||
import com.google.android.exoplayer2.offline.DefaultDownloaderFactory;
|
|
||||||
import com.google.android.exoplayer2.offline.DownloadManager;
|
import com.google.android.exoplayer2.offline.DownloadManager;
|
||||||
import com.google.android.exoplayer2.offline.DownloaderConstructorHelper;
|
|
||||||
import com.google.android.exoplayer2.ui.DownloadNotificationHelper;
|
import com.google.android.exoplayer2.ui.DownloadNotificationHelper;
|
||||||
import com.google.android.exoplayer2.upstream.DataSource;
|
import com.google.android.exoplayer2.upstream.DataSource;
|
||||||
import com.google.android.exoplayer2.upstream.DefaultDataSourceFactory;
|
import com.google.android.exoplayer2.upstream.DefaultDataSourceFactory;
|
||||||
import com.google.android.exoplayer2.upstream.DefaultHttpDataSourceFactory;
|
import com.google.android.exoplayer2.upstream.DefaultHttpDataSourceFactory;
|
||||||
import com.google.android.exoplayer2.upstream.FileDataSource;
|
|
||||||
import com.google.android.exoplayer2.upstream.HttpDataSource;
|
import com.google.android.exoplayer2.upstream.HttpDataSource;
|
||||||
import com.google.android.exoplayer2.upstream.cache.Cache;
|
import com.google.android.exoplayer2.upstream.cache.Cache;
|
||||||
import com.google.android.exoplayer2.upstream.cache.CacheDataSource;
|
import com.google.android.exoplayer2.upstream.cache.CacheDataSource;
|
||||||
import com.google.android.exoplayer2.upstream.cache.CacheDataSourceFactory;
|
|
||||||
import com.google.android.exoplayer2.upstream.cache.NoOpCacheEvictor;
|
import com.google.android.exoplayer2.upstream.cache.NoOpCacheEvictor;
|
||||||
import com.google.android.exoplayer2.upstream.cache.SimpleCache;
|
import com.google.android.exoplayer2.upstream.cache.SimpleCache;
|
||||||
import com.google.android.exoplayer2.util.Log;
|
import com.google.android.exoplayer2.util.Log;
|
||||||
|
|
@ -131,11 +127,9 @@ public class DemoApplication extends Application {
|
||||||
DOWNLOAD_ACTION_FILE, downloadIndex, /* addNewDownloadsAsCompleted= */ false);
|
DOWNLOAD_ACTION_FILE, downloadIndex, /* addNewDownloadsAsCompleted= */ false);
|
||||||
upgradeActionFile(
|
upgradeActionFile(
|
||||||
DOWNLOAD_TRACKER_ACTION_FILE, downloadIndex, /* addNewDownloadsAsCompleted= */ true);
|
DOWNLOAD_TRACKER_ACTION_FILE, downloadIndex, /* addNewDownloadsAsCompleted= */ true);
|
||||||
DownloaderConstructorHelper downloaderConstructorHelper =
|
|
||||||
new DownloaderConstructorHelper(getDownloadCache(), buildHttpDataSourceFactory());
|
|
||||||
downloadManager =
|
downloadManager =
|
||||||
new DownloadManager(
|
new DownloadManager(
|
||||||
this, downloadIndex, new DefaultDownloaderFactory(downloaderConstructorHelper));
|
this, getDatabaseProvider(), getDownloadCache(), buildHttpDataSourceFactory());
|
||||||
downloadTracker =
|
downloadTracker =
|
||||||
new DownloadTracker(/* context= */ this, buildDataSourceFactory(), downloadManager);
|
new DownloadTracker(/* context= */ this, buildDataSourceFactory(), downloadManager);
|
||||||
}
|
}
|
||||||
|
|
@ -172,14 +166,12 @@ public class DemoApplication extends Application {
|
||||||
return downloadDirectory;
|
return downloadDirectory;
|
||||||
}
|
}
|
||||||
|
|
||||||
protected static CacheDataSourceFactory buildReadOnlyCacheDataSource(
|
protected static CacheDataSource.Factory buildReadOnlyCacheDataSource(
|
||||||
DataSource.Factory upstreamFactory, Cache cache) {
|
DataSource.Factory upstreamFactory, Cache cache) {
|
||||||
return new CacheDataSourceFactory(
|
return new CacheDataSource.Factory()
|
||||||
cache,
|
.setCache(cache)
|
||||||
upstreamFactory,
|
.setUpstreamDataSourceFactory(upstreamFactory)
|
||||||
new FileDataSource.Factory(),
|
.setCacheWriteDataSinkFactory(null)
|
||||||
/* cacheWriteDataSinkFactory= */ null,
|
.setFlags(CacheDataSource.FLAG_IGNORE_CACHE_ON_ERROR);
|
||||||
CacheDataSource.FLAG_IGNORE_CACHE_ON_ERROR,
|
|
||||||
/* eventListener= */ null);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -51,15 +51,15 @@
|
||||||
# Constructors accessed via reflection in DefaultDownloaderFactory
|
# Constructors accessed via reflection in DefaultDownloaderFactory
|
||||||
-dontnote com.google.android.exoplayer2.source.dash.offline.DashDownloader
|
-dontnote com.google.android.exoplayer2.source.dash.offline.DashDownloader
|
||||||
-keepclassmembers class com.google.android.exoplayer2.source.dash.offline.DashDownloader {
|
-keepclassmembers class com.google.android.exoplayer2.source.dash.offline.DashDownloader {
|
||||||
<init>(android.net.Uri, java.util.List, com.google.android.exoplayer2.offline.DownloaderConstructorHelper);
|
<init>(android.net.Uri, java.util.List, com.google.android.exoplayer2.upstream.cache.CacheDataSource.Factory);
|
||||||
}
|
}
|
||||||
-dontnote com.google.android.exoplayer2.source.hls.offline.HlsDownloader
|
-dontnote com.google.android.exoplayer2.source.hls.offline.HlsDownloader
|
||||||
-keepclassmembers class com.google.android.exoplayer2.source.hls.offline.HlsDownloader {
|
-keepclassmembers class com.google.android.exoplayer2.source.hls.offline.HlsDownloader {
|
||||||
<init>(android.net.Uri, java.util.List, com.google.android.exoplayer2.offline.DownloaderConstructorHelper);
|
<init>(android.net.Uri, java.util.List, com.google.android.exoplayer2.upstream.cache.CacheDataSource.Factory);
|
||||||
}
|
}
|
||||||
-dontnote com.google.android.exoplayer2.source.smoothstreaming.offline.SsDownloader
|
-dontnote com.google.android.exoplayer2.source.smoothstreaming.offline.SsDownloader
|
||||||
-keepclassmembers class com.google.android.exoplayer2.source.smoothstreaming.offline.SsDownloader {
|
-keepclassmembers class com.google.android.exoplayer2.source.smoothstreaming.offline.SsDownloader {
|
||||||
<init>(android.net.Uri, java.util.List, com.google.android.exoplayer2.offline.DownloaderConstructorHelper);
|
<init>(android.net.Uri, java.util.List, com.google.android.exoplayer2.upstream.cache.CacheDataSource.Factory);
|
||||||
}
|
}
|
||||||
|
|
||||||
# Constructors accessed via reflection in DefaultMediaSourceFactory and DownloadHelper
|
# Constructors accessed via reflection in DefaultMediaSourceFactory and DownloadHelper
|
||||||
|
|
|
||||||
|
|
@ -17,6 +17,7 @@ package com.google.android.exoplayer2.offline;
|
||||||
|
|
||||||
import android.net.Uri;
|
import android.net.Uri;
|
||||||
import androidx.annotation.Nullable;
|
import androidx.annotation.Nullable;
|
||||||
|
import com.google.android.exoplayer2.upstream.cache.CacheDataSource;
|
||||||
import java.lang.reflect.Constructor;
|
import java.lang.reflect.Constructor;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
|
|
||||||
|
|
@ -32,7 +33,7 @@ public class DefaultDownloaderFactory implements DownloaderFactory {
|
||||||
@Nullable private static final Constructor<? extends Downloader> SS_DOWNLOADER_CONSTRUCTOR;
|
@Nullable private static final Constructor<? extends Downloader> SS_DOWNLOADER_CONSTRUCTOR;
|
||||||
|
|
||||||
static {
|
static {
|
||||||
Constructor<? extends Downloader> dashDownloaderConstructor = null;
|
@Nullable Constructor<? extends Downloader> dashDownloaderConstructor = null;
|
||||||
try {
|
try {
|
||||||
// LINT.IfChange
|
// LINT.IfChange
|
||||||
dashDownloaderConstructor =
|
dashDownloaderConstructor =
|
||||||
|
|
@ -43,7 +44,7 @@ public class DefaultDownloaderFactory implements DownloaderFactory {
|
||||||
// Expected if the app was built without the DASH module.
|
// Expected if the app was built without the DASH module.
|
||||||
}
|
}
|
||||||
DASH_DOWNLOADER_CONSTRUCTOR = dashDownloaderConstructor;
|
DASH_DOWNLOADER_CONSTRUCTOR = dashDownloaderConstructor;
|
||||||
Constructor<? extends Downloader> hlsDownloaderConstructor = null;
|
@Nullable Constructor<? extends Downloader> hlsDownloaderConstructor = null;
|
||||||
try {
|
try {
|
||||||
// LINT.IfChange
|
// LINT.IfChange
|
||||||
hlsDownloaderConstructor =
|
hlsDownloaderConstructor =
|
||||||
|
|
@ -54,7 +55,7 @@ public class DefaultDownloaderFactory implements DownloaderFactory {
|
||||||
// Expected if the app was built without the HLS module.
|
// Expected if the app was built without the HLS module.
|
||||||
}
|
}
|
||||||
HLS_DOWNLOADER_CONSTRUCTOR = hlsDownloaderConstructor;
|
HLS_DOWNLOADER_CONSTRUCTOR = hlsDownloaderConstructor;
|
||||||
Constructor<? extends Downloader> ssDownloaderConstructor = null;
|
@Nullable Constructor<? extends Downloader> ssDownloaderConstructor = null;
|
||||||
try {
|
try {
|
||||||
// LINT.IfChange
|
// LINT.IfChange
|
||||||
ssDownloaderConstructor =
|
ssDownloaderConstructor =
|
||||||
|
|
@ -68,11 +69,16 @@ public class DefaultDownloaderFactory implements DownloaderFactory {
|
||||||
SS_DOWNLOADER_CONSTRUCTOR = ssDownloaderConstructor;
|
SS_DOWNLOADER_CONSTRUCTOR = ssDownloaderConstructor;
|
||||||
}
|
}
|
||||||
|
|
||||||
private final DownloaderConstructorHelper downloaderConstructorHelper;
|
private final CacheDataSource.Factory cacheDataSourceFactory;
|
||||||
|
|
||||||
/** @param downloaderConstructorHelper A helper for instantiating downloaders. */
|
/**
|
||||||
public DefaultDownloaderFactory(DownloaderConstructorHelper downloaderConstructorHelper) {
|
* Creates an instance.
|
||||||
this.downloaderConstructorHelper = downloaderConstructorHelper;
|
*
|
||||||
|
* @param cacheDataSourceFactory A {@link CacheDataSource.Factory} for the cache into which
|
||||||
|
* downloads will be written.
|
||||||
|
*/
|
||||||
|
public DefaultDownloaderFactory(CacheDataSource.Factory cacheDataSourceFactory) {
|
||||||
|
this.cacheDataSourceFactory = cacheDataSourceFactory;
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
|
|
@ -80,7 +86,7 @@ public class DefaultDownloaderFactory implements DownloaderFactory {
|
||||||
switch (request.type) {
|
switch (request.type) {
|
||||||
case DownloadRequest.TYPE_PROGRESSIVE:
|
case DownloadRequest.TYPE_PROGRESSIVE:
|
||||||
return new ProgressiveDownloader(
|
return new ProgressiveDownloader(
|
||||||
request.uri, request.customCacheKey, downloaderConstructorHelper);
|
request.uri, request.customCacheKey, cacheDataSourceFactory);
|
||||||
case DownloadRequest.TYPE_DASH:
|
case DownloadRequest.TYPE_DASH:
|
||||||
return createDownloader(request, DASH_DOWNLOADER_CONSTRUCTOR);
|
return createDownloader(request, DASH_DOWNLOADER_CONSTRUCTOR);
|
||||||
case DownloadRequest.TYPE_HLS:
|
case DownloadRequest.TYPE_HLS:
|
||||||
|
|
@ -98,7 +104,7 @@ public class DefaultDownloaderFactory implements DownloaderFactory {
|
||||||
throw new IllegalStateException("Module missing for: " + request.type);
|
throw new IllegalStateException("Module missing for: " + request.type);
|
||||||
}
|
}
|
||||||
try {
|
try {
|
||||||
return constructor.newInstance(request.uri, request.streamKeys, downloaderConstructorHelper);
|
return constructor.newInstance(request.uri, request.streamKeys, cacheDataSourceFactory);
|
||||||
} catch (Exception e) {
|
} catch (Exception e) {
|
||||||
throw new RuntimeException("Failed to instantiate downloader for: " + request.type, e);
|
throw new RuntimeException("Failed to instantiate downloader for: " + request.type, e);
|
||||||
}
|
}
|
||||||
|
|
@ -109,7 +115,7 @@ public class DefaultDownloaderFactory implements DownloaderFactory {
|
||||||
try {
|
try {
|
||||||
return clazz
|
return clazz
|
||||||
.asSubclass(Downloader.class)
|
.asSubclass(Downloader.class)
|
||||||
.getConstructor(Uri.class, List.class, DownloaderConstructorHelper.class);
|
.getConstructor(Uri.class, List.class, CacheDataSource.Factory.class);
|
||||||
} catch (NoSuchMethodException e) {
|
} catch (NoSuchMethodException e) {
|
||||||
// The downloader is present, but the expected constructor is missing.
|
// The downloader is present, but the expected constructor is missing.
|
||||||
throw new RuntimeException("Downloader constructor missing", e);
|
throw new RuntimeException("Downloader constructor missing", e);
|
||||||
|
|
|
||||||
|
|
@ -40,6 +40,7 @@ import com.google.android.exoplayer2.scheduler.RequirementsWatcher;
|
||||||
import com.google.android.exoplayer2.upstream.DataSource;
|
import com.google.android.exoplayer2.upstream.DataSource;
|
||||||
import com.google.android.exoplayer2.upstream.DataSource.Factory;
|
import com.google.android.exoplayer2.upstream.DataSource.Factory;
|
||||||
import com.google.android.exoplayer2.upstream.cache.Cache;
|
import com.google.android.exoplayer2.upstream.cache.Cache;
|
||||||
|
import com.google.android.exoplayer2.upstream.cache.CacheDataSource;
|
||||||
import com.google.android.exoplayer2.upstream.cache.CacheEvictor;
|
import com.google.android.exoplayer2.upstream.cache.CacheEvictor;
|
||||||
import com.google.android.exoplayer2.upstream.cache.NoOpCacheEvictor;
|
import com.google.android.exoplayer2.upstream.cache.NoOpCacheEvictor;
|
||||||
import com.google.android.exoplayer2.util.Assertions;
|
import com.google.android.exoplayer2.util.Assertions;
|
||||||
|
|
@ -197,7 +198,10 @@ public final class DownloadManager {
|
||||||
this(
|
this(
|
||||||
context,
|
context,
|
||||||
new DefaultDownloadIndex(databaseProvider),
|
new DefaultDownloadIndex(databaseProvider),
|
||||||
new DefaultDownloaderFactory(new DownloaderConstructorHelper(cache, upstreamFactory)));
|
new DefaultDownloaderFactory(
|
||||||
|
new CacheDataSource.Factory()
|
||||||
|
.setCache(cache)
|
||||||
|
.setUpstreamDataSourceFactory(upstreamFactory)));
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
|
|
||||||
|
|
@ -1,135 +0,0 @@
|
||||||
/*
|
|
||||||
* Copyright (C) 2017 The Android Open Source Project
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
package com.google.android.exoplayer2.offline;
|
|
||||||
|
|
||||||
import androidx.annotation.Nullable;
|
|
||||||
import com.google.android.exoplayer2.C;
|
|
||||||
import com.google.android.exoplayer2.upstream.DataSink;
|
|
||||||
import com.google.android.exoplayer2.upstream.DataSource;
|
|
||||||
import com.google.android.exoplayer2.upstream.FileDataSource;
|
|
||||||
import com.google.android.exoplayer2.upstream.cache.Cache;
|
|
||||||
import com.google.android.exoplayer2.upstream.cache.CacheDataSinkFactory;
|
|
||||||
import com.google.android.exoplayer2.upstream.cache.CacheDataSource;
|
|
||||||
import com.google.android.exoplayer2.upstream.cache.CacheKeyFactory;
|
|
||||||
import com.google.android.exoplayer2.util.PriorityTaskManager;
|
|
||||||
|
|
||||||
/** A helper class that holds necessary parameters for {@link Downloader} construction. */
|
|
||||||
public final class DownloaderConstructorHelper {
|
|
||||||
|
|
||||||
private final CacheDataSource.Factory onlineCacheDataSourceFactory;
|
|
||||||
private final CacheDataSource.Factory offlineCacheDataSourceFactory;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* @param cache Cache instance to be used to store downloaded data.
|
|
||||||
* @param upstreamFactory A {@link DataSource.Factory} for creating {@link DataSource}s for
|
|
||||||
* downloading data.
|
|
||||||
*/
|
|
||||||
public DownloaderConstructorHelper(Cache cache, DataSource.Factory upstreamFactory) {
|
|
||||||
this(
|
|
||||||
cache,
|
|
||||||
upstreamFactory,
|
|
||||||
/* cacheReadDataSourceFactory= */ null,
|
|
||||||
/* cacheWriteDataSinkFactory= */ null,
|
|
||||||
/* priorityTaskManager= */ null);
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* @param cache Cache instance to be used to store downloaded data.
|
|
||||||
* @param upstreamFactory A {@link DataSource.Factory} for creating {@link DataSource}s for
|
|
||||||
* downloading data.
|
|
||||||
* @param cacheReadDataSourceFactory A {@link DataSource.Factory} for creating {@link DataSource}s
|
|
||||||
* for reading data from the cache. If null then a {@link FileDataSource.Factory} will be
|
|
||||||
* used.
|
|
||||||
* @param cacheWriteDataSinkFactory A {@link DataSink.Factory} for creating {@link DataSource}s
|
|
||||||
* for writing data to the cache. If null then a {@link CacheDataSinkFactory} will be used.
|
|
||||||
* @param priorityTaskManager A {@link PriorityTaskManager} to use when downloading. If non-null,
|
|
||||||
* downloaders will register as tasks with priority {@link C#PRIORITY_DOWNLOAD} whilst
|
|
||||||
* downloading.
|
|
||||||
*/
|
|
||||||
public DownloaderConstructorHelper(
|
|
||||||
Cache cache,
|
|
||||||
DataSource.Factory upstreamFactory,
|
|
||||||
@Nullable DataSource.Factory cacheReadDataSourceFactory,
|
|
||||||
@Nullable DataSink.Factory cacheWriteDataSinkFactory,
|
|
||||||
@Nullable PriorityTaskManager priorityTaskManager) {
|
|
||||||
this(
|
|
||||||
cache,
|
|
||||||
upstreamFactory,
|
|
||||||
cacheReadDataSourceFactory,
|
|
||||||
cacheWriteDataSinkFactory,
|
|
||||||
priorityTaskManager,
|
|
||||||
/* cacheKeyFactory= */ null);
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* @param cache Cache instance to be used to store downloaded data.
|
|
||||||
* @param upstreamFactory A {@link DataSource.Factory} for creating {@link DataSource}s for
|
|
||||||
* downloading data.
|
|
||||||
* @param cacheReadDataSourceFactory A {@link DataSource.Factory} for creating {@link DataSource}s
|
|
||||||
* for reading data from the cache. If null then a {@link FileDataSource.Factory} will be
|
|
||||||
* used.
|
|
||||||
* @param cacheWriteDataSinkFactory A {@link DataSink.Factory} for creating {@link DataSource}s
|
|
||||||
* for writing data to the cache. If null then a {@link CacheDataSinkFactory} will be used.
|
|
||||||
* @param priorityTaskManager A {@link PriorityTaskManager} to use when downloading. If non-null,
|
|
||||||
* downloaders will register as tasks with priority {@link C#PRIORITY_DOWNLOAD} whilst
|
|
||||||
* downloading.
|
|
||||||
* @param cacheKeyFactory An optional factory for cache keys.
|
|
||||||
*/
|
|
||||||
public DownloaderConstructorHelper(
|
|
||||||
Cache cache,
|
|
||||||
DataSource.Factory upstreamFactory,
|
|
||||||
@Nullable DataSource.Factory cacheReadDataSourceFactory,
|
|
||||||
@Nullable DataSink.Factory cacheWriteDataSinkFactory,
|
|
||||||
@Nullable PriorityTaskManager priorityTaskManager,
|
|
||||||
@Nullable CacheKeyFactory cacheKeyFactory) {
|
|
||||||
onlineCacheDataSourceFactory =
|
|
||||||
new CacheDataSource.Factory()
|
|
||||||
.setCache(cache)
|
|
||||||
.setUpstreamDataSourceFactory(upstreamFactory)
|
|
||||||
.setUpstreamPriorityTaskManager(priorityTaskManager)
|
|
||||||
.setUpstreamPriority(C.PRIORITY_DOWNLOAD)
|
|
||||||
.setFlags(CacheDataSource.FLAG_BLOCK_ON_CACHE);
|
|
||||||
offlineCacheDataSourceFactory =
|
|
||||||
new CacheDataSource.Factory()
|
|
||||||
.setCache(cache)
|
|
||||||
.setCacheWriteDataSinkFactory(null)
|
|
||||||
.setFlags(CacheDataSource.FLAG_BLOCK_ON_CACHE);
|
|
||||||
if (cacheKeyFactory != null) {
|
|
||||||
onlineCacheDataSourceFactory.setCacheKeyFactory(cacheKeyFactory);
|
|
||||||
offlineCacheDataSourceFactory.setCacheKeyFactory(cacheKeyFactory);
|
|
||||||
}
|
|
||||||
if (cacheReadDataSourceFactory != null) {
|
|
||||||
onlineCacheDataSourceFactory.setCacheReadDataSourceFactory(cacheReadDataSourceFactory);
|
|
||||||
offlineCacheDataSourceFactory.setCacheReadDataSourceFactory(cacheReadDataSourceFactory);
|
|
||||||
}
|
|
||||||
if (cacheWriteDataSinkFactory != null) {
|
|
||||||
onlineCacheDataSourceFactory.setCacheWriteDataSinkFactory(cacheWriteDataSinkFactory);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/** Returns a new {@link CacheDataSource} instance. */
|
|
||||||
public CacheDataSource createCacheDataSource() {
|
|
||||||
return onlineCacheDataSourceFactory.createDataSource();
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Returns a new {@link CacheDataSource} instance which accesses cache read-only and throws an
|
|
||||||
* exception on cache miss.
|
|
||||||
*/
|
|
||||||
public CacheDataSource createOfflineCacheDataSource() {
|
|
||||||
return offlineCacheDataSourceFactory.createDataSource();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
@ -25,15 +25,7 @@ import com.google.android.exoplayer2.util.PriorityTaskManager;
|
||||||
import java.io.IOException;
|
import java.io.IOException;
|
||||||
import java.util.concurrent.atomic.AtomicBoolean;
|
import java.util.concurrent.atomic.AtomicBoolean;
|
||||||
|
|
||||||
/**
|
/** A downloader for progressive media streams. */
|
||||||
* A downloader for progressive media streams.
|
|
||||||
*
|
|
||||||
* <p>The downloader attempts to download the entire media bytes referenced by a {@link Uri} into a
|
|
||||||
* cache as defined by {@link DownloaderConstructorHelper}. Callers can use the constructor to
|
|
||||||
* specify a custom cache key for the downloaded bytes.
|
|
||||||
*
|
|
||||||
* <p>The downloader will avoid downloading already-downloaded media bytes.
|
|
||||||
*/
|
|
||||||
public final class ProgressiveDownloader implements Downloader {
|
public final class ProgressiveDownloader implements Downloader {
|
||||||
|
|
||||||
private static final int BUFFER_SIZE_BYTES = 128 * 1024;
|
private static final int BUFFER_SIZE_BYTES = 128 * 1024;
|
||||||
|
|
@ -46,17 +38,18 @@ public final class ProgressiveDownloader implements Downloader {
|
||||||
* @param uri Uri of the data to be downloaded.
|
* @param uri Uri of the data to be downloaded.
|
||||||
* @param customCacheKey A custom key that uniquely identifies the original stream. Used for cache
|
* @param customCacheKey A custom key that uniquely identifies the original stream. Used for cache
|
||||||
* indexing. May be null.
|
* indexing. May be null.
|
||||||
* @param constructorHelper A {@link DownloaderConstructorHelper} instance.
|
* @param cacheDataSourceFactory A {@link CacheDataSource.Factory} for the cache into which the
|
||||||
|
* download will be written.
|
||||||
*/
|
*/
|
||||||
public ProgressiveDownloader(
|
public ProgressiveDownloader(
|
||||||
Uri uri, @Nullable String customCacheKey, DownloaderConstructorHelper constructorHelper) {
|
Uri uri, @Nullable String customCacheKey, CacheDataSource.Factory cacheDataSourceFactory) {
|
||||||
this.dataSpec =
|
dataSpec =
|
||||||
new DataSpec.Builder()
|
new DataSpec.Builder()
|
||||||
.setUri(uri)
|
.setUri(uri)
|
||||||
.setKey(customCacheKey)
|
.setKey(customCacheKey)
|
||||||
.setFlags(DataSpec.FLAG_ALLOW_CACHE_FRAGMENTATION)
|
.setFlags(DataSpec.FLAG_ALLOW_CACHE_FRAGMENTATION)
|
||||||
.build();
|
.build();
|
||||||
this.dataSource = constructorHelper.createCacheDataSource();
|
dataSource = cacheDataSourceFactory.createDataSourceForDownloading();
|
||||||
isCanceled = new AtomicBoolean();
|
isCanceled = new AtomicBoolean();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -67,7 +67,7 @@ public abstract class SegmentDownloader<M extends FilterableManifest<M>> impleme
|
||||||
|
|
||||||
private final DataSpec manifestDataSpec;
|
private final DataSpec manifestDataSpec;
|
||||||
private final CacheDataSource dataSource;
|
private final CacheDataSource dataSource;
|
||||||
private final CacheDataSource offlineDataSource;
|
private final CacheDataSource removingDataSource;
|
||||||
private final ArrayList<StreamKey> streamKeys;
|
private final ArrayList<StreamKey> streamKeys;
|
||||||
private final AtomicBoolean isCanceled;
|
private final AtomicBoolean isCanceled;
|
||||||
|
|
||||||
|
|
@ -75,14 +75,15 @@ public abstract class SegmentDownloader<M extends FilterableManifest<M>> impleme
|
||||||
* @param manifestUri The {@link Uri} of the manifest to be downloaded.
|
* @param manifestUri The {@link Uri} of the manifest to be downloaded.
|
||||||
* @param streamKeys Keys defining which streams in the manifest should be selected for download.
|
* @param streamKeys Keys defining which streams in the manifest should be selected for download.
|
||||||
* If empty, all streams are downloaded.
|
* If empty, all streams are downloaded.
|
||||||
* @param constructorHelper A {@link DownloaderConstructorHelper} instance.
|
* @param cacheDataSourceFactory A {@link CacheDataSource.Factory} for the cache into which the
|
||||||
|
* download will be written.
|
||||||
*/
|
*/
|
||||||
public SegmentDownloader(
|
public SegmentDownloader(
|
||||||
Uri manifestUri, List<StreamKey> streamKeys, DownloaderConstructorHelper constructorHelper) {
|
Uri manifestUri, List<StreamKey> streamKeys, CacheDataSource.Factory cacheDataSourceFactory) {
|
||||||
this.manifestDataSpec = getCompressibleDataSpec(manifestUri);
|
this.manifestDataSpec = getCompressibleDataSpec(manifestUri);
|
||||||
this.streamKeys = new ArrayList<>(streamKeys);
|
this.streamKeys = new ArrayList<>(streamKeys);
|
||||||
this.dataSource = constructorHelper.createCacheDataSource();
|
this.dataSource = cacheDataSourceFactory.createDataSourceForDownloading();
|
||||||
this.offlineDataSource = constructorHelper.createOfflineCacheDataSource();
|
this.removingDataSource = cacheDataSourceFactory.createDataSourceForRemovingDownload();
|
||||||
isCanceled = new AtomicBoolean();
|
isCanceled = new AtomicBoolean();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -176,8 +177,8 @@ public abstract class SegmentDownloader<M extends FilterableManifest<M>> impleme
|
||||||
@Override
|
@Override
|
||||||
public final void remove() throws InterruptedException {
|
public final void remove() throws InterruptedException {
|
||||||
try {
|
try {
|
||||||
M manifest = getManifest(offlineDataSource, manifestDataSpec);
|
M manifest = getManifest(removingDataSource, manifestDataSpec);
|
||||||
List<Segment> segments = getSegments(offlineDataSource, manifest, true);
|
List<Segment> segments = getSegments(removingDataSource, manifest, true);
|
||||||
for (int i = 0; i < segments.size(); i++) {
|
for (int i = 0; i < segments.size(); i++) {
|
||||||
removeDataSpec(segments.get(i).dataSpec);
|
removeDataSpec(segments.get(i).dataSpec);
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -207,12 +207,54 @@ public final class CacheDataSource implements DataSource {
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public CacheDataSource createDataSource() {
|
public CacheDataSource createDataSource() {
|
||||||
|
return createDataSourceInternal(
|
||||||
|
upstreamDataSourceFactory != null ? upstreamDataSourceFactory.createDataSource() : null,
|
||||||
|
flags,
|
||||||
|
upstreamPriority);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Returns an instance suitable for downloading content. The created instance is equivalent to
|
||||||
|
* one that would be created by {@link #createDataSource()}, except:
|
||||||
|
*
|
||||||
|
* <ul>
|
||||||
|
* <li>The {@link #FLAG_BLOCK_ON_CACHE} is always set.
|
||||||
|
* <li>The task priority is overridden to be {@link C#PRIORITY_DOWNLOAD}.
|
||||||
|
* </ul>
|
||||||
|
*
|
||||||
|
* @return An instance suitable for downloading content.
|
||||||
|
*/
|
||||||
|
public CacheDataSource createDataSourceForDownloading() {
|
||||||
|
return createDataSourceInternal(
|
||||||
|
upstreamDataSourceFactory != null ? upstreamDataSourceFactory.createDataSource() : null,
|
||||||
|
flags | FLAG_BLOCK_ON_CACHE,
|
||||||
|
C.PRIORITY_DOWNLOAD);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Returns an instance suitable for reading cached content as part of removing a download. The
|
||||||
|
* created instance is equivalent to one that would be created by {@link #createDataSource()},
|
||||||
|
* except:
|
||||||
|
*
|
||||||
|
* <ul>
|
||||||
|
* <li>The upstream is overridden to be {@code null}, since when removing content we don't
|
||||||
|
* want to request anything that's not already cached.
|
||||||
|
* <li>The {@link #FLAG_BLOCK_ON_CACHE} is always set.
|
||||||
|
* <li>The task priority is overridden to be {@link C#PRIORITY_DOWNLOAD}.
|
||||||
|
* </ul>
|
||||||
|
*
|
||||||
|
* @return An instance suitable for reading cached content as part of removing a download.
|
||||||
|
*/
|
||||||
|
public CacheDataSource createDataSourceForRemovingDownload() {
|
||||||
|
return createDataSourceInternal(
|
||||||
|
/* upstreamDataSource= */ null, flags | FLAG_BLOCK_ON_CACHE, C.PRIORITY_DOWNLOAD);
|
||||||
|
}
|
||||||
|
|
||||||
|
private CacheDataSource createDataSourceInternal(
|
||||||
|
@Nullable DataSource upstreamDataSource, @Flags int flags, int upstreamPriority) {
|
||||||
Cache cache = Assertions.checkNotNull(this.cache);
|
Cache cache = Assertions.checkNotNull(this.cache);
|
||||||
@Nullable
|
|
||||||
DataSource upstreamDataSource =
|
|
||||||
upstreamDataSourceFactory != null ? upstreamDataSourceFactory.createDataSource() : null;
|
|
||||||
@Nullable DataSink cacheWriteDataSink;
|
@Nullable DataSink cacheWriteDataSink;
|
||||||
if (cacheIsReadOnly) {
|
if (cacheIsReadOnly || upstreamDataSource == null) {
|
||||||
cacheWriteDataSink = null;
|
cacheWriteDataSink = null;
|
||||||
} else if (cacheWriteDataSinkFactory != null) {
|
} else if (cacheWriteDataSinkFactory != null) {
|
||||||
cacheWriteDataSink = cacheWriteDataSinkFactory.createDataSink();
|
cacheWriteDataSink = cacheWriteDataSinkFactory.createDataSink();
|
||||||
|
|
|
||||||
|
|
@ -21,6 +21,7 @@ import android.net.Uri;
|
||||||
import androidx.test.ext.junit.runners.AndroidJUnit4;
|
import androidx.test.ext.junit.runners.AndroidJUnit4;
|
||||||
import com.google.android.exoplayer2.upstream.DummyDataSource;
|
import com.google.android.exoplayer2.upstream.DummyDataSource;
|
||||||
import com.google.android.exoplayer2.upstream.cache.Cache;
|
import com.google.android.exoplayer2.upstream.cache.Cache;
|
||||||
|
import com.google.android.exoplayer2.upstream.cache.CacheDataSource;
|
||||||
import java.util.Collections;
|
import java.util.Collections;
|
||||||
import org.junit.Test;
|
import org.junit.Test;
|
||||||
import org.junit.runner.RunWith;
|
import org.junit.runner.RunWith;
|
||||||
|
|
@ -32,9 +33,11 @@ public final class DefaultDownloaderFactoryTest {
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
public void createProgressiveDownloader() throws Exception {
|
public void createProgressiveDownloader() throws Exception {
|
||||||
DownloaderConstructorHelper constructorHelper =
|
CacheDataSource.Factory cacheDataSourceFactory =
|
||||||
new DownloaderConstructorHelper(Mockito.mock(Cache.class), DummyDataSource.FACTORY);
|
new CacheDataSource.Factory()
|
||||||
DownloaderFactory factory = new DefaultDownloaderFactory(constructorHelper);
|
.setCache(Mockito.mock(Cache.class))
|
||||||
|
.setUpstreamDataSourceFactory(DummyDataSource.FACTORY);
|
||||||
|
DownloaderFactory factory = new DefaultDownloaderFactory(cacheDataSourceFactory);
|
||||||
|
|
||||||
Downloader downloader =
|
Downloader downloader =
|
||||||
factory.createDownloader(
|
factory.createDownloader(
|
||||||
|
|
|
||||||
|
|
@ -20,7 +20,6 @@ import androidx.annotation.Nullable;
|
||||||
import com.google.android.exoplayer2.C;
|
import com.google.android.exoplayer2.C;
|
||||||
import com.google.android.exoplayer2.extractor.ChunkIndex;
|
import com.google.android.exoplayer2.extractor.ChunkIndex;
|
||||||
import com.google.android.exoplayer2.offline.DownloadException;
|
import com.google.android.exoplayer2.offline.DownloadException;
|
||||||
import com.google.android.exoplayer2.offline.DownloaderConstructorHelper;
|
|
||||||
import com.google.android.exoplayer2.offline.SegmentDownloader;
|
import com.google.android.exoplayer2.offline.SegmentDownloader;
|
||||||
import com.google.android.exoplayer2.offline.StreamKey;
|
import com.google.android.exoplayer2.offline.StreamKey;
|
||||||
import com.google.android.exoplayer2.source.dash.DashSegmentIndex;
|
import com.google.android.exoplayer2.source.dash.DashSegmentIndex;
|
||||||
|
|
@ -35,6 +34,7 @@ import com.google.android.exoplayer2.source.dash.manifest.Representation;
|
||||||
import com.google.android.exoplayer2.upstream.DataSource;
|
import com.google.android.exoplayer2.upstream.DataSource;
|
||||||
import com.google.android.exoplayer2.upstream.DataSpec;
|
import com.google.android.exoplayer2.upstream.DataSpec;
|
||||||
import com.google.android.exoplayer2.upstream.ParsingLoadable;
|
import com.google.android.exoplayer2.upstream.ParsingLoadable;
|
||||||
|
import com.google.android.exoplayer2.upstream.cache.CacheDataSource;
|
||||||
import java.io.IOException;
|
import java.io.IOException;
|
||||||
import java.util.ArrayList;
|
import java.util.ArrayList;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
|
|
@ -46,19 +46,20 @@ import java.util.List;
|
||||||
*
|
*
|
||||||
* <pre>{@code
|
* <pre>{@code
|
||||||
* SimpleCache cache = new SimpleCache(downloadFolder, new NoOpCacheEvictor(), databaseProvider);
|
* SimpleCache cache = new SimpleCache(downloadFolder, new NoOpCacheEvictor(), databaseProvider);
|
||||||
* DefaultHttpDataSourceFactory factory = new DefaultHttpDataSourceFactory("ExoPlayer", null);
|
* CacheDataSource.Factory cacheDataSourceFactory =
|
||||||
* DownloaderConstructorHelper constructorHelper =
|
* new CacheDataSource.Factory()
|
||||||
* new DownloaderConstructorHelper(cache, factory);
|
* .setCache(cache)
|
||||||
|
* .setUpstreamDataSourceFactory(new DefaultHttpDataSourceFactory(userAgent));
|
||||||
* // Create a downloader for the first representation of the first adaptation set of the first
|
* // Create a downloader for the first representation of the first adaptation set of the first
|
||||||
* // period.
|
* // period.
|
||||||
* DashDownloader dashDownloader =
|
* DashDownloader dashDownloader =
|
||||||
* new DashDownloader(
|
* new DashDownloader(
|
||||||
* manifestUrl, Collections.singletonList(new StreamKey(0, 0, 0)), constructorHelper);
|
* manifestUrl, Collections.singletonList(new StreamKey(0, 0, 0)), cacheDataSourceFactory);
|
||||||
* // Perform the download.
|
* // Perform the download.
|
||||||
* dashDownloader.download(progressListener);
|
* dashDownloader.download(progressListener);
|
||||||
* // Access downloaded data using CacheDataSource
|
* // Use the downloaded data for playback.
|
||||||
* CacheDataSource cacheDataSource =
|
* DashMediaSource mediaSource =
|
||||||
* new CacheDataSource(cache, factory.createDataSource(), CacheDataSource.FLAG_BLOCK_ON_CACHE);
|
* new DashMediaSource.Factory(cacheDataSourceFactory).createMediaSource(mediaItem);
|
||||||
* }</pre>
|
* }</pre>
|
||||||
*/
|
*/
|
||||||
public final class DashDownloader extends SegmentDownloader<DashManifest> {
|
public final class DashDownloader extends SegmentDownloader<DashManifest> {
|
||||||
|
|
@ -67,11 +68,12 @@ public final class DashDownloader extends SegmentDownloader<DashManifest> {
|
||||||
* @param manifestUri The {@link Uri} of the manifest to be downloaded.
|
* @param manifestUri The {@link Uri} of the manifest to be downloaded.
|
||||||
* @param streamKeys Keys defining which representations in the manifest should be selected for
|
* @param streamKeys Keys defining which representations in the manifest should be selected for
|
||||||
* download. If empty, all representations are downloaded.
|
* download. If empty, all representations are downloaded.
|
||||||
* @param constructorHelper A {@link DownloaderConstructorHelper} instance.
|
* @param cacheDataSourceFactory A {@link CacheDataSource.Factory} for the cache into which the
|
||||||
|
* download will be written.
|
||||||
*/
|
*/
|
||||||
public DashDownloader(
|
public DashDownloader(
|
||||||
Uri manifestUri, List<StreamKey> streamKeys, DownloaderConstructorHelper constructorHelper) {
|
Uri manifestUri, List<StreamKey> streamKeys, CacheDataSource.Factory cacheDataSourceFactory) {
|
||||||
super(manifestUri, streamKeys, constructorHelper);
|
super(manifestUri, streamKeys, cacheDataSourceFactory);
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
|
|
|
||||||
|
|
@ -32,17 +32,16 @@ import com.google.android.exoplayer2.offline.DefaultDownloaderFactory;
|
||||||
import com.google.android.exoplayer2.offline.DownloadException;
|
import com.google.android.exoplayer2.offline.DownloadException;
|
||||||
import com.google.android.exoplayer2.offline.DownloadRequest;
|
import com.google.android.exoplayer2.offline.DownloadRequest;
|
||||||
import com.google.android.exoplayer2.offline.Downloader;
|
import com.google.android.exoplayer2.offline.Downloader;
|
||||||
import com.google.android.exoplayer2.offline.DownloaderConstructorHelper;
|
|
||||||
import com.google.android.exoplayer2.offline.DownloaderFactory;
|
import com.google.android.exoplayer2.offline.DownloaderFactory;
|
||||||
import com.google.android.exoplayer2.offline.StreamKey;
|
import com.google.android.exoplayer2.offline.StreamKey;
|
||||||
import com.google.android.exoplayer2.testutil.CacheAsserts.RequestSet;
|
import com.google.android.exoplayer2.testutil.CacheAsserts.RequestSet;
|
||||||
import com.google.android.exoplayer2.testutil.FakeDataSet;
|
import com.google.android.exoplayer2.testutil.FakeDataSet;
|
||||||
import com.google.android.exoplayer2.testutil.FakeDataSource;
|
import com.google.android.exoplayer2.testutil.FakeDataSource;
|
||||||
import com.google.android.exoplayer2.testutil.FakeDataSource.Factory;
|
|
||||||
import com.google.android.exoplayer2.testutil.TestUtil;
|
import com.google.android.exoplayer2.testutil.TestUtil;
|
||||||
import com.google.android.exoplayer2.upstream.DataSpec;
|
import com.google.android.exoplayer2.upstream.DataSpec;
|
||||||
import com.google.android.exoplayer2.upstream.DummyDataSource;
|
import com.google.android.exoplayer2.upstream.DummyDataSource;
|
||||||
import com.google.android.exoplayer2.upstream.cache.Cache;
|
import com.google.android.exoplayer2.upstream.cache.Cache;
|
||||||
|
import com.google.android.exoplayer2.upstream.cache.CacheDataSource;
|
||||||
import com.google.android.exoplayer2.upstream.cache.NoOpCacheEvictor;
|
import com.google.android.exoplayer2.upstream.cache.NoOpCacheEvictor;
|
||||||
import com.google.android.exoplayer2.upstream.cache.SimpleCache;
|
import com.google.android.exoplayer2.upstream.cache.SimpleCache;
|
||||||
import com.google.android.exoplayer2.util.Util;
|
import com.google.android.exoplayer2.util.Util;
|
||||||
|
|
@ -81,9 +80,11 @@ public class DashDownloaderTest {
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
public void createWithDefaultDownloaderFactory() {
|
public void createWithDefaultDownloaderFactory() {
|
||||||
DownloaderConstructorHelper constructorHelper =
|
CacheDataSource.Factory cacheDataSourceFactory =
|
||||||
new DownloaderConstructorHelper(Mockito.mock(Cache.class), DummyDataSource.FACTORY);
|
new CacheDataSource.Factory()
|
||||||
DownloaderFactory factory = new DefaultDownloaderFactory(constructorHelper);
|
.setCache(Mockito.mock(Cache.class))
|
||||||
|
.setUpstreamDataSourceFactory(DummyDataSource.FACTORY);
|
||||||
|
DownloaderFactory factory = new DefaultDownloaderFactory(cacheDataSourceFactory);
|
||||||
|
|
||||||
Downloader downloader =
|
Downloader downloader =
|
||||||
factory.createDownloader(
|
factory.createDownloader(
|
||||||
|
|
@ -184,7 +185,7 @@ public class DashDownloaderTest {
|
||||||
.setRandomData("text_segment_2", 2)
|
.setRandomData("text_segment_2", 2)
|
||||||
.setRandomData("text_segment_3", 3);
|
.setRandomData("text_segment_3", 3);
|
||||||
FakeDataSource fakeDataSource = new FakeDataSource(fakeDataSet);
|
FakeDataSource fakeDataSource = new FakeDataSource(fakeDataSet);
|
||||||
Factory factory = mock(Factory.class);
|
FakeDataSource.Factory factory = mock(FakeDataSource.Factory.class);
|
||||||
when(factory.createDataSource()).thenReturn(fakeDataSource);
|
when(factory.createDataSource()).thenReturn(fakeDataSource);
|
||||||
|
|
||||||
DashDownloader dashDownloader =
|
DashDownloader dashDownloader =
|
||||||
|
|
@ -216,7 +217,7 @@ public class DashDownloaderTest {
|
||||||
.setRandomData("period_2_segment_2", 2)
|
.setRandomData("period_2_segment_2", 2)
|
||||||
.setRandomData("period_2_segment_3", 3);
|
.setRandomData("period_2_segment_3", 3);
|
||||||
FakeDataSource fakeDataSource = new FakeDataSource(fakeDataSet);
|
FakeDataSource fakeDataSource = new FakeDataSource(fakeDataSet);
|
||||||
Factory factory = mock(Factory.class);
|
FakeDataSource.Factory factory = mock(FakeDataSource.Factory.class);
|
||||||
when(factory.createDataSource()).thenReturn(fakeDataSource);
|
when(factory.createDataSource()).thenReturn(fakeDataSource);
|
||||||
|
|
||||||
DashDownloader dashDownloader =
|
DashDownloader dashDownloader =
|
||||||
|
|
@ -327,12 +328,16 @@ public class DashDownloaderTest {
|
||||||
}
|
}
|
||||||
|
|
||||||
private DashDownloader getDashDownloader(FakeDataSet fakeDataSet, StreamKey... keys) {
|
private DashDownloader getDashDownloader(FakeDataSet fakeDataSet, StreamKey... keys) {
|
||||||
return getDashDownloader(new Factory().setFakeDataSet(fakeDataSet), keys);
|
return getDashDownloader(new FakeDataSource.Factory().setFakeDataSet(fakeDataSet), keys);
|
||||||
}
|
}
|
||||||
|
|
||||||
private DashDownloader getDashDownloader(Factory factory, StreamKey... keys) {
|
private DashDownloader getDashDownloader(
|
||||||
return new DashDownloader(
|
FakeDataSource.Factory upstreamDataSourceFactory, StreamKey... keys) {
|
||||||
TEST_MPD_URI, keysList(keys), new DownloaderConstructorHelper(cache, factory));
|
CacheDataSource.Factory cacheDataSourceFactory =
|
||||||
|
new CacheDataSource.Factory()
|
||||||
|
.setCache(cache)
|
||||||
|
.setUpstreamDataSourceFactory(upstreamDataSourceFactory);
|
||||||
|
return new DashDownloader(TEST_MPD_URI, keysList(keys), cacheDataSourceFactory);
|
||||||
}
|
}
|
||||||
|
|
||||||
private static ArrayList<StreamKey> keysList(StreamKey... keys) {
|
private static ArrayList<StreamKey> keysList(StreamKey... keys) {
|
||||||
|
|
|
||||||
|
|
@ -29,7 +29,6 @@ import com.google.android.exoplayer2.offline.DefaultDownloadIndex;
|
||||||
import com.google.android.exoplayer2.offline.DefaultDownloaderFactory;
|
import com.google.android.exoplayer2.offline.DefaultDownloaderFactory;
|
||||||
import com.google.android.exoplayer2.offline.DownloadManager;
|
import com.google.android.exoplayer2.offline.DownloadManager;
|
||||||
import com.google.android.exoplayer2.offline.DownloadRequest;
|
import com.google.android.exoplayer2.offline.DownloadRequest;
|
||||||
import com.google.android.exoplayer2.offline.DownloaderConstructorHelper;
|
|
||||||
import com.google.android.exoplayer2.offline.StreamKey;
|
import com.google.android.exoplayer2.offline.StreamKey;
|
||||||
import com.google.android.exoplayer2.scheduler.Requirements;
|
import com.google.android.exoplayer2.scheduler.Requirements;
|
||||||
import com.google.android.exoplayer2.testutil.CacheAsserts.RequestSet;
|
import com.google.android.exoplayer2.testutil.CacheAsserts.RequestSet;
|
||||||
|
|
@ -40,6 +39,7 @@ import com.google.android.exoplayer2.testutil.FakeDataSource;
|
||||||
import com.google.android.exoplayer2.testutil.TestDownloadManagerListener;
|
import com.google.android.exoplayer2.testutil.TestDownloadManagerListener;
|
||||||
import com.google.android.exoplayer2.testutil.TestUtil;
|
import com.google.android.exoplayer2.testutil.TestUtil;
|
||||||
import com.google.android.exoplayer2.upstream.DataSource.Factory;
|
import com.google.android.exoplayer2.upstream.DataSource.Factory;
|
||||||
|
import com.google.android.exoplayer2.upstream.cache.CacheDataSource;
|
||||||
import com.google.android.exoplayer2.upstream.cache.NoOpCacheEvictor;
|
import com.google.android.exoplayer2.upstream.cache.NoOpCacheEvictor;
|
||||||
import com.google.android.exoplayer2.upstream.cache.SimpleCache;
|
import com.google.android.exoplayer2.upstream.cache.SimpleCache;
|
||||||
import com.google.android.exoplayer2.util.Util;
|
import com.google.android.exoplayer2.util.Util;
|
||||||
|
|
@ -253,12 +253,14 @@ public class DownloadManagerDashTest {
|
||||||
runOnMainThread(
|
runOnMainThread(
|
||||||
() -> {
|
() -> {
|
||||||
Factory fakeDataSourceFactory = new FakeDataSource.Factory().setFakeDataSet(fakeDataSet);
|
Factory fakeDataSourceFactory = new FakeDataSource.Factory().setFakeDataSet(fakeDataSet);
|
||||||
|
DefaultDownloaderFactory downloaderFactory =
|
||||||
|
new DefaultDownloaderFactory(
|
||||||
|
new CacheDataSource.Factory()
|
||||||
|
.setCache(cache)
|
||||||
|
.setUpstreamDataSourceFactory(fakeDataSourceFactory));
|
||||||
downloadManager =
|
downloadManager =
|
||||||
new DownloadManager(
|
new DownloadManager(
|
||||||
ApplicationProvider.getApplicationContext(),
|
ApplicationProvider.getApplicationContext(), downloadIndex, downloaderFactory);
|
||||||
downloadIndex,
|
|
||||||
new DefaultDownloaderFactory(
|
|
||||||
new DownloaderConstructorHelper(cache, fakeDataSourceFactory)));
|
|
||||||
downloadManager.setRequirements(new Requirements(0));
|
downloadManager.setRequirements(new Requirements(0));
|
||||||
|
|
||||||
downloadManagerListener =
|
downloadManagerListener =
|
||||||
|
|
|
||||||
|
|
@ -33,7 +33,6 @@ import com.google.android.exoplayer2.offline.Download;
|
||||||
import com.google.android.exoplayer2.offline.DownloadManager;
|
import com.google.android.exoplayer2.offline.DownloadManager;
|
||||||
import com.google.android.exoplayer2.offline.DownloadRequest;
|
import com.google.android.exoplayer2.offline.DownloadRequest;
|
||||||
import com.google.android.exoplayer2.offline.DownloadService;
|
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.offline.StreamKey;
|
||||||
import com.google.android.exoplayer2.scheduler.Scheduler;
|
import com.google.android.exoplayer2.scheduler.Scheduler;
|
||||||
import com.google.android.exoplayer2.testutil.DummyMainThread;
|
import com.google.android.exoplayer2.testutil.DummyMainThread;
|
||||||
|
|
@ -42,6 +41,7 @@ import com.google.android.exoplayer2.testutil.FakeDataSource;
|
||||||
import com.google.android.exoplayer2.testutil.TestDownloadManagerListener;
|
import com.google.android.exoplayer2.testutil.TestDownloadManagerListener;
|
||||||
import com.google.android.exoplayer2.testutil.TestUtil;
|
import com.google.android.exoplayer2.testutil.TestUtil;
|
||||||
import com.google.android.exoplayer2.upstream.DataSource;
|
import com.google.android.exoplayer2.upstream.DataSource;
|
||||||
|
import com.google.android.exoplayer2.upstream.cache.CacheDataSource;
|
||||||
import com.google.android.exoplayer2.upstream.cache.NoOpCacheEvictor;
|
import com.google.android.exoplayer2.upstream.cache.NoOpCacheEvictor;
|
||||||
import com.google.android.exoplayer2.upstream.cache.SimpleCache;
|
import com.google.android.exoplayer2.upstream.cache.SimpleCache;
|
||||||
import com.google.android.exoplayer2.util.ConditionVariable;
|
import com.google.android.exoplayer2.util.ConditionVariable;
|
||||||
|
|
@ -113,12 +113,14 @@ public class DownloadServiceDashTest {
|
||||||
() -> {
|
() -> {
|
||||||
DefaultDownloadIndex downloadIndex =
|
DefaultDownloadIndex downloadIndex =
|
||||||
new DefaultDownloadIndex(TestUtil.getInMemoryDatabaseProvider());
|
new DefaultDownloadIndex(TestUtil.getInMemoryDatabaseProvider());
|
||||||
|
DefaultDownloaderFactory downloaderFactory =
|
||||||
|
new DefaultDownloaderFactory(
|
||||||
|
new CacheDataSource.Factory()
|
||||||
|
.setCache(cache)
|
||||||
|
.setUpstreamDataSourceFactory(fakeDataSourceFactory));
|
||||||
final DownloadManager dashDownloadManager =
|
final DownloadManager dashDownloadManager =
|
||||||
new DownloadManager(
|
new DownloadManager(
|
||||||
ApplicationProvider.getApplicationContext(),
|
ApplicationProvider.getApplicationContext(), downloadIndex, downloaderFactory);
|
||||||
downloadIndex,
|
|
||||||
new DefaultDownloaderFactory(
|
|
||||||
new DownloaderConstructorHelper(cache, fakeDataSourceFactory)));
|
|
||||||
downloadManagerListener =
|
downloadManagerListener =
|
||||||
new TestDownloadManagerListener(dashDownloadManager, dummyMainThread);
|
new TestDownloadManagerListener(dashDownloadManager, dummyMainThread);
|
||||||
dashDownloadManager.resumeDownloads();
|
dashDownloadManager.resumeDownloads();
|
||||||
|
|
|
||||||
|
|
@ -17,7 +17,6 @@ package com.google.android.exoplayer2.source.hls.offline;
|
||||||
|
|
||||||
import android.net.Uri;
|
import android.net.Uri;
|
||||||
import com.google.android.exoplayer2.C;
|
import com.google.android.exoplayer2.C;
|
||||||
import com.google.android.exoplayer2.offline.DownloaderConstructorHelper;
|
|
||||||
import com.google.android.exoplayer2.offline.SegmentDownloader;
|
import com.google.android.exoplayer2.offline.SegmentDownloader;
|
||||||
import com.google.android.exoplayer2.offline.StreamKey;
|
import com.google.android.exoplayer2.offline.StreamKey;
|
||||||
import com.google.android.exoplayer2.source.hls.playlist.HlsMasterPlaylist;
|
import com.google.android.exoplayer2.source.hls.playlist.HlsMasterPlaylist;
|
||||||
|
|
@ -27,6 +26,7 @@ import com.google.android.exoplayer2.source.hls.playlist.HlsPlaylistParser;
|
||||||
import com.google.android.exoplayer2.upstream.DataSource;
|
import com.google.android.exoplayer2.upstream.DataSource;
|
||||||
import com.google.android.exoplayer2.upstream.DataSpec;
|
import com.google.android.exoplayer2.upstream.DataSpec;
|
||||||
import com.google.android.exoplayer2.upstream.ParsingLoadable;
|
import com.google.android.exoplayer2.upstream.ParsingLoadable;
|
||||||
|
import com.google.android.exoplayer2.upstream.cache.CacheDataSource;
|
||||||
import com.google.android.exoplayer2.util.UriUtil;
|
import com.google.android.exoplayer2.util.UriUtil;
|
||||||
import java.io.IOException;
|
import java.io.IOException;
|
||||||
import java.util.ArrayList;
|
import java.util.ArrayList;
|
||||||
|
|
@ -40,20 +40,20 @@ import java.util.List;
|
||||||
*
|
*
|
||||||
* <pre>{@code
|
* <pre>{@code
|
||||||
* SimpleCache cache = new SimpleCache(downloadFolder, new NoOpCacheEvictor(), databaseProvider);
|
* SimpleCache cache = new SimpleCache(downloadFolder, new NoOpCacheEvictor(), databaseProvider);
|
||||||
* DefaultHttpDataSourceFactory factory = new DefaultHttpDataSourceFactory("ExoPlayer", null);
|
* CacheDataSource.Factory cacheDataSourceFactory =
|
||||||
* DownloaderConstructorHelper constructorHelper =
|
* new CacheDataSource.Factory()
|
||||||
* new DownloaderConstructorHelper(cache, factory);
|
* .setCache(cache)
|
||||||
|
* .setUpstreamDataSourceFactory(new DefaultHttpDataSourceFactory(userAgent));
|
||||||
* // Create a downloader for the first variant in a master playlist.
|
* // Create a downloader for the first variant in a master playlist.
|
||||||
* HlsDownloader hlsDownloader =
|
* HlsDownloader hlsDownloader =
|
||||||
* new HlsDownloader(
|
* new HlsDownloader(
|
||||||
* playlistUri,
|
* playlistUri,
|
||||||
* Collections.singletonList(new StreamKey(HlsMasterPlaylist.GROUP_INDEX_VARIANT, 0)),
|
* Collections.singletonList(new StreamKey(HlsMasterPlaylist.GROUP_INDEX_VARIANT, 0));
|
||||||
* constructorHelper);
|
|
||||||
* // Perform the download.
|
* // Perform the download.
|
||||||
* hlsDownloader.download(progressListener);
|
* hlsDownloader.download(progressListener);
|
||||||
* // Access downloaded data using CacheDataSource
|
* // Use the downloaded data for playback.
|
||||||
* CacheDataSource cacheDataSource =
|
* HlsMediaSource mediaSource =
|
||||||
* new CacheDataSource(cache, factory.createDataSource(), CacheDataSource.FLAG_BLOCK_ON_CACHE);
|
* new HlsMediaSource.Factory(cacheDataSourceFactory).createMediaSource(mediaItem);
|
||||||
* }</pre>
|
* }</pre>
|
||||||
*/
|
*/
|
||||||
public final class HlsDownloader extends SegmentDownloader<HlsPlaylist> {
|
public final class HlsDownloader extends SegmentDownloader<HlsPlaylist> {
|
||||||
|
|
@ -62,11 +62,12 @@ public final class HlsDownloader extends SegmentDownloader<HlsPlaylist> {
|
||||||
* @param playlistUri The {@link Uri} of the playlist to be downloaded.
|
* @param playlistUri The {@link Uri} of the playlist to be downloaded.
|
||||||
* @param streamKeys Keys defining which renditions in the playlist should be selected for
|
* @param streamKeys Keys defining which renditions in the playlist should be selected for
|
||||||
* download. If empty, all renditions are downloaded.
|
* download. If empty, all renditions are downloaded.
|
||||||
* @param constructorHelper A {@link DownloaderConstructorHelper} instance.
|
* @param cacheDataSourceFactory A {@link CacheDataSource.Factory} for the cache into which the
|
||||||
|
* download will be written.
|
||||||
*/
|
*/
|
||||||
public HlsDownloader(
|
public HlsDownloader(
|
||||||
Uri playlistUri, List<StreamKey> streamKeys, DownloaderConstructorHelper constructorHelper) {
|
Uri playlistUri, List<StreamKey> streamKeys, CacheDataSource.Factory cacheDataSourceFactory) {
|
||||||
super(playlistUri, streamKeys, constructorHelper);
|
super(playlistUri, streamKeys, cacheDataSourceFactory);
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
|
|
|
||||||
|
|
@ -40,15 +40,15 @@ import androidx.test.ext.junit.runners.AndroidJUnit4;
|
||||||
import com.google.android.exoplayer2.offline.DefaultDownloaderFactory;
|
import com.google.android.exoplayer2.offline.DefaultDownloaderFactory;
|
||||||
import com.google.android.exoplayer2.offline.DownloadRequest;
|
import com.google.android.exoplayer2.offline.DownloadRequest;
|
||||||
import com.google.android.exoplayer2.offline.Downloader;
|
import com.google.android.exoplayer2.offline.Downloader;
|
||||||
import com.google.android.exoplayer2.offline.DownloaderConstructorHelper;
|
|
||||||
import com.google.android.exoplayer2.offline.DownloaderFactory;
|
import com.google.android.exoplayer2.offline.DownloaderFactory;
|
||||||
import com.google.android.exoplayer2.offline.StreamKey;
|
import com.google.android.exoplayer2.offline.StreamKey;
|
||||||
import com.google.android.exoplayer2.source.hls.playlist.HlsMasterPlaylist;
|
import com.google.android.exoplayer2.source.hls.playlist.HlsMasterPlaylist;
|
||||||
import com.google.android.exoplayer2.testutil.CacheAsserts.RequestSet;
|
import com.google.android.exoplayer2.testutil.CacheAsserts.RequestSet;
|
||||||
import com.google.android.exoplayer2.testutil.FakeDataSet;
|
import com.google.android.exoplayer2.testutil.FakeDataSet;
|
||||||
import com.google.android.exoplayer2.testutil.FakeDataSource.Factory;
|
import com.google.android.exoplayer2.testutil.FakeDataSource;
|
||||||
import com.google.android.exoplayer2.upstream.DummyDataSource;
|
import com.google.android.exoplayer2.upstream.DummyDataSource;
|
||||||
import com.google.android.exoplayer2.upstream.cache.Cache;
|
import com.google.android.exoplayer2.upstream.cache.Cache;
|
||||||
|
import com.google.android.exoplayer2.upstream.cache.CacheDataSource;
|
||||||
import com.google.android.exoplayer2.upstream.cache.NoOpCacheEvictor;
|
import com.google.android.exoplayer2.upstream.cache.NoOpCacheEvictor;
|
||||||
import com.google.android.exoplayer2.upstream.cache.SimpleCache;
|
import com.google.android.exoplayer2.upstream.cache.SimpleCache;
|
||||||
import com.google.android.exoplayer2.util.Util;
|
import com.google.android.exoplayer2.util.Util;
|
||||||
|
|
@ -97,9 +97,11 @@ public class HlsDownloaderTest {
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
public void createWithDefaultDownloaderFactory() {
|
public void createWithDefaultDownloaderFactory() {
|
||||||
DownloaderConstructorHelper constructorHelper =
|
CacheDataSource.Factory cacheDataSourceFactory =
|
||||||
new DownloaderConstructorHelper(Mockito.mock(Cache.class), DummyDataSource.FACTORY);
|
new CacheDataSource.Factory()
|
||||||
DownloaderFactory factory = new DefaultDownloaderFactory(constructorHelper);
|
.setCache(Mockito.mock(Cache.class))
|
||||||
|
.setUpstreamDataSourceFactory(DummyDataSource.FACTORY);
|
||||||
|
DownloaderFactory factory = new DefaultDownloaderFactory(cacheDataSourceFactory);
|
||||||
|
|
||||||
Downloader downloader =
|
Downloader downloader =
|
||||||
factory.createDownloader(
|
factory.createDownloader(
|
||||||
|
|
@ -213,9 +215,11 @@ public class HlsDownloaderTest {
|
||||||
}
|
}
|
||||||
|
|
||||||
private HlsDownloader getHlsDownloader(String mediaPlaylistUri, List<StreamKey> keys) {
|
private HlsDownloader getHlsDownloader(String mediaPlaylistUri, List<StreamKey> keys) {
|
||||||
Factory factory = new Factory().setFakeDataSet(fakeDataSet);
|
CacheDataSource.Factory cacheDataSourceFactory =
|
||||||
return new HlsDownloader(
|
new CacheDataSource.Factory()
|
||||||
Uri.parse(mediaPlaylistUri), keys, new DownloaderConstructorHelper(cache, factory));
|
.setCache(cache)
|
||||||
|
.setUpstreamDataSourceFactory(new FakeDataSource.Factory().setFakeDataSet(fakeDataSet));
|
||||||
|
return new HlsDownloader(Uri.parse(mediaPlaylistUri), keys, cacheDataSourceFactory);
|
||||||
}
|
}
|
||||||
|
|
||||||
private static ArrayList<StreamKey> getKeys(int... variantIndices) {
|
private static ArrayList<StreamKey> getKeys(int... variantIndices) {
|
||||||
|
|
|
||||||
|
|
@ -17,7 +17,6 @@ package com.google.android.exoplayer2.source.smoothstreaming.offline;
|
||||||
|
|
||||||
import android.net.Uri;
|
import android.net.Uri;
|
||||||
import com.google.android.exoplayer2.C;
|
import com.google.android.exoplayer2.C;
|
||||||
import com.google.android.exoplayer2.offline.DownloaderConstructorHelper;
|
|
||||||
import com.google.android.exoplayer2.offline.SegmentDownloader;
|
import com.google.android.exoplayer2.offline.SegmentDownloader;
|
||||||
import com.google.android.exoplayer2.offline.StreamKey;
|
import com.google.android.exoplayer2.offline.StreamKey;
|
||||||
import com.google.android.exoplayer2.source.smoothstreaming.manifest.SsManifest;
|
import com.google.android.exoplayer2.source.smoothstreaming.manifest.SsManifest;
|
||||||
|
|
@ -27,6 +26,7 @@ import com.google.android.exoplayer2.source.smoothstreaming.manifest.SsUtil;
|
||||||
import com.google.android.exoplayer2.upstream.DataSource;
|
import com.google.android.exoplayer2.upstream.DataSource;
|
||||||
import com.google.android.exoplayer2.upstream.DataSpec;
|
import com.google.android.exoplayer2.upstream.DataSpec;
|
||||||
import com.google.android.exoplayer2.upstream.ParsingLoadable;
|
import com.google.android.exoplayer2.upstream.ParsingLoadable;
|
||||||
|
import com.google.android.exoplayer2.upstream.cache.CacheDataSource;
|
||||||
import java.io.IOException;
|
import java.io.IOException;
|
||||||
import java.util.ArrayList;
|
import java.util.ArrayList;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
|
|
@ -38,20 +38,21 @@ import java.util.List;
|
||||||
*
|
*
|
||||||
* <pre>{@code
|
* <pre>{@code
|
||||||
* SimpleCache cache = new SimpleCache(downloadFolder, new NoOpCacheEvictor(), databaseProvider);
|
* SimpleCache cache = new SimpleCache(downloadFolder, new NoOpCacheEvictor(), databaseProvider);
|
||||||
* DefaultHttpDataSourceFactory factory = new DefaultHttpDataSourceFactory("ExoPlayer", null);
|
* CacheDataSource.Factory cacheDataSourceFactory =
|
||||||
* DownloaderConstructorHelper constructorHelper =
|
* new CacheDataSource.Factory()
|
||||||
* new DownloaderConstructorHelper(cache, factory);
|
* .setCache(cache)
|
||||||
|
* .setUpstreamDataSourceFactory(new DefaultHttpDataSourceFactory(userAgent));
|
||||||
* // Create a downloader for the first track of the first stream element.
|
* // Create a downloader for the first track of the first stream element.
|
||||||
* SsDownloader ssDownloader =
|
* SsDownloader ssDownloader =
|
||||||
* new SsDownloader(
|
* new SsDownloader(
|
||||||
* manifestUrl,
|
* manifestUrl,
|
||||||
* Collections.singletonList(new StreamKey(0, 0)),
|
* Collections.singletonList(new StreamKey(0, 0)),
|
||||||
* constructorHelper);
|
* cacheDataSourceFactory);
|
||||||
* // Perform the download.
|
* // Perform the download.
|
||||||
* ssDownloader.download(progressListener);
|
* ssDownloader.download(progressListener);
|
||||||
* // Access downloaded data using CacheDataSource
|
* // Use the downloaded data for playback.
|
||||||
* CacheDataSource cacheDataSource =
|
* SsMediaSource mediaSource =
|
||||||
* new CacheDataSource(cache, factory.createDataSource(), CacheDataSource.FLAG_BLOCK_ON_CACHE);
|
* new SsMediaSource.Factory(cacheDataSourceFactory).createMediaSource(mediaItem);
|
||||||
* }</pre>
|
* }</pre>
|
||||||
*/
|
*/
|
||||||
public final class SsDownloader extends SegmentDownloader<SsManifest> {
|
public final class SsDownloader extends SegmentDownloader<SsManifest> {
|
||||||
|
|
@ -60,11 +61,12 @@ public final class SsDownloader extends SegmentDownloader<SsManifest> {
|
||||||
* @param manifestUri The {@link Uri} of the manifest to be downloaded.
|
* @param manifestUri The {@link Uri} of the manifest to be downloaded.
|
||||||
* @param streamKeys Keys defining which streams in the manifest should be selected for download.
|
* @param streamKeys Keys defining which streams in the manifest should be selected for download.
|
||||||
* If empty, all streams are downloaded.
|
* If empty, all streams are downloaded.
|
||||||
* @param constructorHelper A {@link DownloaderConstructorHelper} instance.
|
* @param cacheDataSourceFactory A {@link CacheDataSource.Factory} for the cache into which the
|
||||||
|
* download will be written.
|
||||||
*/
|
*/
|
||||||
public SsDownloader(
|
public SsDownloader(
|
||||||
Uri manifestUri, List<StreamKey> streamKeys, DownloaderConstructorHelper constructorHelper) {
|
Uri manifestUri, List<StreamKey> streamKeys, CacheDataSource.Factory cacheDataSourceFactory) {
|
||||||
super(SsUtil.fixManifestUri(manifestUri), streamKeys, constructorHelper);
|
super(SsUtil.fixManifestUri(manifestUri), streamKeys, cacheDataSourceFactory);
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
|
|
|
||||||
|
|
@ -22,11 +22,11 @@ import androidx.test.ext.junit.runners.AndroidJUnit4;
|
||||||
import com.google.android.exoplayer2.offline.DefaultDownloaderFactory;
|
import com.google.android.exoplayer2.offline.DefaultDownloaderFactory;
|
||||||
import com.google.android.exoplayer2.offline.DownloadRequest;
|
import com.google.android.exoplayer2.offline.DownloadRequest;
|
||||||
import com.google.android.exoplayer2.offline.Downloader;
|
import com.google.android.exoplayer2.offline.Downloader;
|
||||||
import com.google.android.exoplayer2.offline.DownloaderConstructorHelper;
|
|
||||||
import com.google.android.exoplayer2.offline.DownloaderFactory;
|
import com.google.android.exoplayer2.offline.DownloaderFactory;
|
||||||
import com.google.android.exoplayer2.offline.StreamKey;
|
import com.google.android.exoplayer2.offline.StreamKey;
|
||||||
import com.google.android.exoplayer2.upstream.DummyDataSource;
|
import com.google.android.exoplayer2.upstream.DummyDataSource;
|
||||||
import com.google.android.exoplayer2.upstream.cache.Cache;
|
import com.google.android.exoplayer2.upstream.cache.Cache;
|
||||||
|
import com.google.android.exoplayer2.upstream.cache.CacheDataSource;
|
||||||
import java.util.Collections;
|
import java.util.Collections;
|
||||||
import org.junit.Test;
|
import org.junit.Test;
|
||||||
import org.junit.runner.RunWith;
|
import org.junit.runner.RunWith;
|
||||||
|
|
@ -38,9 +38,11 @@ public final class SsDownloaderTest {
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
public void createWithDefaultDownloaderFactory() throws Exception {
|
public void createWithDefaultDownloaderFactory() throws Exception {
|
||||||
DownloaderConstructorHelper constructorHelper =
|
CacheDataSource.Factory cacheDataSourceFactory =
|
||||||
new DownloaderConstructorHelper(Mockito.mock(Cache.class), DummyDataSource.FACTORY);
|
new CacheDataSource.Factory()
|
||||||
DownloaderFactory factory = new DefaultDownloaderFactory(constructorHelper);
|
.setCache(Mockito.mock(Cache.class))
|
||||||
|
.setUpstreamDataSourceFactory(DummyDataSource.FACTORY);
|
||||||
|
DownloaderFactory factory = new DefaultDownloaderFactory(cacheDataSourceFactory);
|
||||||
|
|
||||||
Downloader downloader =
|
Downloader downloader =
|
||||||
factory.createDownloader(
|
factory.createDownloader(
|
||||||
|
|
|
||||||
|
|
@ -20,7 +20,6 @@ import static com.google.common.truth.Truth.assertWithMessage;
|
||||||
import android.net.Uri;
|
import android.net.Uri;
|
||||||
import androidx.test.ext.junit.runners.AndroidJUnit4;
|
import androidx.test.ext.junit.runners.AndroidJUnit4;
|
||||||
import androidx.test.rule.ActivityTestRule;
|
import androidx.test.rule.ActivityTestRule;
|
||||||
import com.google.android.exoplayer2.offline.DownloaderConstructorHelper;
|
|
||||||
import com.google.android.exoplayer2.offline.StreamKey;
|
import com.google.android.exoplayer2.offline.StreamKey;
|
||||||
import com.google.android.exoplayer2.source.dash.DashUtil;
|
import com.google.android.exoplayer2.source.dash.DashUtil;
|
||||||
import com.google.android.exoplayer2.source.dash.manifest.AdaptationSet;
|
import com.google.android.exoplayer2.source.dash.manifest.AdaptationSet;
|
||||||
|
|
@ -120,9 +119,11 @@ public final class DashDownloadTest {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
DownloaderConstructorHelper constructorHelper =
|
CacheDataSource.Factory cacheDataSourceFactory =
|
||||||
new DownloaderConstructorHelper(cache, httpDataSourceFactory);
|
new CacheDataSource.Factory()
|
||||||
return new DashDownloader(MANIFEST_URI, keys, constructorHelper);
|
.setCache(cache)
|
||||||
|
.setUpstreamDataSourceFactory(httpDataSourceFactory);
|
||||||
|
return new DashDownloader(MANIFEST_URI, keys, cacheDataSourceFactory);
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
|
||||||
Loading…
Reference in a new issue