leonardoxh / race-control-tv

Android TV app for F1 TV
MIT License
210 stars 19 forks source link

Not able to watch Live and recent Sessions, DRM issue #119

Closed LoVega1337 closed 2 years ago

LoVega1337 commented 2 years ago

So I tried watching the Australian FP2 replay and the player just stays blank and doesn't retrieve any video. This might be the first indication that F1TV is cracking down on 3rd party apps that don't support Widevine DRM.

This might be an issue with the ExoPlayer not supporting Widevine but I'm not sure yet. See for reference: https://github.com/robvdpol/RaceControl/issues/414#issuecomment-1092454241

Edit: ExoPlayer does in fact support DRM, just isn't configured in this app yet. This might need some work, otherwise the app can't play live and recent sessions.

AidanGee7 commented 2 years ago

Same issue here for me sadly.

meisterj commented 2 years ago

Same issue here, Philips Android TV, cant watch recent race/training. highlights work, so i think its an Language issue? highlights are only in english

LoVega1337 commented 2 years ago

@meisterj Not a language issue, this is a DRM issue. Everything except the International feeds of the main events are exclusively in English.

juangzz commented 2 years ago

Same issue here, can login now with new apk, but not loading live broadcast. This is not cool F1

nelis68 commented 2 years ago

Same problem here , it seems a time issue. After a couple of hours it works .

leonardoxh commented 2 years ago

Yep this has to do with the DRM part.

I have some ideas to play around with, but it is going to take some time.

Woziak commented 2 years ago

With the 2.6.1 apk I am able to login but it does not start the app after login. I am on a DuneHD Android TV player.

gazdajezda commented 2 years ago

Same here. Newest apk on Phillips POS9002 Android TV. Old races works, also now i can watch todays qually, but at the time of live event and even for some hour, player was blank. Seems they let open non-drm content available later.

LoVega1337 commented 2 years ago

@leonardoxh I read through a couple of documentations of ExoPlayer and the implementation of DRM might be quite simple, although the current implementation of the ExoPlayer itself looks kinda complicated so I need a bit of help here.

The license URL from F1TV is this URL (with edited CHANNEL_ID and CONTENT_ID var): https://f1tv.formula1.com/2.0/R/ENG/BIG_SCREEN_HLS/ALL/CONTENT/LA/widevine?channelId=$CHANNEL_ID&contentId=$CONTENT_ID

My quick and dirty Implementation of it (according to the ExoPlayer doc) in the ChannelPlaybackFragment.kt:


private static @Nullable UUID getDrmUuid(String drmScheme) {
        switch (toLowerInvariant(drmScheme)) {
            case "widevine":
                return C.WIDEVINE_UUID;
            case "playready":
                return C.PLAYREADY_UUID;
            case "clearkey":
                return C.CLEARKEY_UUID;
            default:
                try {
                return UUID.fromString(drmScheme);
              } catch (RuntimeException e) {
                return null;
              }
         }
    }

    private val player: ExoPlayer by lazy {
        val player = ExoPlayer.Builder(requireContext())
            .setTrackSelector(trackSelector)
            .setDrmConfiguration(
                new ExoPlayer.DrmConfiguration.Builder(C.WIDEVINE_UUID)
                    .setLicenseUri("https://f1tv.formula1.com/2.0/R/ENG/BIG_SCREEN_HLS/ALL/CONTENT/LA/widevine?channelId=$CHANNEL_ID&contentId=$CONTENT_ID")
                    .setMultiSession(true)
                    .setLicenseRequestHeaders(httpDataSourceFactory) // Might need to be changed back to "httpRequestHeaders"
                    .build())
            .build()
        player.playWhenReady = true
        player.addAnalyticsListener(EventLogger(trackSelector))
        player
    }
nilsnilsnils commented 2 years ago

Same problem here , it seems a time issue. After a couple of hours it works .

Same here on my site

leonardoxh commented 2 years ago

@LoVega1337 looks awesome to start with at least. Thanks

leonardoxh commented 2 years ago

I released today this one:

https://github.com/leonardoxh/race-control-tv/releases/tag/v2.6.2

Which will fix the DRM issues, I only tested with the F3 sessions but seems to work fine. I will keep this thread open until I know for sure this fixed everything.

LoVega1337 commented 2 years ago

Works beautifully for me, awesome!

Although:

nilsnilsnils commented 2 years ago

Thanks for all your hard work :)

bashopman commented 2 years ago

Works like a charm! Thanks!

meisterj commented 2 years ago

Tahnk You!!! Works for me now :-)

gazdajezda commented 2 years ago

As others: thankx!

ragnos commented 2 years ago

While it did work yesterday, today during the Porsche Cup Practice the stream doesn't start for me. Replays work. The player takes some seconds with the spinning wheel animation, then crashes and starts again. Can't even enter the language settings because it all happens so quick.

Screenshot 2022-04-23 09-35-22

FireTV 4k, App Version 2.6.2. Deleted cache, then all data, then removed the app and sideloaded again. No change in behaviour.

Edit: It's quite likely FOM screwed up somewhere, because right now they got TWO live sessions going on:

grafik Screenshot 2022-04-23 09-51-32

While both sessions work in my browser, they both don't in-app like described above.

leonardoxh commented 2 years ago

I've noticed that I might have messed up the links a bit 😅 will test new stuff today

Vlame04 commented 2 years ago

I have the same problem. With F1, F2 and F3 I can watch the replays but I can't watch the live sessions. From PSC I can't watch anything

ArneAbbink commented 2 years ago

Exactly the same issue over here. No live content, only replays.

nilsnilsnils commented 2 years ago

Same here cant watch f1 Sprint live. Yesterday everything was fine watching quali live

Zorrobus commented 2 years ago

Same here, no live stream, crash season 2019. Sony Android TV

Dlopezv92 commented 2 years ago

Same problem here. Worked in the yesterday qualy but today in the Imola Sprint doesn’t work. The icon Load is always in the screen and doesn’t load anything

JustJoostNL commented 2 years ago

For me also the same problem last race, wish you luck with fixing it @leonardoxh

ragnos commented 2 years ago

The issue persists with the currently starting fp1 session.

rulasmarmol commented 2 years ago

Same here, live stream not working, only replays.

Coedy commented 2 years ago

Same here. I get a spinning loading animation, and restart of the stream (with the same spinning loading animation). Good luck @leonardoxh!

pietjelombok commented 2 years ago

Live stream is not starting

Dominion99NL commented 2 years ago

I cannot get it to work, I have removed the app on my Sony Android TV and installed it again, i do get a login page from the F1 website, enter my credentials but after successfull login, i'm taking to the dashboard from the F1 website, do i miss a button somewhere to return to the F1 App because i'm never getting back to the F1 app, when i close the app and restart the process is repeating itself.

LoVega1337 commented 2 years ago

@leonardoxh So I did a little bit of investigation and it seems like it kind of fetches the wrong sessionId or contentId. I started the last replay from the Miami GP through the F1TV site and it fetches the following .mpd URL: https://ott-video-cf.formula1.com/6180c994cb835402/out/v1/95a456635d9f4a22bf3423fda15932ff/index.mpd?[...] I tried starting the same replay on the app in debug mode and it tries to fetch the URL: https://ott-video-cf.formula1.com/6180c994cb835402/out/v1/02dd87aa3baf42ba934707e36f52cb9a/index.mpd?[...] This throws me an 403 error in the app and when copying it into the browser, the other URL from the F1TV site works fine and starts downloading the index.mpd.

The ChannelPlaybackFragment.kt fetches the complete URL, although I'm not sure where it gets the different IDs from.

Shamrayev365 commented 2 years ago

Is this project still alive?

WouterVork commented 2 years ago

Wondering the same thing. I really hope so; the quality of the stream is (or was) so much better than the official app

jonathanflack commented 2 years ago

I am seeing the exact same behavior as @LoVega1337 today when trying to load the Monaco quali replay for F1. It's fetching the wrong URL and failing. Screen is exactly as @ragnos posted earlier.

Worked fine for P3 highlights. 2.6.2

nilsnilsnils commented 2 years ago

Idee for a Workaround with a self created apk.

Can anyone create a fork where the Login webseite appears on every start and the name and password will be auto filled from Text file and the Login finishes auto.?

Editing the text file and creating the apk myself is not the problem.

JustJoostNL commented 2 years ago

Is this a workaround for the drm issue?

leonardoxh commented 2 years ago

The project is still alive, but I do not have a way to fix the DRM issue yet, unfortunately

jmarttila commented 2 years ago

I have been able to stream all of the recent races live using my own patches. I needed to change streaming to HLS, and attach User-Agent, ascendontoken and entitlementtoken to the DrmConfiguration in MediaSourceItemFactory

Examples:

nilsnilsnils commented 2 years ago

I have been able to stream all of the recent races live using my own patches. I needed to change streaming to HLS, and attach User-Agent, ascendontoken and entitlementtoken to the DrmConfiguration in MediaSourceItemFactory

Examples:

  • Use DASH

-        private const val PLAY_URL = "https://f1tv.formula1.com/1.0/R/ENG/BIG_SCREEN_%s/ALL/CONTENT/PLAY?contentId=%s"

-        const val DRM_URL = "https://f1tv.formula1.com/2.0/R/ENG/BIG_SCREEN_HLS/ALL/CONTENT/LA/widevine?contentId=%s&channelId=%s"

+        private const val PLAY_URL = "https://f1tv.formula1.com/2.0/R/ENG/BIG_SCREEN_%s/ALL/CONTENT/PLAY?contentId=%s"

+        const val DRM_URL = "https://f1tv.formula1.com/2.0/R/ENG/BIG_SCREEN_DASH/ALL/CONTENT/LA/widevine?contentId=%s"
  • Headers

                MediaItem.DrmConfiguration.Builder(C.WIDEVINE_UUID)

                    .setLicenseRequestHeaders(

                        mutableMapOf(

                            "User-Agent" to BuildConfig.DEFAULT_USER_AGENT,

                            "ascendontoken" to "<token>",

                            "entitlementtoken" to "<token>"

                        )

                    )

                    .setLicenseUri(F1Client.DRM_URL.format(viewing.contentId))

                    .setMultiSession(true)

                    .build()

Can you create an APK that we can test it :)?

jmarttila commented 2 years ago

I just hardcoded the tokens into the APK I deployed to my device, it does not provide the necessary login/token aquiring flows. If you want to test this out, you'll want to build the app yourself with the necessary tokens.

In addition, only live streams work so it's not really a full solution. I haven't had time to make a general solution.

leonardoxh commented 2 years ago

This is a port of the solution above:

https://github.com/leonardoxh/race-control-tv/pull/136

Will try it out this weekend

gazdajezda commented 2 years ago

Are there apk with that fix available? Ty

leonardoxh commented 2 years ago

I have this test APK: https://drive.google.com/file/d/1oDTbyt-scbkqqM-Xt3ChBa8WLmg-tFz5/view?usp=sharing

The current content works and I see the DRM Loggins going, however I need to test this more Friday with the live content.

gazdajezda commented 2 years ago

Np. I will test it too :)

jmarttila commented 2 years ago

The test PR branch did not work directly with live streaming. However, I could get it to work when I applied the changes I did exactly:

diff --git a/app/src/main/java/fr/groggy/racecontrol/tv/f1/F1Client.kt b/app/src/main/java/fr/groggy/racecontrol/tv/f1/F1Client.kt
index c397911..3d1dd18 100644
--- a/app/src/main/java/fr/groggy/racecontrol/tv/f1/F1Client.kt
+++ b/app/src/main/java/fr/groggy/racecontrol/tv/f1/F1Client.kt
@@ -23,8 +23,8 @@ class F1Client @Inject constructor(
     companion object {
         const val API_KEY = "fCUCjWrKPu9ylJwRAv8BpGLEgiAuThx7"

-        private const val PLAY_URL = "https://f1tv.formula1.com/1.0/R/ENG/BIG_SCREEN_%s/ALL/CONTENT/PLAY?contentId=%s"
-        const val DRM_URL = "https://f1tv.formula1.com/2.0/R/ENG/BIG_SCREEN_HLS/ALL/CONTENT/LA/widevine?contentId=%s&channelId=%s"
+        private const val PLAY_URL = "https://f1tv.formula1.com/2.0/R/ENG/BIG_SCREEN_%s/ALL/CONTENT/PLAY?contentId=%s"
+        const val DRM_URL = "https://f1tv.formula1.com/2.0/R/ENG/BIG_SCREEN_DASH/ALL/CONTENT/LA/widevine?contentId=%s"
     }

     private val viewingResponseJsonAdapter = moshi.adapter(F1TvViewingResponse::class.java)
diff --git a/app/src/main/java/fr/groggy/racecontrol/tv/ui/channel/playback/ChannelPlaybackActivity.kt b/app/src/main/java/fr/groggy/racecontrol/tv/ui/channel/playback/ChannelPlaybackActivity.kt
index aae0f2d..e16d92f 100644
--- a/app/src/main/java/fr/groggy/racecontrol/tv/ui/channel/playback/ChannelPlaybackActivity.kt
+++ b/app/src/main/java/fr/groggy/racecontrol/tv/ui/channel/playback/ChannelPlaybackActivity.kt
@@ -43,7 +43,7 @@ class ChannelPlaybackActivity : FragmentActivity(R.layout.activity_channel_playb
         super.onCreate(savedInstanceState)

         lifecycleScope.launchWhenCreated {
-            attachViewingIfNeeded(Settings.StreamType.DASH_HLS)
+            attachViewingIfNeeded(Settings.StreamType.DASH)
         }
     }

@@ -113,13 +113,13 @@ class ChannelPlaybackActivity : FragmentActivity(R.layout.activity_channel_playb
                 remove(fragment)
                 runOnCommit {
                     lifecycleScope.launch {
-                        attachViewingIfNeeded(Settings.StreamType.HLS)
+                        attachViewingIfNeeded(Settings.StreamType.DASH)
                     }
                 }
             }
         } else {
             lifecycleScope.launch {
-                attachViewingIfNeeded(Settings.StreamType.HLS)
+                attachViewingIfNeeded(Settings.StreamType.DASH)
             }
         }
     }
leonardoxh commented 2 years ago

Oh dam, the PLAY_URL was wrong, that was the key all the time, now it works flawless again!!!

Will release it asap

leonardoxh commented 2 years ago

It is released:

https://github.com/leonardoxh/race-control-tv/releases/tag/2.7.0

I will keep this issue open still for this weekend and if everything works we can finally close this monster.

nilsnilsnils commented 2 years ago

Thanks for your work :) you mentioned me in the release nodes but you must mean someone else 😅

gazdajezda commented 2 years ago

Great! Can't wait to watch again on TV :)

leonardoxh commented 2 years ago

Could be @nilsnilsnils