From a7c897003c35e8db816c470131f548081fc9b02e Mon Sep 17 00:00:00 2001 From: tonihei Date: Wed, 23 Apr 2025 04:11:32 -0700 Subject: [PATCH] Fix bug where a MaskingMediaSource never throws prepare error We suppressed the direct error throwing ability in to avoid throwing errors later in the playlist too early. This logic got moved to MaskingMediaSource in , but its original purpose was no longer needed when the player stopped calling this method directly in . This left a pending bug that any other usage of MaskingMediaSource (e.g. within AdsMediaSource) no longer forwards source prepare errors. Issue: androidx/media#2337 PiperOrigin-RevId: 750537823 --- RELEASENOTES.md | 2 ++ .../exoplayer/source/MaskingMediaSource.java | 7 ------- .../media3/exoplayer/ExoPlayerTest.java | 21 +++++++++++++++++++ 3 files changed, 23 insertions(+), 7 deletions(-) diff --git a/RELEASENOTES.md b/RELEASENOTES.md index 79f505b6de..4970515cd9 100644 --- a/RELEASENOTES.md +++ b/RELEASENOTES.md @@ -9,6 +9,8 @@ scrubber bar around). The behavior of scrubbing mode can be customized with `setScrubbingModeParameters(..)` on `ExoPlayer` and `ExoPlayer.Builder`. + * Fix bug where prepare errors in the content of `AdsMediaSource` may be + never reported ([#2337](https://github.com/androidx/media/issues/2337)). * Transformer: * Filling an initial gap (added via `addGap()`) with silent audio now requires explicitly setting `experimentalSetForceAudioTrack(true)` in diff --git a/libraries/exoplayer/src/main/java/androidx/media3/exoplayer/source/MaskingMediaSource.java b/libraries/exoplayer/src/main/java/androidx/media3/exoplayer/source/MaskingMediaSource.java index bbbb163f3a..b14c182932 100644 --- a/libraries/exoplayer/src/main/java/androidx/media3/exoplayer/source/MaskingMediaSource.java +++ b/libraries/exoplayer/src/main/java/androidx/media3/exoplayer/source/MaskingMediaSource.java @@ -102,13 +102,6 @@ public final class MaskingMediaSource extends WrappingMediaSource { } } - @Override - @SuppressWarnings("MissingSuperCall") - public void maybeThrowSourceInfoRefreshError() { - // Do nothing. Source info refresh errors will be thrown when calling - // MaskingMediaPeriod.maybeThrowPrepareError. - } - @Override public MaskingMediaPeriod createPeriod( MediaPeriodId id, Allocator allocator, long startPositionUs) { diff --git a/libraries/exoplayer/src/test/java/androidx/media3/exoplayer/ExoPlayerTest.java b/libraries/exoplayer/src/test/java/androidx/media3/exoplayer/ExoPlayerTest.java index bfed31a2db..2c14b175a1 100644 --- a/libraries/exoplayer/src/test/java/androidx/media3/exoplayer/ExoPlayerTest.java +++ b/libraries/exoplayer/src/test/java/androidx/media3/exoplayer/ExoPlayerTest.java @@ -16818,6 +16818,27 @@ public final class ExoPlayerTest { assertThat(shouldRendererThrowRecoverableError.get()).isFalse(); } + @Test + public void prepareMaskingMediaSource_withRealSourcePrepareError_reportsPlaybackException() + throws Exception { + ExoPlayer player = new TestExoPlayerBuilder(context).build(); + FakeMediaSource realSourceWithPrepareFailure = + new FakeMediaSource() { + @Override + public void maybeThrowSourceInfoRefreshError() throws IOException { + throw new IOException(); + } + }; + realSourceWithPrepareFailure.setAllowPreparation(false); + MediaSource maskingMediaSource = + new MaskingMediaSource(realSourceWithPrepareFailure, /* useLazyPreparation= */ false); + player.setMediaSource(maskingMediaSource); + + player.prepare(); + // Assert the prepare error is reported. + advance(player).untilPlayerError(); + } + // Internal methods. private void addWatchAsSystemFeature() {