From 1a01dcc55af8ebe435c664baeb42100dfb225c83 Mon Sep 17 00:00:00 2001 From: Oliver Woodman Date: Wed, 22 Apr 2015 16:22:48 +0100 Subject: [PATCH] Separate UriDataSource from HttpDataSource. Using a file:// URL for loading an HLS stream (for testing) would fail due to casting the connection to an HttpURLConnection in DefaultHttpDataSource. This change makes UriDataSource an interface for objects that are DataSources with URIs. That allows for reading manifests for HLS using just a UriDataSource rather than an HttpDataSource (URLs in the playlist are relative to the data source's URL so the getUri method is needed). --- .../demo/player/DashRendererBuilder.java | 8 +- .../demo/player/ExtractorRendererBuilder.java | 4 +- .../demo/player/HlsRendererBuilder.java | 4 +- .../SmoothStreamingRendererBuilder.java | 8 +- .../MediaPresentationDescriptionParser.java | 4 +- .../dash/mpd/UtcTimingElementResolver.java | 26 +++--- .../exoplayer/hls/HlsPlaylistParser.java | 4 +- .../SmoothStreamingManifestParser.java | 5 +- .../exoplayer/upstream/DataSource.java | 6 +- .../upstream/DefaultHttpDataSource.java | 2 +- .../upstream/DefaultUriDataSource.java | 87 +++++++++++++++++++ .../exoplayer/upstream/FileDataSource.java | 10 ++- .../exoplayer/upstream/HttpDataSource.java | 11 +-- .../exoplayer/upstream/UriDataSource.java | 64 ++------------ ...{NetworkLoadable.java => UriLoadable.java} | 22 ++--- .../exoplayer/util/ManifestFetcher.java | 34 ++++---- 16 files changed, 167 insertions(+), 132 deletions(-) create mode 100644 library/src/main/java/com/google/android/exoplayer/upstream/DefaultUriDataSource.java rename library/src/main/java/com/google/android/exoplayer/upstream/{NetworkLoadable.java => UriLoadable.java} (79%) diff --git a/demo/src/main/java/com/google/android/exoplayer/demo/player/DashRendererBuilder.java b/demo/src/main/java/com/google/android/exoplayer/demo/player/DashRendererBuilder.java index 13f09f88df..d3d96c146f 100644 --- a/demo/src/main/java/com/google/android/exoplayer/demo/player/DashRendererBuilder.java +++ b/demo/src/main/java/com/google/android/exoplayer/demo/player/DashRendererBuilder.java @@ -52,8 +52,8 @@ import com.google.android.exoplayer.upstream.BufferPool; import com.google.android.exoplayer.upstream.DataSource; import com.google.android.exoplayer.upstream.DefaultBandwidthMeter; import com.google.android.exoplayer.upstream.DefaultHttpDataSource; +import com.google.android.exoplayer.upstream.DefaultUriDataSource; import com.google.android.exoplayer.upstream.HttpDataSource; -import com.google.android.exoplayer.upstream.UriDataSource; import com.google.android.exoplayer.util.ManifestFetcher; import com.google.android.exoplayer.util.ManifestFetcher.ManifestCallback; import com.google.android.exoplayer.util.MimeTypes; @@ -247,7 +247,7 @@ public class DashRendererBuilder implements RendererBuilder, debugRenderer = null; } else { int[] videoRepresentationIndices = Util.toArray(videoRepresentationIndexList); - DataSource videoDataSource = new UriDataSource(userAgent, bandwidthMeter); + DataSource videoDataSource = new DefaultUriDataSource(userAgent, bandwidthMeter); ChunkSource videoChunkSource = new DashChunkSource(manifestFetcher, videoAdaptationSetIndex, videoRepresentationIndices, videoDataSource, new AdaptiveEvaluator(bandwidthMeter), LIVE_EDGE_LATENCY_MS, elapsedRealtimeOffset); @@ -265,7 +265,7 @@ public class DashRendererBuilder implements RendererBuilder, List audioTrackNameList = new ArrayList(); int audioEncoding = AudioFormat.ENCODING_PCM_16BIT; if (audioAdaptationSet != null) { - DataSource audioDataSource = new UriDataSource(userAgent, bandwidthMeter); + DataSource audioDataSource = new DefaultUriDataSource(userAgent, bandwidthMeter); FormatEvaluator audioEvaluator = new FormatEvaluator.FixedEvaluator(); List audioRepresentations = audioAdaptationSet.representations; List codecs = new ArrayList(); @@ -321,7 +321,7 @@ public class DashRendererBuilder implements RendererBuilder, } // Build the text chunk sources. - DataSource textDataSource = new UriDataSource(userAgent, bandwidthMeter); + DataSource textDataSource = new DefaultUriDataSource(userAgent, bandwidthMeter); FormatEvaluator textEvaluator = new FormatEvaluator.FixedEvaluator(); List textChunkSourceList = new ArrayList(); List textTrackNameList = new ArrayList(); diff --git a/demo/src/main/java/com/google/android/exoplayer/demo/player/ExtractorRendererBuilder.java b/demo/src/main/java/com/google/android/exoplayer/demo/player/ExtractorRendererBuilder.java index 94d49488f9..c9cff47697 100644 --- a/demo/src/main/java/com/google/android/exoplayer/demo/player/ExtractorRendererBuilder.java +++ b/demo/src/main/java/com/google/android/exoplayer/demo/player/ExtractorRendererBuilder.java @@ -23,7 +23,7 @@ import com.google.android.exoplayer.demo.player.DemoPlayer.RendererBuilderCallba import com.google.android.exoplayer.extractor.Extractor; import com.google.android.exoplayer.extractor.ExtractorSampleSource; import com.google.android.exoplayer.upstream.DataSource; -import com.google.android.exoplayer.upstream.UriDataSource; +import com.google.android.exoplayer.upstream.DefaultUriDataSource; import android.media.MediaCodec; import android.net.Uri; @@ -52,7 +52,7 @@ public class ExtractorRendererBuilder implements RendererBuilder { @Override public void buildRenderers(DemoPlayer player, RendererBuilderCallback callback) { // Build the video and audio renderers. - DataSource dataSource = new UriDataSource(userAgent, null); + DataSource dataSource = new DefaultUriDataSource(userAgent, null); ExtractorSampleSource sampleSource = new ExtractorSampleSource(uri, dataSource, extractor, 2, BUFFER_SIZE); MediaCodecVideoTrackRenderer videoRenderer = new MediaCodecVideoTrackRenderer(sampleSource, diff --git a/demo/src/main/java/com/google/android/exoplayer/demo/player/HlsRendererBuilder.java b/demo/src/main/java/com/google/android/exoplayer/demo/player/HlsRendererBuilder.java index 2f87c47b37..d87d2aab51 100644 --- a/demo/src/main/java/com/google/android/exoplayer/demo/player/HlsRendererBuilder.java +++ b/demo/src/main/java/com/google/android/exoplayer/demo/player/HlsRendererBuilder.java @@ -30,7 +30,7 @@ import com.google.android.exoplayer.text.eia608.Eia608TrackRenderer; import com.google.android.exoplayer.upstream.DataSource; import com.google.android.exoplayer.upstream.DefaultBandwidthMeter; import com.google.android.exoplayer.upstream.DefaultHttpDataSource; -import com.google.android.exoplayer.upstream.UriDataSource; +import com.google.android.exoplayer.upstream.DefaultUriDataSource; import com.google.android.exoplayer.util.ManifestFetcher; import com.google.android.exoplayer.util.ManifestFetcher.ManifestCallback; @@ -79,7 +79,7 @@ public class HlsRendererBuilder implements RendererBuilder, ManifestCallback { + implements UriLoadable.Parser { private static final Pattern FRAME_RATE_PATTERN = Pattern.compile("(\\d+)(?:/(\\d+))??"); diff --git a/library/src/main/java/com/google/android/exoplayer/dash/mpd/UtcTimingElementResolver.java b/library/src/main/java/com/google/android/exoplayer/dash/mpd/UtcTimingElementResolver.java index eb87b23cee..c530bafe84 100644 --- a/library/src/main/java/com/google/android/exoplayer/dash/mpd/UtcTimingElementResolver.java +++ b/library/src/main/java/com/google/android/exoplayer/dash/mpd/UtcTimingElementResolver.java @@ -16,10 +16,10 @@ package com.google.android.exoplayer.dash.mpd; import com.google.android.exoplayer.ParserException; -import com.google.android.exoplayer.upstream.HttpDataSource; import com.google.android.exoplayer.upstream.Loader; import com.google.android.exoplayer.upstream.Loader.Loadable; -import com.google.android.exoplayer.upstream.NetworkLoadable; +import com.google.android.exoplayer.upstream.UriDataSource; +import com.google.android.exoplayer.upstream.UriLoadable; import com.google.android.exoplayer.util.Assertions; import com.google.android.exoplayer.util.Util; @@ -64,34 +64,34 @@ public class UtcTimingElementResolver implements Loader.Callback { void onTimestampError(UtcTimingElement utcTiming, IOException e); } - private final HttpDataSource httpDataSource; + private final UriDataSource uriDataSource; private final UtcTimingElement timingElement; private final long timingElementElapsedRealtime; private final UtcTimingCallback callback; private Loader singleUseLoader; - private NetworkLoadable singleUseLoadable; + private UriLoadable singleUseLoadable; /** * Resolves a {@link UtcTimingElement}. * - * @param httpDataSource A source to use should network requests be necessary. + * @param uriDataSource A source to use should loading from a URI be necessary. * @param timingElement The element to resolve. * @param timingElementElapsedRealtime The {@link SystemClock#elapsedRealtime()} timestamp at * which the element was obtained. Used if the element contains a timestamp directly. * @param callback The callback to invoke on resolution or failure. */ - public static void resolveTimingElement(HttpDataSource httpDataSource, + public static void resolveTimingElement(UriDataSource uriDataSource, UtcTimingElement timingElement, long timingElementElapsedRealtime, UtcTimingCallback callback) { - UtcTimingElementResolver resolver = new UtcTimingElementResolver(httpDataSource, timingElement, + UtcTimingElementResolver resolver = new UtcTimingElementResolver(uriDataSource, timingElement, timingElementElapsedRealtime, callback); resolver.resolve(); } - private UtcTimingElementResolver(HttpDataSource httpDataSource, UtcTimingElement timingElement, + private UtcTimingElementResolver(UriDataSource uriDataSource, UtcTimingElement timingElement, long timingElementElapsedRealtime, UtcTimingCallback callback) { - this.httpDataSource = httpDataSource; + this.uriDataSource = uriDataSource; this.timingElement = Assertions.checkNotNull(timingElement); this.timingElementElapsedRealtime = timingElementElapsedRealtime; this.callback = Assertions.checkNotNull(callback); @@ -122,9 +122,9 @@ public class UtcTimingElementResolver implements Loader.Callback { } } - private void resolveHttp(NetworkLoadable.Parser parser) { + private void resolveHttp(UriLoadable.Parser parser) { singleUseLoader = new Loader("utctiming"); - singleUseLoadable = new NetworkLoadable(timingElement.value, httpDataSource, parser); + singleUseLoadable = new UriLoadable(timingElement.value, uriDataSource, parser); singleUseLoader.startLoading(singleUseLoadable, this); } @@ -150,7 +150,7 @@ public class UtcTimingElementResolver implements Loader.Callback { singleUseLoader.release(); } - private static class XsDateTimeParser implements NetworkLoadable.Parser { + private static class XsDateTimeParser implements UriLoadable.Parser { @Override public Long parse(String connectionUrl, InputStream inputStream) throws ParserException, @@ -165,7 +165,7 @@ public class UtcTimingElementResolver implements Loader.Callback { } - private static class Iso8601Parser implements NetworkLoadable.Parser { + private static class Iso8601Parser implements UriLoadable.Parser { @Override public Long parse(String connectionUrl, InputStream inputStream) throws ParserException, diff --git a/library/src/main/java/com/google/android/exoplayer/hls/HlsPlaylistParser.java b/library/src/main/java/com/google/android/exoplayer/hls/HlsPlaylistParser.java index d33f686010..187d1e8b95 100644 --- a/library/src/main/java/com/google/android/exoplayer/hls/HlsPlaylistParser.java +++ b/library/src/main/java/com/google/android/exoplayer/hls/HlsPlaylistParser.java @@ -18,7 +18,7 @@ package com.google.android.exoplayer.hls; import com.google.android.exoplayer.C; import com.google.android.exoplayer.ParserException; import com.google.android.exoplayer.hls.HlsMediaPlaylist.Segment; -import com.google.android.exoplayer.upstream.NetworkLoadable; +import com.google.android.exoplayer.upstream.UriLoadable; import java.io.BufferedReader; import java.io.IOException; @@ -34,7 +34,7 @@ import java.util.regex.Pattern; /** * HLS playlists parsing logic. */ -public final class HlsPlaylistParser implements NetworkLoadable.Parser { +public final class HlsPlaylistParser implements UriLoadable.Parser { private static final String VERSION_TAG = "#EXT-X-VERSION"; private static final String STREAM_INF_TAG = "#EXT-X-STREAM-INF"; diff --git a/library/src/main/java/com/google/android/exoplayer/smoothstreaming/SmoothStreamingManifestParser.java b/library/src/main/java/com/google/android/exoplayer/smoothstreaming/SmoothStreamingManifestParser.java index 27dd7752da..78dde28b1a 100644 --- a/library/src/main/java/com/google/android/exoplayer/smoothstreaming/SmoothStreamingManifestParser.java +++ b/library/src/main/java/com/google/android/exoplayer/smoothstreaming/SmoothStreamingManifestParser.java @@ -19,7 +19,7 @@ import com.google.android.exoplayer.ParserException; import com.google.android.exoplayer.smoothstreaming.SmoothStreamingManifest.ProtectionElement; import com.google.android.exoplayer.smoothstreaming.SmoothStreamingManifest.StreamElement; import com.google.android.exoplayer.smoothstreaming.SmoothStreamingManifest.TrackElement; -import com.google.android.exoplayer.upstream.NetworkLoadable; +import com.google.android.exoplayer.upstream.UriLoadable; import com.google.android.exoplayer.util.Assertions; import com.google.android.exoplayer.util.CodecSpecificDataUtil; import com.google.android.exoplayer.util.MimeTypes; @@ -44,8 +44,7 @@ import java.util.UUID; * @see * IIS Smooth Streaming Client Manifest Format */ -public class SmoothStreamingManifestParser implements - NetworkLoadable.Parser { +public class SmoothStreamingManifestParser implements UriLoadable.Parser { private final XmlPullParserFactory xmlParserFactory; diff --git a/library/src/main/java/com/google/android/exoplayer/upstream/DataSource.java b/library/src/main/java/com/google/android/exoplayer/upstream/DataSource.java index 3d711708ee..002fda19ea 100644 --- a/library/src/main/java/com/google/android/exoplayer/upstream/DataSource.java +++ b/library/src/main/java/com/google/android/exoplayer/upstream/DataSource.java @@ -41,7 +41,7 @@ public interface DataSource { * unresolved. For all other requests, the value returned will be equal to the request's * {@link DataSpec#length}. */ - public long open(DataSpec dataSpec) throws IOException; + long open(DataSpec dataSpec) throws IOException; /** * Closes the {@link DataSource}. @@ -51,7 +51,7 @@ public interface DataSource { * * @throws IOException If an error occurs closing the source. */ - public void close() throws IOException; + void close() throws IOException; /** * Reads up to {@code length} bytes of data and stores them into {@code buffer}, starting at @@ -67,6 +67,6 @@ public interface DataSource { * range is reached. * @throws IOException If an error occurs reading from the source. */ - public int read(byte[] buffer, int offset, int readLength) throws IOException; + int read(byte[] buffer, int offset, int readLength) throws IOException; } diff --git a/library/src/main/java/com/google/android/exoplayer/upstream/DefaultHttpDataSource.java b/library/src/main/java/com/google/android/exoplayer/upstream/DefaultHttpDataSource.java index d809b28110..ff7c69240c 100644 --- a/library/src/main/java/com/google/android/exoplayer/upstream/DefaultHttpDataSource.java +++ b/library/src/main/java/com/google/android/exoplayer/upstream/DefaultHttpDataSource.java @@ -112,7 +112,7 @@ public class DefaultHttpDataSource implements HttpDataSource { } @Override - public String getUrl() { + public String getUri() { return connection == null ? null : connection.getURL().toString(); } diff --git a/library/src/main/java/com/google/android/exoplayer/upstream/DefaultUriDataSource.java b/library/src/main/java/com/google/android/exoplayer/upstream/DefaultUriDataSource.java new file mode 100644 index 0000000000..9c20861bf5 --- /dev/null +++ b/library/src/main/java/com/google/android/exoplayer/upstream/DefaultUriDataSource.java @@ -0,0 +1,87 @@ +/* + * Copyright (C) 2014 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.exoplayer.upstream; + +import com.google.android.exoplayer.util.Assertions; + +import java.io.IOException; + +/** + * A data source that fetches data from a local or remote {@link DataSpec}. + */ +public final class DefaultUriDataSource implements UriDataSource { + + private static final String FILE_URI_SCHEME = "file"; + + private final UriDataSource fileDataSource; + private final UriDataSource httpDataSource; + + /** + * {@code null} if no data source is open. Otherwise, equal to {@link #fileDataSource} if the open + * data source is a file, or {@link #httpDataSource} otherwise. + */ + private UriDataSource dataSource; + + /** + * Constructs a new data source that delegates to a {@link FileDataSource} for file URIs and an + * {@link DefaultHttpDataSource} for other URIs. + * + * @param userAgent The User-Agent string that should be used when requesting remote data. + * @param transferListener An optional listener. + */ + public DefaultUriDataSource(String userAgent, TransferListener transferListener) { + this(new FileDataSource(transferListener), + new DefaultHttpDataSource(userAgent, null, transferListener)); + } + + /** + * Constructs a new data source using {@code fileDataSource} for file URIs, and + * {@code httpDataSource} for non-file URIs. + * + * @param fileDataSource {@link UriDataSource} to use for file URIs. + * @param httpDataSource {@link UriDataSource} to use for non-file URIs. + */ + public DefaultUriDataSource(UriDataSource fileDataSource, UriDataSource httpDataSource) { + this.fileDataSource = Assertions.checkNotNull(fileDataSource); + this.httpDataSource = Assertions.checkNotNull(httpDataSource); + } + + @Override + public long open(DataSpec dataSpec) throws IOException { + Assertions.checkState(dataSource == null); + dataSource = FILE_URI_SCHEME.equals(dataSpec.uri.getScheme()) ? fileDataSource : httpDataSource; + return dataSource.open(dataSpec); + } + + @Override + public int read(byte[] buffer, int offset, int readLength) throws IOException { + return dataSource.read(buffer, offset, readLength); + } + + @Override + public String getUri() { + return dataSource == null ? null : dataSource.getUri(); + } + + @Override + public void close() throws IOException { + if (dataSource != null) { + dataSource.close(); + dataSource = null; + } + } + +} diff --git a/library/src/main/java/com/google/android/exoplayer/upstream/FileDataSource.java b/library/src/main/java/com/google/android/exoplayer/upstream/FileDataSource.java index 42431d4739..bd890b38d2 100644 --- a/library/src/main/java/com/google/android/exoplayer/upstream/FileDataSource.java +++ b/library/src/main/java/com/google/android/exoplayer/upstream/FileDataSource.java @@ -24,7 +24,7 @@ import java.io.RandomAccessFile; /** * A local file {@link DataSource}. */ -public final class FileDataSource implements DataSource { +public final class FileDataSource implements UriDataSource { /** * Thrown when IOException is encountered during local file read operation. @@ -40,6 +40,7 @@ public final class FileDataSource implements DataSource { private final TransferListener listener; private RandomAccessFile file; + private String uri; private long bytesRemaining; private boolean opened; @@ -62,6 +63,7 @@ public final class FileDataSource implements DataSource { @Override public long open(DataSpec dataSpec) throws FileDataSourceException { try { + uri = dataSpec.uri.toString(); file = new RandomAccessFile(dataSpec.uri.getPath(), "r"); file.seek(dataSpec.position); bytesRemaining = dataSpec.length == C.LENGTH_UNBOUNDED ? file.length() - dataSpec.position @@ -104,6 +106,11 @@ public final class FileDataSource implements DataSource { } } + @Override + public String getUri() { + return uri; + } + @Override public void close() throws FileDataSourceException { if (file != null) { @@ -113,6 +120,7 @@ public final class FileDataSource implements DataSource { throw new FileDataSourceException(e); } finally { file = null; + uri = null; if (opened) { opened = false; diff --git a/library/src/main/java/com/google/android/exoplayer/upstream/HttpDataSource.java b/library/src/main/java/com/google/android/exoplayer/upstream/HttpDataSource.java index 880a3f2cc2..2944616a09 100644 --- a/library/src/main/java/com/google/android/exoplayer/upstream/HttpDataSource.java +++ b/library/src/main/java/com/google/android/exoplayer/upstream/HttpDataSource.java @@ -27,7 +27,7 @@ import java.util.Map; /** * An HTTP specific extension to {@link DataSource}. */ -public interface HttpDataSource extends DataSource { +public interface HttpDataSource extends UriDataSource { /** * A {@link Predicate} that rejects content types often used for pay-walls. @@ -123,15 +123,6 @@ public interface HttpDataSource extends DataSource { @Override int read(byte[] buffer, int offset, int readLength) throws HttpDataSourceException; - /** - * When the source is open, returns the url from which data is being read. - *

- * If redirection occurred, the url after redirection is the one returned. - * - * @return When the source is open, the url from which data is being read. Null otherwise. - */ - String getUrl(); - /** * Sets the value of a request header field. The value will be used for subsequent connections * established by the source. diff --git a/library/src/main/java/com/google/android/exoplayer/upstream/UriDataSource.java b/library/src/main/java/com/google/android/exoplayer/upstream/UriDataSource.java index 42500bf45c..61da0520ba 100644 --- a/library/src/main/java/com/google/android/exoplayer/upstream/UriDataSource.java +++ b/library/src/main/java/com/google/android/exoplayer/upstream/UriDataSource.java @@ -15,68 +15,18 @@ */ package com.google.android.exoplayer.upstream; -import com.google.android.exoplayer.util.Assertions; - -import java.io.IOException; - /** - * A data source that fetches data from a local or remote {@link DataSpec}. + * A component that provides media data from a URI. */ -public final class UriDataSource implements DataSource { - - private static final String FILE_URI_SCHEME = "file"; - - private final DataSource fileDataSource; - private final DataSource httpDataSource; +public interface UriDataSource extends DataSource { /** - * {@code null} if no data source is open. Otherwise, equal to {@link #fileDataSource} if the open - * data source is a file, or {@link #httpDataSource} otherwise. - */ - private DataSource dataSource; - - /** - * Constructs a new data source that delegates to a {@link FileDataSource} for file URIs and an - * {@link DefaultHttpDataSource} for other URIs. + * When the source is open, returns the URI from which data is being read. + *

+ * If redirection occurred, the URI after redirection is the one returned. * - * @param userAgent The User-Agent string that should be used when requesting remote data. - * @param transferListener An optional listener. + * @return When the source is open, the URI from which data is being read. Null otherwise. */ - public UriDataSource(String userAgent, TransferListener transferListener) { - this(new FileDataSource(transferListener), - new DefaultHttpDataSource(userAgent, null, transferListener)); - } - - /** - * Constructs a new data source using {@code fileDataSource} for file URIs, and - * {@code httpDataSource} for non-file URIs. - * - * @param fileDataSource {@link DataSource} to use for file URIs. - * @param httpDataSource {@link DataSource} to use for non-file URIs. - */ - public UriDataSource(DataSource fileDataSource, DataSource httpDataSource) { - this.fileDataSource = Assertions.checkNotNull(fileDataSource); - this.httpDataSource = Assertions.checkNotNull(httpDataSource); - } - - @Override - public long open(DataSpec dataSpec) throws IOException { - Assertions.checkState(dataSource == null); - dataSource = FILE_URI_SCHEME.equals(dataSpec.uri.getScheme()) ? fileDataSource : httpDataSource; - return dataSource.open(dataSpec); - } - - @Override - public int read(byte[] buffer, int offset, int readLength) throws IOException { - return dataSource.read(buffer, offset, readLength); - } - - @Override - public void close() throws IOException { - if (dataSource != null) { - dataSource.close(); - dataSource = null; - } - } + String getUri(); } diff --git a/library/src/main/java/com/google/android/exoplayer/upstream/NetworkLoadable.java b/library/src/main/java/com/google/android/exoplayer/upstream/UriLoadable.java similarity index 79% rename from library/src/main/java/com/google/android/exoplayer/upstream/NetworkLoadable.java rename to library/src/main/java/com/google/android/exoplayer/upstream/UriLoadable.java index d4f4e6abf7..cce6f9347e 100644 --- a/library/src/main/java/com/google/android/exoplayer/upstream/NetworkLoadable.java +++ b/library/src/main/java/com/google/android/exoplayer/upstream/UriLoadable.java @@ -24,19 +24,19 @@ import java.io.IOException; import java.io.InputStream; /** - * A {@link Loadable} for loading an object over the network. + * A {@link Loadable} for loading an object from a URI. * * @param The type of the object being loaded. */ -public final class NetworkLoadable implements Loadable { +public final class UriLoadable implements Loadable { /** - * Parses an object from data loaded over the network. + * Parses an object from loaded data. */ public interface Parser { /** - * Parses an object from a network response. + * Parses an object from a response. * * @param connectionUrl The source of the response, after any redirection. * @param inputStream An {@link InputStream} from which the response data can be read. @@ -49,7 +49,7 @@ public final class NetworkLoadable implements Loadable { } private final DataSpec dataSpec; - private final HttpDataSource httpDataSource; + private final UriDataSource uriDataSource; private final Parser parser; private volatile T result; @@ -57,11 +57,11 @@ public final class NetworkLoadable implements Loadable { /** * @param url The url from which the object should be loaded. - * @param httpDataSource A {@link HttpDataSource} to use when loading the data. - * @param parser Parses the object from the network response. + * @param uriDataSource A {@link UriDataSource} to use when loading the data. + * @param parser Parses the object from the response. */ - public NetworkLoadable(String url, HttpDataSource httpDataSource, Parser parser) { - this.httpDataSource = httpDataSource; + public UriLoadable(String url, UriDataSource uriDataSource, Parser parser) { + this.uriDataSource = uriDataSource; this.parser = parser; dataSpec = new DataSpec(Uri.parse(url), DataSpec.FLAG_ALLOW_GZIP); } @@ -87,10 +87,10 @@ public final class NetworkLoadable implements Loadable { @Override public final void load() throws IOException, InterruptedException { - DataSourceInputStream inputStream = new DataSourceInputStream(httpDataSource, dataSpec); + DataSourceInputStream inputStream = new DataSourceInputStream(uriDataSource, dataSpec); try { inputStream.open(); - result = parser.parse(httpDataSource.getUrl(), inputStream); + result = parser.parse(uriDataSource.getUri(), inputStream); } finally { inputStream.close(); } diff --git a/library/src/main/java/com/google/android/exoplayer/util/ManifestFetcher.java b/library/src/main/java/com/google/android/exoplayer/util/ManifestFetcher.java index de856b3d2a..a626ec20c3 100644 --- a/library/src/main/java/com/google/android/exoplayer/util/ManifestFetcher.java +++ b/library/src/main/java/com/google/android/exoplayer/util/ManifestFetcher.java @@ -15,10 +15,10 @@ */ package com.google.android.exoplayer.util; -import com.google.android.exoplayer.upstream.HttpDataSource; import com.google.android.exoplayer.upstream.Loader; import com.google.android.exoplayer.upstream.Loader.Loadable; -import com.google.android.exoplayer.upstream.NetworkLoadable; +import com.google.android.exoplayer.upstream.UriDataSource; +import com.google.android.exoplayer.upstream.UriLoadable; import android.os.Handler; import android.os.Looper; @@ -83,8 +83,8 @@ public class ManifestFetcher implements Loader.Callback { } - private final NetworkLoadable.Parser parser; - private final HttpDataSource httpDataSource; + private final UriLoadable.Parser parser; + private final UriDataSource uriDataSource; private final Handler eventHandler; private final EventListener eventListener; @@ -92,7 +92,7 @@ public class ManifestFetcher implements Loader.Callback { private int enabledCount; private Loader loader; - private NetworkLoadable currentLoadable; + private UriLoadable currentLoadable; private int loadExceptionCount; private long loadExceptionTimestamp; @@ -103,27 +103,27 @@ public class ManifestFetcher implements Loader.Callback { /** * @param manifestUrl The manifest location. - * @param httpDataSource The {@link HttpDataSource} to use when loading the manifest. + * @param uriDataSource The {@link UriDataSource} to use when loading the manifest. * @param parser A parser to parse the loaded manifest data. */ - public ManifestFetcher(String manifestUrl, HttpDataSource httpDataSource, - NetworkLoadable.Parser parser) { - this(manifestUrl, httpDataSource, parser, null, null); + public ManifestFetcher(String manifestUrl, UriDataSource uriDataSource, + UriLoadable.Parser parser) { + this(manifestUrl, uriDataSource, parser, null, null); } /** * @param manifestUrl The manifest location. - * @param httpDataSource The {@link HttpDataSource} to use when loading the manifest. + * @param uriDataSource The {@link UriDataSource} to use when loading the manifest. * @param parser A parser to parse the loaded manifest data. * @param eventHandler A handler to use when delivering events to {@code eventListener}. May be * null if delivery of events is not required. * @param eventListener A listener of events. May be null if delivery of events is not required. */ - public ManifestFetcher(String manifestUrl, HttpDataSource httpDataSource, - NetworkLoadable.Parser parser, Handler eventHandler, EventListener eventListener) { + public ManifestFetcher(String manifestUrl, UriDataSource uriDataSource, + UriLoadable.Parser parser, Handler eventHandler, EventListener eventListener) { this.parser = parser; this.manifestUrl = manifestUrl; - this.httpDataSource = httpDataSource; + this.uriDataSource = uriDataSource; this.eventHandler = eventHandler; this.eventListener = eventListener; } @@ -146,7 +146,7 @@ public class ManifestFetcher implements Loader.Callback { */ public void singleLoad(Looper callbackLooper, final ManifestCallback callback) { SingleFetchHelper fetchHelper = new SingleFetchHelper( - new NetworkLoadable(manifestUrl, httpDataSource, parser), callbackLooper, callback); + new UriLoadable(manifestUrl, uriDataSource, parser), callbackLooper, callback); fetchHelper.startLoading(); } @@ -219,7 +219,7 @@ public class ManifestFetcher implements Loader.Callback { loader = new Loader("manifestLoader"); } if (!loader.isLoading()) { - currentLoadable = new NetworkLoadable(manifestUrl, httpDataSource, parser); + currentLoadable = new UriLoadable(manifestUrl, uriDataSource, parser); loader.startLoading(currentLoadable, this); notifyManifestRefreshStarted(); } @@ -303,12 +303,12 @@ public class ManifestFetcher implements Loader.Callback { private class SingleFetchHelper implements Loader.Callback { - private final NetworkLoadable singleUseLoadable; + private final UriLoadable singleUseLoadable; private final Looper callbackLooper; private final ManifestCallback wrappedCallback; private final Loader singleUseLoader; - public SingleFetchHelper(NetworkLoadable singleUseLoadable, Looper callbackLooper, + public SingleFetchHelper(UriLoadable singleUseLoadable, Looper callbackLooper, ManifestCallback wrappedCallback) { this.singleUseLoadable = singleUseLoadable; this.callbackLooper = callbackLooper;