Commit fab80874 by olly Committed by Ian Baker

Sanitize CacheDataSource/CacheDataSink factories

PiperOrigin-RevId: 307636959
parent 96ccb893
...@@ -73,6 +73,8 @@ ...@@ -73,6 +73,8 @@
* Fix `AdsMediaSource` child `MediaSource`s not being released. * Fix `AdsMediaSource` child `MediaSource`s not being released.
* Parse track titles from Matroska files * Parse track titles from Matroska files
([#7247](https://github.com/google/ExoPlayer/pull/7247)). ([#7247](https://github.com/google/ExoPlayer/pull/7247)).
* Replace `CacheDataSinkFactory` and `CacheDataSourceFactory` with
`CacheDataSink.Factory` and `CacheDataSource.Factory` respectively.
* Text: * Text:
* Parse `<ruby>` and `<rt>` tags in WebVTT subtitles (rendering is coming * Parse `<ruby>` and `<rt>` tags in WebVTT subtitles (rendering is coming
later). later).
......
...@@ -19,14 +19,11 @@ import androidx.annotation.Nullable; ...@@ -19,14 +19,11 @@ import androidx.annotation.Nullable;
import com.google.android.exoplayer2.C; import com.google.android.exoplayer2.C;
import com.google.android.exoplayer2.upstream.DataSink; import com.google.android.exoplayer2.upstream.DataSink;
import com.google.android.exoplayer2.upstream.DataSource; import com.google.android.exoplayer2.upstream.DataSource;
import com.google.android.exoplayer2.upstream.DummyDataSource;
import com.google.android.exoplayer2.upstream.FileDataSource; import com.google.android.exoplayer2.upstream.FileDataSource;
import com.google.android.exoplayer2.upstream.PriorityDataSourceFactory; import com.google.android.exoplayer2.upstream.PriorityDataSourceFactory;
import com.google.android.exoplayer2.upstream.cache.Cache; import com.google.android.exoplayer2.upstream.cache.Cache;
import com.google.android.exoplayer2.upstream.cache.CacheDataSink;
import com.google.android.exoplayer2.upstream.cache.CacheDataSinkFactory; import com.google.android.exoplayer2.upstream.cache.CacheDataSinkFactory;
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.CacheKeyFactory; import com.google.android.exoplayer2.upstream.cache.CacheKeyFactory;
import com.google.android.exoplayer2.util.PriorityTaskManager; import com.google.android.exoplayer2.util.PriorityTaskManager;
...@@ -34,8 +31,8 @@ import com.google.android.exoplayer2.util.PriorityTaskManager; ...@@ -34,8 +31,8 @@ import com.google.android.exoplayer2.util.PriorityTaskManager;
public final class DownloaderConstructorHelper { public final class DownloaderConstructorHelper {
@Nullable private final PriorityTaskManager priorityTaskManager; @Nullable private final PriorityTaskManager priorityTaskManager;
private final CacheDataSourceFactory onlineCacheDataSourceFactory; private final CacheDataSource.Factory onlineCacheDataSourceFactory;
private final CacheDataSourceFactory offlineCacheDataSourceFactory; private final CacheDataSource.Factory offlineCacheDataSourceFactory;
/** /**
* @param cache Cache instance to be used to store downloaded data. * @param cache Cache instance to be used to store downloaded data.
...@@ -100,37 +97,32 @@ public final class DownloaderConstructorHelper { ...@@ -100,37 +97,32 @@ public final class DownloaderConstructorHelper {
@Nullable DataSink.Factory cacheWriteDataSinkFactory, @Nullable DataSink.Factory cacheWriteDataSinkFactory,
@Nullable PriorityTaskManager priorityTaskManager, @Nullable PriorityTaskManager priorityTaskManager,
@Nullable CacheKeyFactory cacheKeyFactory) { @Nullable CacheKeyFactory cacheKeyFactory) {
this.priorityTaskManager = priorityTaskManager;
if (priorityTaskManager != null) { if (priorityTaskManager != null) {
upstreamFactory = upstreamFactory =
new PriorityDataSourceFactory(upstreamFactory, priorityTaskManager, C.PRIORITY_DOWNLOAD); new PriorityDataSourceFactory(upstreamFactory, priorityTaskManager, C.PRIORITY_DOWNLOAD);
} }
DataSource.Factory readDataSourceFactory =
cacheReadDataSourceFactory != null
? cacheReadDataSourceFactory
: new FileDataSource.Factory();
if (cacheWriteDataSinkFactory == null) {
cacheWriteDataSinkFactory =
new CacheDataSinkFactory(cache, CacheDataSink.DEFAULT_FRAGMENT_SIZE);
}
onlineCacheDataSourceFactory = onlineCacheDataSourceFactory =
new CacheDataSourceFactory( new CacheDataSource.Factory()
cache, .setCache(cache)
upstreamFactory, .setUpstreamDataSourceFactory(upstreamFactory)
readDataSourceFactory, .setFlags(CacheDataSource.FLAG_BLOCK_ON_CACHE);
cacheWriteDataSinkFactory,
CacheDataSource.FLAG_BLOCK_ON_CACHE,
/* eventListener= */ null,
cacheKeyFactory);
offlineCacheDataSourceFactory = offlineCacheDataSourceFactory =
new CacheDataSourceFactory( new CacheDataSource.Factory()
cache, .setCache(cache)
DummyDataSource.FACTORY, .setCacheWriteDataSinkFactory(null)
readDataSourceFactory, .setFlags(CacheDataSource.FLAG_BLOCK_ON_CACHE);
null, if (cacheKeyFactory != null) {
CacheDataSource.FLAG_BLOCK_ON_CACHE, onlineCacheDataSourceFactory.setCacheKeyFactory(cacheKeyFactory);
/* eventListener= */ null, offlineCacheDataSourceFactory.setCacheKeyFactory(cacheKeyFactory);
cacheKeyFactory); }
this.priorityTaskManager = priorityTaskManager; if (cacheReadDataSourceFactory != null) {
onlineCacheDataSourceFactory.setCacheReadDataSourceFactory(cacheReadDataSourceFactory);
offlineCacheDataSourceFactory.setCacheReadDataSourceFactory(cacheReadDataSourceFactory);
}
if (cacheWriteDataSinkFactory != null) {
onlineCacheDataSourceFactory.setCacheWriteDataSinkFactory(cacheWriteDataSinkFactory);
}
} }
/** Returns a {@link PriorityTaskManager} instance. */ /** Returns a {@link PriorityTaskManager} instance. */
......
...@@ -39,6 +39,78 @@ import org.checkerframework.checker.nullness.qual.MonotonicNonNull; ...@@ -39,6 +39,78 @@ import org.checkerframework.checker.nullness.qual.MonotonicNonNull;
*/ */
public final class CacheDataSink implements DataSink { public final class CacheDataSink implements DataSink {
/** {@link DataSink.Factory} for {@link CacheDataSink} instances. */
public static final class Factory implements DataSink.Factory {
private @MonotonicNonNull Cache cache;
private long fragmentSize;
private int bufferSize;
/** Creates an instance. */
public Factory() {
fragmentSize = CacheDataSink.DEFAULT_FRAGMENT_SIZE;
bufferSize = CacheDataSink.DEFAULT_BUFFER_SIZE;
}
/**
* Sets the cache to which data will be written.
*
* <p>Must be called before the factory is used.
*
* @param cache The cache to which data will be written.
* @return This factory.
*/
public Factory setCache(Cache cache) {
this.cache = cache;
return this;
}
/**
* Sets the cache file fragment size. For requests that should be fragmented into multiple cache
* files, this is the maximum size of a cache file in bytes. If set to {@link C#LENGTH_UNSET}
* then no fragmentation will occur. Using a small value allows for finer-grained cache eviction
* policies, at the cost of increased overhead both on the cache implementation and the file
* system. Values under {@code (2 * 1024 * 1024)} are not recommended.
*
* <p>The default value is {@link CacheDataSink#DEFAULT_FRAGMENT_SIZE}.
*
* @param fragmentSize The fragment size in bytes, or {@link C#LENGTH_UNSET} to disable
* fragmentation.
* @return This factory.
*/
public Factory setFragmentSize(long fragmentSize) {
this.fragmentSize = fragmentSize;
return this;
}
/**
* Sets the size of an in-memory buffer used when writing to a cache file. A zero or negative
* value disables buffering.
*
* <p>The default value is {@link CacheDataSink#DEFAULT_BUFFER_SIZE}.
*
* @param bufferSize The buffer size in bytes.
* @return This factory.
*/
public Factory setBufferSize(int bufferSize) {
this.bufferSize = bufferSize;
return this;
}
@Override
public DataSink createDataSink() {
return new CacheDataSink(Assertions.checkNotNull(cache), fragmentSize, bufferSize);
}
}
/** Thrown when an {@link IOException} is encountered when writing data to the sink. */
public static final class CacheDataSinkException extends CacheException {
public CacheDataSinkException(IOException cause) {
super(cause);
}
}
/** Default {@code fragmentSize} recommended for caching use cases. */ /** Default {@code fragmentSize} recommended for caching use cases. */
public static final long DEFAULT_FRAGMENT_SIZE = 5 * 1024 * 1024; public static final long DEFAULT_FRAGMENT_SIZE = 5 * 1024 * 1024;
/** Default buffer size in bytes. */ /** Default buffer size in bytes. */
...@@ -60,17 +132,6 @@ public final class CacheDataSink implements DataSink { ...@@ -60,17 +132,6 @@ public final class CacheDataSink implements DataSink {
private @MonotonicNonNull ReusableBufferedOutputStream bufferedOutputStream; private @MonotonicNonNull ReusableBufferedOutputStream bufferedOutputStream;
/** /**
* Thrown when IOException is encountered when writing data into sink.
*/
public static class CacheDataSinkException extends CacheException {
public CacheDataSinkException(IOException cause) {
super(cause);
}
}
/**
* Constructs an instance using {@link #DEFAULT_BUFFER_SIZE}. * Constructs an instance using {@link #DEFAULT_BUFFER_SIZE}.
* *
* @param cache The cache into which data should be written. * @param cache The cache into which data should be written.
......
...@@ -17,9 +17,8 @@ package com.google.android.exoplayer2.upstream.cache; ...@@ -17,9 +17,8 @@ package com.google.android.exoplayer2.upstream.cache;
import com.google.android.exoplayer2.upstream.DataSink; import com.google.android.exoplayer2.upstream.DataSink;
/** /** @deprecated Use {@link CacheDataSink.Factory}. */
* A {@link DataSink.Factory} that produces {@link CacheDataSink}. @Deprecated
*/
public final class CacheDataSinkFactory implements DataSink.Factory { public final class CacheDataSinkFactory implements DataSink.Factory {
private final Cache cache; private final Cache cache;
......
...@@ -20,7 +20,8 @@ import com.google.android.exoplayer2.upstream.DataSink; ...@@ -20,7 +20,8 @@ import com.google.android.exoplayer2.upstream.DataSink;
import com.google.android.exoplayer2.upstream.DataSource; import com.google.android.exoplayer2.upstream.DataSource;
import com.google.android.exoplayer2.upstream.FileDataSource; import com.google.android.exoplayer2.upstream.FileDataSource;
/** A {@link DataSource.Factory} that produces {@link CacheDataSource}. */ /** @deprecated Use {@link CacheDataSource.Factory}. */
@Deprecated
public final class CacheDataSourceFactory implements DataSource.Factory { public final class CacheDataSourceFactory implements DataSource.Factory {
private final Cache cache; private final Cache cache;
...@@ -44,6 +45,7 @@ public final class CacheDataSourceFactory implements DataSource.Factory { ...@@ -44,6 +45,7 @@ public final class CacheDataSourceFactory implements DataSource.Factory {
} }
/** @see CacheDataSource#CacheDataSource(Cache, DataSource, int) */ /** @see CacheDataSource#CacheDataSource(Cache, DataSource, int) */
@SuppressWarnings("deprecation")
public CacheDataSourceFactory( public CacheDataSourceFactory(
Cache cache, DataSource.Factory upstreamFactory, @CacheDataSource.Flags int flags) { Cache cache, DataSource.Factory upstreamFactory, @CacheDataSource.Flags int flags) {
this( this(
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or sign in to comment