mirror of
https://github.com/home-assistant/core.git
synced 2025-07-23 05:07:41 +00:00
Use camera_capabilities instead frontend_stream_type (#130604)
This commit is contained in:
parent
069e6c4554
commit
e48857987b
@ -896,7 +896,7 @@ class Camera(Entity, cached_properties=CACHED_PROPERTIES_WITH_ATTR_):
|
|||||||
else:
|
else:
|
||||||
frontend_stream_types.add(StreamType.HLS)
|
frontend_stream_types.add(StreamType.HLS)
|
||||||
|
|
||||||
if self._webrtc_provider:
|
if self._webrtc_provider or self._legacy_webrtc_provider:
|
||||||
frontend_stream_types.add(StreamType.WEB_RTC)
|
frontend_stream_types.add(StreamType.WEB_RTC)
|
||||||
|
|
||||||
return CameraCapabilities(frontend_stream_types)
|
return CameraCapabilities(frontend_stream_types)
|
||||||
|
@ -64,7 +64,7 @@ class CameraMediaSource(MediaSource):
|
|||||||
if not camera:
|
if not camera:
|
||||||
raise Unresolvable(f"Could not resolve media item: {item.identifier}")
|
raise Unresolvable(f"Could not resolve media item: {item.identifier}")
|
||||||
|
|
||||||
if (stream_type := camera.frontend_stream_type) is None:
|
if not (stream_types := camera.camera_capabilities.frontend_stream_types):
|
||||||
return PlayMedia(
|
return PlayMedia(
|
||||||
f"/api/camera_proxy_stream/{camera.entity_id}", camera.content_type
|
f"/api/camera_proxy_stream/{camera.entity_id}", camera.content_type
|
||||||
)
|
)
|
||||||
@ -76,7 +76,7 @@ class CameraMediaSource(MediaSource):
|
|||||||
url = await _async_stream_endpoint_url(self.hass, camera, HLS_PROVIDER)
|
url = await _async_stream_endpoint_url(self.hass, camera, HLS_PROVIDER)
|
||||||
except HomeAssistantError as err:
|
except HomeAssistantError as err:
|
||||||
# Handle known error
|
# Handle known error
|
||||||
if stream_type != StreamType.HLS:
|
if StreamType.HLS not in stream_types:
|
||||||
raise Unresolvable(
|
raise Unresolvable(
|
||||||
"Camera does not support MJPEG or HLS streaming."
|
"Camera does not support MJPEG or HLS streaming."
|
||||||
) from err
|
) from err
|
||||||
|
@ -230,13 +230,15 @@ def require_webrtc_support(
|
|||||||
"""Validate that the camera supports WebRTC."""
|
"""Validate that the camera supports WebRTC."""
|
||||||
entity_id = msg["entity_id"]
|
entity_id = msg["entity_id"]
|
||||||
camera = get_camera_from_entity_id(hass, entity_id)
|
camera = get_camera_from_entity_id(hass, entity_id)
|
||||||
if camera.frontend_stream_type != StreamType.WEB_RTC:
|
if StreamType.WEB_RTC not in (
|
||||||
|
stream_types := camera.camera_capabilities.frontend_stream_types
|
||||||
|
):
|
||||||
connection.send_error(
|
connection.send_error(
|
||||||
msg["id"],
|
msg["id"],
|
||||||
error_code,
|
error_code,
|
||||||
(
|
(
|
||||||
"Camera does not support WebRTC,"
|
"Camera does not support WebRTC,"
|
||||||
f" frontend_stream_type={camera.frontend_stream_type}"
|
f" frontend_stream_types={stream_types}"
|
||||||
),
|
),
|
||||||
)
|
)
|
||||||
return
|
return
|
||||||
|
@ -5,6 +5,7 @@ from unittest.mock import PropertyMock, patch
|
|||||||
import pytest
|
import pytest
|
||||||
|
|
||||||
from homeassistant.components import media_source
|
from homeassistant.components import media_source
|
||||||
|
from homeassistant.components.camera import CameraCapabilities
|
||||||
from homeassistant.components.camera.const import StreamType
|
from homeassistant.components.camera.const import StreamType
|
||||||
from homeassistant.components.stream import FORMAT_CONTENT_TYPE
|
from homeassistant.components.stream import FORMAT_CONTENT_TYPE
|
||||||
from homeassistant.core import HomeAssistant
|
from homeassistant.core import HomeAssistant
|
||||||
@ -130,8 +131,10 @@ async def test_resolving_errors(hass: HomeAssistant) -> None:
|
|||||||
with (
|
with (
|
||||||
pytest.raises(media_source.Unresolvable) as exc_info,
|
pytest.raises(media_source.Unresolvable) as exc_info,
|
||||||
patch(
|
patch(
|
||||||
"homeassistant.components.camera.Camera.frontend_stream_type",
|
"homeassistant.components.camera.Camera.camera_capabilities",
|
||||||
new_callable=PropertyMock(return_value=StreamType.WEB_RTC),
|
new_callable=PropertyMock(
|
||||||
|
return_value=CameraCapabilities({StreamType.WEB_RTC})
|
||||||
|
),
|
||||||
),
|
),
|
||||||
):
|
):
|
||||||
await media_source.async_resolve_media(
|
await media_source.async_resolve_media(
|
||||||
|
@ -417,7 +417,7 @@ async def test_ws_get_client_config_no_rtc_camera(
|
|||||||
assert not msg["success"]
|
assert not msg["success"]
|
||||||
assert msg["error"] == {
|
assert msg["error"] == {
|
||||||
"code": "webrtc_get_client_config_failed",
|
"code": "webrtc_get_client_config_failed",
|
||||||
"message": "Camera does not support WebRTC, frontend_stream_type=hls",
|
"message": "Camera does not support WebRTC, frontend_stream_types={<StreamType.HLS: 'hls'>}",
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@ -747,7 +747,7 @@ async def test_websocket_webrtc_offer_invalid_stream_type(
|
|||||||
assert not response["success"]
|
assert not response["success"]
|
||||||
assert response["error"] == {
|
assert response["error"] == {
|
||||||
"code": "webrtc_offer_failed",
|
"code": "webrtc_offer_failed",
|
||||||
"message": "Camera does not support WebRTC, frontend_stream_type=hls",
|
"message": "Camera does not support WebRTC, frontend_stream_types={<StreamType.HLS: 'hls'>}",
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@ -800,45 +800,6 @@ async def mock_hls_stream_source_fixture() -> AsyncGenerator[AsyncMock]:
|
|||||||
yield mock_hls_stream_source
|
yield mock_hls_stream_source
|
||||||
|
|
||||||
|
|
||||||
@pytest.mark.usefixtures(
|
|
||||||
"mock_camera",
|
|
||||||
"mock_hls_stream_source", # Not an RTSP stream source
|
|
||||||
"mock_camera_webrtc_frontendtype_only",
|
|
||||||
)
|
|
||||||
async def test_unsupported_rtsp_to_webrtc_stream_type(
|
|
||||||
hass: HomeAssistant, hass_ws_client: WebSocketGenerator
|
|
||||||
) -> None:
|
|
||||||
"""Test rtsp-to-webrtc is not registered for non-RTSP streams."""
|
|
||||||
client = await hass_ws_client(hass)
|
|
||||||
await client.send_json_auto_id(
|
|
||||||
{
|
|
||||||
"type": "camera/webrtc/offer",
|
|
||||||
"entity_id": "camera.demo_camera",
|
|
||||||
"offer": WEBRTC_OFFER,
|
|
||||||
}
|
|
||||||
)
|
|
||||||
response = await client.receive_json()
|
|
||||||
assert response["type"] == TYPE_RESULT
|
|
||||||
assert response["success"]
|
|
||||||
subscription_id = response["id"]
|
|
||||||
|
|
||||||
# Session id
|
|
||||||
response = await client.receive_json()
|
|
||||||
assert response["id"] == subscription_id
|
|
||||||
assert response["type"] == "event"
|
|
||||||
assert response["event"]["type"] == "session"
|
|
||||||
|
|
||||||
# Answer
|
|
||||||
response = await client.receive_json()
|
|
||||||
assert response["id"] == subscription_id
|
|
||||||
assert response["type"] == "event"
|
|
||||||
assert response["event"] == {
|
|
||||||
"type": "error",
|
|
||||||
"code": "webrtc_offer_failed",
|
|
||||||
"message": "Camera does not support WebRTC",
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
@pytest.mark.usefixtures("mock_camera", "mock_stream_source")
|
@pytest.mark.usefixtures("mock_camera", "mock_stream_source")
|
||||||
async def test_rtsp_to_webrtc_provider_unregistered(
|
async def test_rtsp_to_webrtc_provider_unregistered(
|
||||||
hass: HomeAssistant, hass_ws_client: WebSocketGenerator
|
hass: HomeAssistant, hass_ws_client: WebSocketGenerator
|
||||||
@ -894,7 +855,7 @@ async def test_rtsp_to_webrtc_provider_unregistered(
|
|||||||
assert not response["success"]
|
assert not response["success"]
|
||||||
assert response["error"] == {
|
assert response["error"] == {
|
||||||
"code": "webrtc_offer_failed",
|
"code": "webrtc_offer_failed",
|
||||||
"message": "Camera does not support WebRTC, frontend_stream_type=hls",
|
"message": "Camera does not support WebRTC, frontend_stream_types={<StreamType.HLS: 'hls'>}",
|
||||||
}
|
}
|
||||||
|
|
||||||
assert not mock_provider.called
|
assert not mock_provider.called
|
||||||
@ -1093,7 +1054,7 @@ async def test_ws_webrtc_candidate_invalid_stream_type(
|
|||||||
assert not response["success"]
|
assert not response["success"]
|
||||||
assert response["error"] == {
|
assert response["error"] == {
|
||||||
"code": "webrtc_candidate_failed",
|
"code": "webrtc_candidate_failed",
|
||||||
"message": "Camera does not support WebRTC, frontend_stream_type=hls",
|
"message": "Camera does not support WebRTC, frontend_stream_types={<StreamType.HLS: 'hls'>}",
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
@ -211,7 +211,7 @@ async def _test_setup_and_signaling(
|
|||||||
) -> None:
|
) -> None:
|
||||||
"""Test the go2rtc config entry."""
|
"""Test the go2rtc config entry."""
|
||||||
entity_id = camera.entity_id
|
entity_id = camera.entity_id
|
||||||
assert camera.frontend_stream_type == StreamType.HLS
|
assert camera.camera_capabilities.frontend_stream_types == {StreamType.HLS}
|
||||||
|
|
||||||
assert await async_setup_component(hass, DOMAIN, config)
|
assert await async_setup_component(hass, DOMAIN, config)
|
||||||
await hass.async_block_till_done(wait_background_tasks=True)
|
await hass.async_block_till_done(wait_background_tasks=True)
|
||||||
|
@ -745,7 +745,7 @@ async def test_camera_web_rtc_unsupported(
|
|||||||
assert not msg["success"]
|
assert not msg["success"]
|
||||||
assert msg["error"] == {
|
assert msg["error"] == {
|
||||||
"code": "webrtc_offer_failed",
|
"code": "webrtc_offer_failed",
|
||||||
"message": "Camera does not support WebRTC, frontend_stream_type=hls",
|
"message": "Camera does not support WebRTC, frontend_stream_types={<StreamType.HLS: 'hls'>}",
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
Loading…
x
Reference in New Issue
Block a user