From 4d2aa8f9a2578e19f7fa99181e4265b32e26b954 Mon Sep 17 00:00:00 2001 From: edde746 <86283021+edde746@users.noreply.github.com> Date: Thu, 3 Sep 2026 13:08:46 +0200 Subject: [PATCH] chore(plex): trim LiveTvDvr to the fields Live TV renders LiveTvDvr parsed 21 DVR fields plus nested Setting and raw Device lists on every Live TV availability refresh, while the app reads only the key, the three lineup labels, and the enabled channel mappings. The rest describe tuner hardware and DVR setup, which Plezy does not implement. Keep key, lineup, lineupTitle, lineupURL and channelMappings, and channelKey/enabled on ChannelMapping. The tests keep the root channel-mapping fallback, malformed-sibling tolerance and flexible `enabled` parsing. --- lib/models/livetv_dvr.dart | 61 ++----------------- lib/models/livetv_dvr.g.dart | 20 ------ test/models/livetv_flexible_parsing_test.dart | 12 ---- test/services/plex_live_tv_support_test.dart | 8 +-- 4 files changed, 10 insertions(+), 91 deletions(-) diff --git a/lib/models/livetv_dvr.dart b/lib/models/livetv_dvr.dart index 45824e906..9668e6253 100644 --- a/lib/models/livetv_dvr.dart +++ b/lib/models/livetv_dvr.dart @@ -1,73 +1,26 @@ import 'package:json_annotation/json_annotation.dart'; import '../utils/json_utils.dart'; -import 'media_subscription.dart'; part 'livetv_dvr.g.dart'; List _parseChannelMappings(Object? raw) => parseFlexibleJsonList(raw, ChannelMapping.fromJson); -List _parseSettings(Object? raw) => parseFlexibleJsonList(raw, SubscriptionSetting.fromJson); - -List> _parseRawMaps(Object? raw) => flexibleMapList(raw); - -/// Represents a Plex Live TV DVR device (e.g., HDHomeRun tuner, IPTV provider) +/// A Plex Live TV DVR (e.g., HDHomeRun tuner, IPTV provider), reduced to what +/// Plezy renders: identity, lineup labelling, and the enabled-channel mapping. +/// Plex also reports tuner hardware, `Setting`, and `Device` relations for DVR +/// setup, which Plezy does not implement. @JsonSerializable(createToJson: false) class LiveTvDvr { @JsonKey(defaultValue: '') final String key; - @JsonKey(defaultValue: '') - final String uuid; - final String? make; - final String? model; - final String? modelNumber; - final String? firmware; - @JsonKey(fromJson: flexibleInt) - final int? tuners; final String? lineup; final String? lineupTitle; final String? lineupURL; - final String? country; - final String? language; - @JsonKey(fromJson: flexibleInt) - final int? status; - @JsonKey(fromJson: flexibleInt) - final int? state; - final String? protocol; - final String? sources; - final String? uri; - @JsonKey(fromJson: flexibleInt) - final int? lastSeenAt; @JsonKey(name: 'ChannelMapping', fromJson: _parseChannelMappings) final List channelMappings; - @JsonKey(name: 'Setting', fromJson: _parseSettings) - final List settings; - @JsonKey(name: 'Device', fromJson: _parseRawMaps) - final List> devices; - LiveTvDvr({ - required this.key, - required this.uuid, - this.make, - this.model, - this.modelNumber, - this.firmware, - this.tuners, - this.lineup, - this.lineupTitle, - this.lineupURL, - this.country, - this.language, - this.status, - this.state, - this.protocol, - this.sources, - this.uri, - this.lastSeenAt, - this.channelMappings = const [], - this.settings = const [], - this.devices = const [], - }); + LiveTvDvr({required this.key, this.lineup, this.lineupTitle, this.lineupURL, this.channelMappings = const []}); factory LiveTvDvr.fromJson(Map json) => _$LiveTvDvrFromJson(json); } @@ -76,12 +29,10 @@ class LiveTvDvr { @JsonSerializable(createToJson: false) class ChannelMapping { final String? channelKey; - final String? deviceIdentifier; @JsonKey(fromJson: flexibleBool) final bool? enabled; - final String? lineupIdentifier; - ChannelMapping({this.channelKey, this.deviceIdentifier, this.enabled, this.lineupIdentifier}); + ChannelMapping({this.channelKey, this.enabled}); factory ChannelMapping.fromJson(Map json) => _$ChannelMappingFromJson(json); } diff --git a/lib/models/livetv_dvr.g.dart b/lib/models/livetv_dvr.g.dart index fd49b4672..aac30e0dc 100644 --- a/lib/models/livetv_dvr.g.dart +++ b/lib/models/livetv_dvr.g.dart @@ -8,36 +8,16 @@ part of 'livetv_dvr.dart'; LiveTvDvr _$LiveTvDvrFromJson(Map json) => LiveTvDvr( key: json['key'] as String? ?? '', - uuid: json['uuid'] as String? ?? '', - make: json['make'] as String?, - model: json['model'] as String?, - modelNumber: json['modelNumber'] as String?, - firmware: json['firmware'] as String?, - tuners: flexibleInt(json['tuners']), lineup: json['lineup'] as String?, lineupTitle: json['lineupTitle'] as String?, lineupURL: json['lineupURL'] as String?, - country: json['country'] as String?, - language: json['language'] as String?, - status: flexibleInt(json['status']), - state: flexibleInt(json['state']), - protocol: json['protocol'] as String?, - sources: json['sources'] as String?, - uri: json['uri'] as String?, - lastSeenAt: flexibleInt(json['lastSeenAt']), channelMappings: json['ChannelMapping'] == null ? const [] : _parseChannelMappings(json['ChannelMapping']), - settings: json['Setting'] == null - ? const [] - : _parseSettings(json['Setting']), - devices: json['Device'] == null ? const [] : _parseRawMaps(json['Device']), ); ChannelMapping _$ChannelMappingFromJson(Map json) => ChannelMapping( channelKey: json['channelKey'] as String?, - deviceIdentifier: json['deviceIdentifier'] as String?, enabled: flexibleBool(json['enabled']), - lineupIdentifier: json['lineupIdentifier'] as String?, ); diff --git a/test/models/livetv_flexible_parsing_test.dart b/test/models/livetv_flexible_parsing_test.dart index 6412ab24e..2481f8150 100644 --- a/test/models/livetv_flexible_parsing_test.dart +++ b/test/models/livetv_flexible_parsing_test.dart @@ -10,20 +10,8 @@ void main() { {'channelKey': 7}, {'channelKey': 'channel-1'}, ], - 'Setting': [ - {'id': 7}, - {'id': 'setting-1'}, - ], - 'Device': [ - 'invalid', - {'uuid': 'device-1'}, - ], }); expect(dvr.channelMappings.map((entry) => entry.channelKey), ['channel-1']); - expect(dvr.settings.map((entry) => entry.id), ['setting-1']); - expect(dvr.devices, [ - {'uuid': 'device-1'}, - ]); final template = SubscriptionTemplate.fromJson({ 'MediaSubscription': [ diff --git a/test/services/plex_live_tv_support_test.dart b/test/services/plex_live_tv_support_test.dart index 5956a423c..0186e7247 100644 --- a/test/services/plex_live_tv_support_test.dart +++ b/test/services/plex_live_tv_support_test.dart @@ -151,13 +151,13 @@ void main() { ]); }); - test('DVR list applies root channel mapping to each DVR and parses string numbers', () async { + test('DVR list applies root channel mapping to each DVR and parses flexible enabled flags', () async { final client = makeClient((request) async { expect(request.url.path, '/livetv/dvrs'); return jsonResponse({ 'MediaContainer': { 'Dvr': [ - {'key': '1', 'uuid': 'dvr-1', 'tuners': '2', 'status': '1'}, + {'key': '1', 'uuid': 'dvr-1', 'lineupTitle': 'Antenna', 'tuners': '2', 'status': '1'}, ], 'ChannelMapping': [ {'channelKey': 'ch-1', 'enabled': '1', 'lineupIdentifier': '001'}, @@ -170,8 +170,8 @@ void main() { final dvrs = await client.liveTvDvr!.fetchDvrs(); expect(dvrs, hasLength(1)); - expect(dvrs.single.tuners, 2); - expect(dvrs.single.status, 1); + expect(dvrs.single.key, '1'); + expect(dvrs.single.lineupTitle, 'Antenna'); expect(dvrs.single.channelMappings.single.channelKey, 'ch-1'); expect(dvrs.single.channelMappings.single.enabled, isTrue); });