Commit d3ba207a by eguven Committed by Oliver Woodman

Refactor CacheDataSource

Simplified and clarified the code.

-------------
Created by MOE: https://github.com/google/moe
MOE_MIGRATED_REVID=180649983
parent bf3d6028
...@@ -97,7 +97,7 @@ public final class CacheDataSource implements DataSource { ...@@ -97,7 +97,7 @@ public final class CacheDataSource implements DataSource {
private final boolean ignoreCacheForUnsetLengthRequests; private final boolean ignoreCacheForUnsetLengthRequests;
private DataSource currentDataSource; private DataSource currentDataSource;
private boolean currentRequestUnbounded; private boolean readingUnknownLengthDataFromUpstream;
private Uri uri; private Uri uri;
private int flags; private int flags;
private String key; private String key;
...@@ -202,7 +202,7 @@ public final class CacheDataSource implements DataSource { ...@@ -202,7 +202,7 @@ public final class CacheDataSource implements DataSource {
} }
} }
} }
openNextSource(true); openNextSource();
return bytesRemaining; return bytesRemaining;
} catch (IOException e) { } catch (IOException e) {
handleBeforeThrow(e); handleBeforeThrow(e);
...@@ -229,15 +229,21 @@ public final class CacheDataSource implements DataSource { ...@@ -229,15 +229,21 @@ public final class CacheDataSource implements DataSource {
bytesRemaining -= bytesRead; bytesRemaining -= bytesRead;
} }
} else { } else {
if (currentRequestUnbounded) { if (readingUnknownLengthDataFromUpstream) {
// We only do unbounded requests to upstream and only when we don't know the actual stream setCurrentDataSourceBytesRemaining(0);
// length. So we reached the end of stream.
setContentLength(readPosition);
bytesRemaining = 0;
} }
closeCurrentSource(); closeCurrentSource();
if (bytesRemaining > 0 || bytesRemaining == C.LENGTH_UNSET) { if (bytesRemaining > 0 || bytesRemaining == C.LENGTH_UNSET) {
if (openNextSource(false)) { try {
openNextSource();
} catch (IOException e) {
if (readingUnknownLengthDataFromUpstream && isCausedByPositionOutOfRange(e)) {
setCurrentDataSourceBytesRemaining(0);
} else {
throw e;
}
}
if (bytesRemaining != 0) {
return read(buffer, offset, readLength); return read(buffer, offset, readLength);
} }
} }
...@@ -270,9 +276,8 @@ public final class CacheDataSource implements DataSource { ...@@ -270,9 +276,8 @@ public final class CacheDataSource implements DataSource {
* Opens the next source. If the cache contains data spanning the current read position then * Opens the next source. If the cache contains data spanning the current read position then
* {@link #cacheReadDataSource} is opened to read from it. Else {@link #upstreamDataSource} is * {@link #cacheReadDataSource} is opened to read from it. Else {@link #upstreamDataSource} is
* opened to read from the upstream source and write into the cache. * opened to read from the upstream source and write into the cache.
* @param initial Whether it is the initial open call.
*/ */
private boolean openNextSource(boolean initial) throws IOException { private void openNextSource() throws IOException {
DataSpec dataSpec; DataSpec dataSpec;
CacheSpan span; CacheSpan span;
if (currentRequestIgnoresCache) { if (currentRequestIgnoresCache) {
...@@ -323,48 +328,38 @@ public final class CacheDataSource implements DataSource { ...@@ -323,48 +328,38 @@ public final class CacheDataSource implements DataSource {
} }
} }
currentRequestUnbounded = dataSpec.length == C.LENGTH_UNSET; // If the request is unbounded it must be an upstream request.
boolean successful = false; readingUnknownLengthDataFromUpstream = dataSpec.length == C.LENGTH_UNSET;
long currentBytesRemaining = 0;
try { long resolvedLength = currentDataSource.open(dataSpec);
currentBytesRemaining = currentDataSource.open(dataSpec); if (readingUnknownLengthDataFromUpstream && resolvedLength != C.LENGTH_UNSET) {
successful = true; setCurrentDataSourceBytesRemaining(resolvedLength);
} catch (IOException e) { }
// if this isn't the initial open call (we had read some bytes) and an unbounded range request }
// failed because of POSITION_OUT_OF_RANGE then mute the exception. We are trying to find the
// end of the stream. private static boolean isCausedByPositionOutOfRange(IOException e) {
if (!initial && currentRequestUnbounded) {
Throwable cause = e; Throwable cause = e;
while (cause != null) { while (cause != null) {
if (cause instanceof DataSourceException) { if (cause instanceof DataSourceException) {
int reason = ((DataSourceException) cause).reason; int reason = ((DataSourceException) cause).reason;
if (reason == DataSourceException.POSITION_OUT_OF_RANGE) { if (reason == DataSourceException.POSITION_OUT_OF_RANGE) {
e = null; return true;
break;
} }
} }
cause = cause.getCause(); cause = cause.getCause();
} }
} return false;
if (e != null) {
throw e;
}
} }
// If we did an unbounded request (which means it's to upstream and private void setCurrentDataSourceBytesRemaining(long bytesRemaining) throws IOException {
// bytesRemaining == C.LENGTH_UNSET) and got a resolved length from open() request this.bytesRemaining = bytesRemaining;
if (currentRequestUnbounded && currentBytesRemaining != C.LENGTH_UNSET) { if (isWritingToCache()) {
bytesRemaining = currentBytesRemaining; cache.setContentLength(key, readPosition + bytesRemaining);
setContentLength(dataSpec.position + bytesRemaining);
} }
return successful;
} }
private void setContentLength(long length) throws IOException { private boolean isWritingToCache() {
// If writing into cache return currentDataSource == cacheWriteDataSource;
if (currentDataSource == cacheWriteDataSource) {
cache.setContentLength(key, length);
}
} }
private void closeCurrentSource() throws IOException { private void closeCurrentSource() throws IOException {
...@@ -374,7 +369,7 @@ public final class CacheDataSource implements DataSource { ...@@ -374,7 +369,7 @@ public final class CacheDataSource implements DataSource {
try { try {
currentDataSource.close(); currentDataSource.close();
currentDataSource = null; currentDataSource = null;
currentRequestUnbounded = false; readingUnknownLengthDataFromUpstream = false;
} finally { } finally {
if (lockedSpan != null) { if (lockedSpan != null) {
cache.releaseHoleSpan(lockedSpan); cache.releaseHoleSpan(lockedSpan);
......
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