Minor refactoring of cast media_player (#65125)

This commit is contained in:
Erik Montnemery 2022-01-29 16:13:59 +01:00 committed by GitHub
parent 4a042e7d73
commit d770a54881
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23

View File

@ -4,7 +4,6 @@ from __future__ import annotations
import asyncio import asyncio
from contextlib import suppress from contextlib import suppress
from datetime import datetime, timedelta from datetime import datetime, timedelta
import functools as ft
import json import json
import logging import logging
from urllib.parse import quote from urllib.parse import quote
@ -461,33 +460,10 @@ class CastDevice(MediaPlayerEntity):
media_controller = self._media_controller() media_controller = self._media_controller()
media_controller.seek(position) media_controller.seek(position)
async def async_browse_media(self, media_content_type=None, media_content_id=None): async def _async_root_payload(self, content_filter):
"""Implement the websocket media browsing helper.""" """Generate root node."""
kwargs = {}
children = [] children = []
# Add external sources
if self._chromecast.cast_type == pychromecast.const.CAST_TYPE_AUDIO:
kwargs["content_filter"] = lambda item: item.media_content_type.startswith(
"audio/"
)
if media_content_id is not None:
if plex.is_plex_media_id(media_content_id):
return await plex.async_browse_media(
self.hass,
media_content_type,
media_content_id,
platform=CAST_DOMAIN,
)
return await media_source.async_browse_media(
self.hass, media_content_id, **kwargs
)
if media_content_type == "plex":
return await plex.async_browse_media(
self.hass, None, None, platform=CAST_DOMAIN
)
if "plex" in self.hass.config.components: if "plex" in self.hass.config.components:
children.append( children.append(
BrowseMedia( BrowseMedia(
@ -501,15 +477,17 @@ class CastDevice(MediaPlayerEntity):
) )
) )
# Add local media source
try: try:
result = await media_source.async_browse_media( result = await media_source.async_browse_media(
self.hass, media_content_id, **kwargs self.hass, None, content_filter=content_filter
) )
children.append(result) children.append(result)
except BrowseError: except BrowseError:
if not children: if not children:
raise raise
# If there's only one media source, resolve it
if len(children) == 1: if len(children) == 1:
return await self.async_browse_media( return await self.async_browse_media(
children[0].media_content_type, children[0].media_content_type,
@ -526,6 +504,34 @@ class CastDevice(MediaPlayerEntity):
children=children, children=children,
) )
async def async_browse_media(self, media_content_type=None, media_content_id=None):
"""Implement the websocket media browsing helper."""
content_filter = None
if self._chromecast.cast_type == pychromecast.const.CAST_TYPE_AUDIO:
def audio_content_filter(item):
"""Filter non audio content."""
return item.media_content_type.startswith("audio/")
content_filter = audio_content_filter
if media_content_id is None:
return await self._async_root_payload(content_filter)
if plex.is_plex_media_id(media_content_id):
return await plex.async_browse_media(
self.hass, media_content_type, media_content_id, platform=CAST_DOMAIN
)
if media_content_type == "plex":
return await plex.async_browse_media(
self.hass, None, None, platform=CAST_DOMAIN
)
return await media_source.async_browse_media(
self.hass, media_content_id, content_filter=content_filter
)
async def async_play_media(self, media_type, media_id, **kwargs): async def async_play_media(self, media_type, media_id, **kwargs):
"""Play a piece of media.""" """Play a piece of media."""
# Handle media_source # Handle media_source
@ -547,12 +553,6 @@ class CastDevice(MediaPlayerEntity):
hass_url = get_url(self.hass, prefer_external=True) hass_url = get_url(self.hass, prefer_external=True)
media_id = f"{hass_url}{media_id}" media_id = f"{hass_url}{media_id}"
await self.hass.async_add_executor_job(
ft.partial(self.play_media, media_type, media_id, **kwargs)
)
def play_media(self, media_type, media_id, **kwargs):
"""Play media from a URL."""
extra = kwargs.get(ATTR_MEDIA_EXTRA, {}) extra = kwargs.get(ATTR_MEDIA_EXTRA, {})
metadata = extra.get("metadata") metadata = extra.get("metadata")
@ -571,7 +571,9 @@ class CastDevice(MediaPlayerEntity):
if "app_id" in app_data: if "app_id" in app_data:
app_id = app_data.pop("app_id") app_id = app_data.pop("app_id")
_LOGGER.info("Starting Cast app by ID %s", app_id) _LOGGER.info("Starting Cast app by ID %s", app_id)
self._chromecast.start_app(app_id) await self.hass.async_add_executor_job(
self._chromecast.start_app, app_id
)
if app_data: if app_data:
_LOGGER.warning( _LOGGER.warning(
"Extra keys %s were ignored. Please use app_name to cast media", "Extra keys %s were ignored. Please use app_name to cast media",
@ -581,21 +583,28 @@ class CastDevice(MediaPlayerEntity):
app_name = app_data.pop("app_name") app_name = app_data.pop("app_name")
try: try:
quick_play(self._chromecast, app_name, app_data) await self.hass.async_add_executor_job(
quick_play, self._chromecast, app_name, app_data
)
except NotImplementedError: except NotImplementedError:
_LOGGER.error("App %s not supported", app_name) _LOGGER.error("App %s not supported", app_name)
# Handle plex # Handle plex
elif media_id and media_id.startswith(PLEX_URI_SCHEME): elif media_id and media_id.startswith(PLEX_URI_SCHEME):
media_id = media_id[len(PLEX_URI_SCHEME) :] media_id = media_id[len(PLEX_URI_SCHEME) :]
media = lookup_plex_media(self.hass, media_type, media_id) media = await self.hass.async_add_executor_job(
lookup_plex_media, self.hass, media_type, media_id
)
if media is None: if media is None:
return return
controller = PlexController() controller = PlexController()
self._chromecast.register_handler(controller) self._chromecast.register_handler(controller)
controller.play_media(media) await self.hass.async_add_executor_job(controller.play_media, media)
else: else:
app_data = {"media_id": media_id, "media_type": media_type, **extra} app_data = {"media_id": media_id, "media_type": media_type, **extra}
quick_play(self._chromecast, "default_media_receiver", app_data) await self.hass.async_add_executor_job(
quick_play, self._chromecast, "default_media_receiver", app_data
)
def _media_status(self): def _media_status(self):
""" """