Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Set-up a comprehensive check when trying to reuse MediaKeySystemAccess #1597

Open
wants to merge 3 commits into
base: dev
Choose a base branch
from

Conversation

peaBerberian
Copy link
Collaborator

While working on cases where an application wants to set-up different DRM configurations depending on the content, yet still keep the same MediaKeys instance if possible (to keep our MediaKeySession cache), I tried to make sure we support at worse a case where a more constrained configuration would still be considered as compatible to a less constrained one - as long as there's no loss of features / capabilities between the two.

After attempts specific to the RxPlayer's keySystems API format, I ended up relying on the asked MediaKeySystemConfigurations (both the new wanted one and the one that led to the current MediaKeySystemAccess) instead, as the corresponding logic seemed easier to me to maintain.

@peaBerberian peaBerberian force-pushed the fix/comprehensive-cached-check branch from de73819 to ce6a11f Compare November 21, 2024 14:56
@peaBerberian peaBerberian added this to the 4.3.0 milestone Nov 21, 2024
@peaBerberian peaBerberian added the DRM Relative to DRM (EncryptedMediaExtensions) label Nov 21, 2024
@peaBerberian peaBerberian added the Priority: 1 (High) This issue or PR has a high priority. label Nov 22, 2024
@peaBerberian peaBerberian force-pushed the fix/comprehensive-cached-check branch from ce6a11f to 4be0f01 Compare November 28, 2024 11:38
Comment on lines 91 to 94
* @param {Object} newConfiguration
* @param {Object} prevConfiguration
* @param {MediaKeySystemAccess} currentKeySystemAccess
* @param {Object} currentKeySystemOptions
* @returns {null|Object}
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

completing jsdoc would help understand the behavior of this function

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

While doing that I realized that it was unnecessarily complicated. I added a commit that renamed that function to isNewMediaKeySystemConfigurationCompatibleToPreviousOne and simplified its call site

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think isNewMediaKeySystemConfigurationCompatibleWithPreviousOne sounds better

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

You're right, I fixed it

Comment on lines 110 to 114
const prevDistinctiveIdentifier = prevConfiguration.distinctiveIdentifier ?? "optional";
const newDistinctiveIdentifier = newConfiguration.distinctiveIdentifier ?? "optional";
if (prevDistinctiveIdentifier !== newDistinctiveIdentifier) {
return null;
}
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Why does the prevConfiguration matters ?
Shoudn't we just look at the newConfiguration and see if it's compatible with the currentKeySystemAccess?

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I found it easier to reason about as currentKeySystemAccess.getConfiguration() has different rules.

Like for audioCapabilities and videoCapabilities for example, where the result is filtered but where you don't want it to be filtered in this specific case.

Also I would guess that most applications will provide similar keySystems parameters for each load

Comment on lines 128 to 132
const prevSessionTypes = prevConfiguration.sessionTypes ?? [];
const newSessionTypes = newConfiguration.sessionTypes ?? [];
if (!isArraySubsetOf(newSessionTypes, prevSessionTypes)) {
return null;
}
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

From what I understand it's working like that, am I wrong?

1st checkCachedMediaKeySystemAccess call:
newConfiguration: ["temporary", "persistant"]
prevSessionTypes: []
-> creating session1 of type ["temporary", "persistant"]

2nd checkCachedMediaKeySystemAccess call:
newConfiguration: ["temporary",]
prevSessionTypes: ["temporary", "persistant"]
-> reusing session 1, ("temporary" is a subset of ["temporary", "persistant"])

3rd checkCachedMediaKeySystemAccess call:
newConfiguration: ["temporary", "persistant"]
prevSessionTypes: ["temporary",]
-> creating session 2, but we could have used session1 !!

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think prevConfiguration will still be the old ["temporary", "persistant"] one in this case

Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Maybe we can add a unit test for getMediaKeySystemAccess and check that it returns correctly an event of type IReuseMediaKeySystemAccessEvent in this case?

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think it may be a biggest bang for the buck if I check for MediaKeySytemAccess reusage in various keySystems configuration in an integration test as allowed here #1478

I mean we could do both kinds of tests and it would be theoretically better, but decrypt/ code changes often and I don't like adding supplementary friction here.

We could also just test the "should we reuse cache" function, which would not need any mock and thus not have the issues of testing getMediaKeySystemAccess (which requires mocking requestMediaKeySystemAccess and its return value, MediaKeySystemAttacher, and maybe some other utils), but it seems simple enough to understand the various cases that here I'm unsure of the benefits.

Copy link
Collaborator Author

@peaBerberian peaBerberian Dec 12, 2024

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Here's an example of how those integration tests could be implemented:
e52bc61

I did not add tests for everything yet, it's just to show you what I mean here.

Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I tried on my own to make a test, it needs to mock the requestMediaKeySystemAccess API, I think this is reasonably simple:
#1603

@Florent-Bouisset
Copy link
Collaborator

This is outside of the PR but the jsdoc is wrong:

- keySystem {Object}: the original keySystem object

The name of the key is keySystemOptions

While working on cases where an application wants to set-up different DRM configurations depending on the content, yet still keep the same `MediaKeys` instance if possible (to keep our `MediaKeySession` cache), I tried to make sure we support at worse a case where a more constrained configuration would still be considered as compatible to a less constrained one - as long as there's no loss of features / capabilities between the two.

After attempts specific to the RxPlayer's `keySystems` API format, I ended up relying on the asked `MediaKeySystemConfiguration`s (both the new wanted one and the one that led to the current `MediaKeySystemAccess`) instead, as the corresponding logic seemed easier to me to maintain.
@peaBerberian peaBerberian force-pushed the fix/comprehensive-cached-check branch from 4be0f01 to 4410d6d Compare December 12, 2024 11:10
@peaBerberian
Copy link
Collaborator Author

I updated the comments and also removed some of them that was redundant.

@peaBerberian peaBerberian force-pushed the fix/comprehensive-cached-check branch from e5b2cde to 87df748 Compare December 13, 2024 09:54
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
DRM Relative to DRM (EncryptedMediaExtensions) Priority: 1 (High) This issue or PR has a high priority.
Projects
None yet
Development

Successfully merging this pull request may close these issues.

3 participants