Simplified title-change notification handling.

This commit is contained in:
2026-05-24 14:11:21 -04:00
parent 38e91add32
commit 58ad476a94
2 changed files with 7 additions and 43 deletions
+2 -12
View File
@@ -134,12 +134,11 @@ def _classify_notification(
observation: StreamStateObservation,
*,
offline_duration_seconds: int | None = None,
went_offline_after_last_notification: bool = False,
) -> _NotificationKind:
"""Classify the live/title notification policy for a transition.
The caller supplies timing context because it comes from the monitor's
monotonic offline cache and notification-service cache, not the transition.
The caller supplies offline duration because it comes from the monitor's
monotonic offline cache, not the transition.
"""
match transition.kind:
case _StreamTransitionKind.WENT_LIVE:
@@ -153,8 +152,6 @@ def _classify_notification(
return _NotificationKind.LIVE
case _StreamTransitionKind.TITLE_CHANGED:
if went_offline_after_last_notification:
return _NotificationKind.LIVE
return _NotificationKind.TITLE_CHANGE
case _:
@@ -314,7 +311,6 @@ class StreamMonitor:
# Notification policy may need runtime timing context in addition to
# the stored state and latest observation.
offline_duration_seconds: int | None = None
went_offline_after_last_notification = False
match transition.kind:
case _StreamTransitionKind.FIRST_OBSERVATION:
@@ -343,11 +339,6 @@ class StreamMonitor:
)
case _StreamTransitionKind.TITLE_CHANGED:
self.log.info("[%s] Stream title was changed!", domain)
# If we saw an offline event after the last notification, send
# a go-live notice instead of only a title-change notice.
went_offline_after_last_notification = self.offline_timer_cache[
domain
] > self.notification_service.get_last_notification_time(domain)
case _StreamTransitionKind.WENT_OFFLINE:
self.offline_timer_cache[domain] = time.monotonic()
self.log.info("[%s] Stream is now offline.", domain)
@@ -359,7 +350,6 @@ class StreamMonitor:
old_state,
observation,
offline_duration_seconds=offline_duration_seconds,
went_offline_after_last_notification=went_offline_after_last_notification,
)
stream_config: StreamConfigObservation | None = None
+5 -31
View File
@@ -457,32 +457,6 @@ class TestClassifyNotification:
assert notification_kind is _NotificationKind.TITLE_CHANGE
def test_went_offline_after_last_notification_notifies_live(self) -> None:
"""Notify live when stream went offline after the last notification."""
old_state = StreamState(
domain="example.com",
title="Old",
online=True,
status_since="2026-01-01T10:00:00+00:00",
)
observation = _stream_observation(
domain="example.com",
title="New",
online=True,
observed_at="2026-01-01T12:00:00+00:00",
)
transition = _classify_transition(old_state, observation)
notification_kind = _classify_notification(
transition,
old_state,
observation,
went_offline_after_last_notification=True,
)
assert notification_kind is _NotificationKind.LIVE
class TestUpdateAllStreams:
"""Parallel stream update orchestration."""
@@ -959,12 +933,12 @@ class TestUpdateStreamTitleChange:
)
assert owncast.config_call_count == 1
async def test_sends_go_live_when_last_notification_before_offline(
async def test_sends_title_change_after_offline_gap(
self,
stream_repo: StreamRepository,
subscription_repo: SubscriptionRepository,
) -> None:
"""Send go-live instead of title-change after an offline gap."""
"""Send title-change when an already-online stream changes title."""
owncast = _StubOwncastClient(
stream_state=_stream_observation(
domain="title.com",
@@ -991,8 +965,8 @@ class TestUpdateStreamTitleChange:
status_since="2026-01-01T12:00:00+00:00",
)
# Offline timer is MORE recent than last notification,
# and both are old enough to pass rate limiting
# Offline timer is more recent than the last notification, but title
# changes remain title changes once the stream is already online.
now = time.monotonic()
monitor.offline_timer_cache["title.com"] = (
now - _SECONDS_BETWEEN_NOTIFICATIONS - 100
@@ -1005,7 +979,7 @@ class TestUpdateStreamTitleChange:
assert result is True
assert len(client.sent_messages) == 1
assert client.sent_messages[0].content.body == (
"🎥 Title Stream is now live!\n"
"📝 Title Stream has changed its stream title!\n"
"Stream Title: Updated Title\n"
"\n"
"To tune in, visit: https://title.com/"