Improve DataSource implementations:

1. Make DefaultUriDataSource robust against exceptions through from close().
2. Make AssetDataSource handle file:///android_asset/ URIs.
This commit is contained in:
Oliver Woodman 2015-05-19 14:05:50 +01:00
parent 672906060c
commit 059b80c1ab
4 changed files with 26 additions and 10 deletions

View File

@ -16,6 +16,7 @@
package com.google.android.exoplayer.upstream;
import com.google.android.exoplayer.C;
import com.google.android.exoplayer.util.Assertions;
import android.content.res.AssetManager;
@ -24,9 +25,9 @@ import java.io.IOException;
import java.io.InputStream;
/**
* A local asset {@link DataSource}.
* A local asset {@link UriDataSource}.
*/
public final class AssetDataSource implements DataSource {
public final class AssetDataSource implements UriDataSource {
/**
* Thrown when IOException is encountered during local asset read operation.
@ -42,6 +43,7 @@ public final class AssetDataSource implements DataSource {
private final AssetManager assetManager;
private final TransferListener listener;
private String uriString;
private InputStream assetInputStream;
private long bytesRemaining;
private boolean opened;
@ -66,10 +68,16 @@ public final class AssetDataSource implements DataSource {
@Override
public long open(DataSpec dataSpec) throws AssetDataSourceException {
try {
// Lose the '/' prefix in the path or else AssetManager won't find our file
assetInputStream = assetManager.open(dataSpec.uri.getPath().substring(1),
AssetManager.ACCESS_RANDOM);
assetInputStream.skip(dataSpec.position);
uriString = dataSpec.uri.toString();
String path = dataSpec.uri.getPath();
if (path.startsWith("/android_asset/")) {
path = path.substring(15);
} else if (path.startsWith("/")) {
path = path.substring(1);
}
assetInputStream = assetManager.open(path, AssetManager.ACCESS_RANDOM);
long skipped = assetInputStream.skip(dataSpec.position);
Assertions.checkState(skipped == dataSpec.position);
bytesRemaining = dataSpec.length == C.LENGTH_UNBOUNDED ? assetInputStream.available()
: dataSpec.length;
if (bytesRemaining < 0) {
@ -110,6 +118,11 @@ public final class AssetDataSource implements DataSource {
}
}
@Override
public String getUri() {
return uriString;
}
@Override
public void close() throws AssetDataSourceException {
if (assetInputStream != null) {

View File

@ -100,8 +100,11 @@ public final class DefaultUriDataSource implements UriDataSource {
@Override
public void close() throws IOException {
if (dataSource != null) {
dataSource.close();
dataSource = null;
try {
dataSource.close();
} finally {
dataSource = null;
}
}
}

View File

@ -22,7 +22,7 @@ import java.io.IOException;
import java.io.RandomAccessFile;
/**
* A local file {@link DataSource}.
* A local file {@link UriDataSource}.
*/
public final class FileDataSource implements UriDataSource {

View File

@ -25,7 +25,7 @@ import java.util.List;
import java.util.Map;
/**
* An HTTP specific extension to {@link DataSource}.
* An HTTP specific extension to {@link UriDataSource}.
*/
public interface HttpDataSource extends UriDataSource {