@homebridge-plugins/homebridge-eufy-security 5.0.0-beta.4 → 5.0.0-beta.40

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (121) hide show
  1. package/CONTRIBUTING.md +9 -17
  2. package/config.schema.json +60 -0
  3. package/dist/account/ownership.js +16 -16
  4. package/dist/account/ownership.js.map +1 -1
  5. package/dist/account/persistence.js +24 -74
  6. package/dist/account/persistence.js.map +1 -1
  7. package/dist/account/temporary-authentication.js +5 -3
  8. package/dist/account/temporary-authentication.js.map +1 -1
  9. package/dist/configuration.js +50 -13
  10. package/dist/configuration.js.map +1 -1
  11. package/dist/device/member-evidence.js +11 -4
  12. package/dist/device/member-evidence.js.map +1 -1
  13. package/dist/device/member-trust.js +14 -32
  14. package/dist/device/member-trust.js.map +1 -1
  15. package/dist/device/snapshot.js +6 -18
  16. package/dist/device/snapshot.js.map +1 -1
  17. package/dist/diagnostics.js +951 -334
  18. package/dist/diagnostics.js.map +1 -1
  19. package/dist/homekit/adapter.js +4 -1
  20. package/dist/homekit/adapter.js.map +1 -1
  21. package/dist/homekit/adapters/battery.js +3 -3
  22. package/dist/homekit/adapters/battery.js.map +1 -1
  23. package/dist/homekit/adapters/camera-controls.js +15 -37
  24. package/dist/homekit/adapters/camera-controls.js.map +1 -1
  25. package/dist/homekit/adapters/camera-streaming.js +74 -48
  26. package/dist/homekit/adapters/camera-streaming.js.map +1 -1
  27. package/dist/homekit/adapters/contact.js +5 -5
  28. package/dist/homekit/adapters/contact.js.map +1 -1
  29. package/dist/homekit/adapters/doorbell.js +3 -15
  30. package/dist/homekit/adapters/doorbell.js.map +1 -1
  31. package/dist/homekit/adapters/lock.js +72 -221
  32. package/dist/homekit/adapters/lock.js.map +1 -1
  33. package/dist/homekit/adapters/motion.js +3 -3
  34. package/dist/homekit/adapters/motion.js.map +1 -1
  35. package/dist/homekit/adapters/package-sensor.js +63 -0
  36. package/dist/homekit/adapters/package-sensor.js.map +1 -0
  37. package/dist/homekit/adapters/registry.js +2 -0
  38. package/dist/homekit/adapters/registry.js.map +1 -1
  39. package/dist/homekit/adapters/security-system.js +106 -250
  40. package/dist/homekit/adapters/security-system.js.map +1 -1
  41. package/dist/homekit/adapters/siren.js +5 -33
  42. package/dist/homekit/adapters/siren.js.map +1 -1
  43. package/dist/homekit/adapters/smart-light.js +19 -217
  44. package/dist/homekit/adapters/smart-light.js.map +1 -1
  45. package/dist/homekit/coverage-matrix.js +8 -67
  46. package/dist/homekit/coverage-matrix.js.map +1 -1
  47. package/dist/homekit/device-control.js +249 -13
  48. package/dist/homekit/device-control.js.map +1 -1
  49. package/dist/homekit/reconciler.js +25 -9
  50. package/dist/homekit/reconciler.js.map +1 -1
  51. package/dist/media/last-successful-image.js +8 -23
  52. package/dist/media/last-successful-image.js.map +1 -1
  53. package/dist/media/live-preview.js +217 -0
  54. package/dist/media/live-preview.js.map +1 -0
  55. package/dist/media/live-stream.js +689 -160
  56. package/dist/media/live-stream.js.map +1 -1
  57. package/dist/media/recording.js +41 -118
  58. package/dist/media/recording.js.map +1 -1
  59. package/dist/media/snapshot.js +22 -17
  60. package/dist/media/snapshot.js.map +1 -1
  61. package/dist/media/station-live-sessions.js +40 -51
  62. package/dist/media/station-live-sessions.js.map +1 -1
  63. package/dist/platform.js +61 -10
  64. package/dist/platform.js.map +1 -1
  65. package/dist/runtime/channel.js +227 -40
  66. package/dist/runtime/channel.js.map +1 -1
  67. package/dist/runtime/device-settings.js +88 -0
  68. package/dist/runtime/device-settings.js.map +1 -0
  69. package/dist/runtime/owner.js +30 -5
  70. package/dist/runtime/owner.js.map +1 -1
  71. package/dist/runtime/sdk-client.js +21 -17
  72. package/dist/runtime/sdk-client.js.map +1 -1
  73. package/dist/runtime/tracker.js +8 -38
  74. package/dist/runtime/tracker.js.map +1 -1
  75. package/dist/storage.js +1 -1
  76. package/dist/storage.js.map +1 -1
  77. package/dist/ui/dashboard.js +36 -16
  78. package/dist/ui/dashboard.js.map +1 -1
  79. package/dist/ui/runtime-channel-client.js +155 -184
  80. package/dist/ui/runtime-channel-client.js.map +1 -1
  81. package/dist/ui/server.js +81 -38
  82. package/dist/ui/server.js.map +1 -1
  83. package/homebridge-ui/public/app.css +531 -239
  84. package/homebridge-ui/public/assets/icons/auto_fix_high.svg +1 -0
  85. package/homebridge-ui/public/assets/icons/battery_0.svg +1 -0
  86. package/homebridge-ui/public/assets/icons/battery_1.svg +1 -0
  87. package/homebridge-ui/public/assets/icons/battery_2.svg +1 -0
  88. package/homebridge-ui/public/assets/icons/battery_3.svg +1 -0
  89. package/homebridge-ui/public/assets/icons/battery_4.svg +1 -0
  90. package/homebridge-ui/public/assets/icons/battery_5.svg +1 -0
  91. package/homebridge-ui/public/assets/icons/battery_6.svg +1 -0
  92. package/homebridge-ui/public/assets/icons/battery_full.svg +1 -0
  93. package/homebridge-ui/public/assets/icons/contact_support.svg +1 -0
  94. package/homebridge-ui/public/assets/icons/delete.svg +1 -0
  95. package/homebridge-ui/public/assets/icons/download.svg +1 -0
  96. package/homebridge-ui/public/assets/icons/extension_off.svg +1 -0
  97. package/homebridge-ui/public/assets/icons/info.svg +1 -0
  98. package/homebridge-ui/public/assets/icons/key_off.svg +1 -0
  99. package/homebridge-ui/public/assets/icons/keyboard_arrow_left.svg +1 -0
  100. package/homebridge-ui/public/assets/icons/keyboard_arrow_right.svg +1 -0
  101. package/homebridge-ui/public/assets/icons/keyboard_double_arrow_left.svg +1 -0
  102. package/homebridge-ui/public/assets/icons/keyboard_double_arrow_right.svg +1 -0
  103. package/homebridge-ui/public/assets/icons/movie_off.svg +1 -0
  104. package/homebridge-ui/public/assets/icons/play_arrow.svg +1 -0
  105. package/homebridge-ui/public/assets/icons/refresh.svg +1 -0
  106. package/homebridge-ui/public/assets/icons/satellite_alt.svg +1 -0
  107. package/homebridge-ui/public/assets/icons/search_off.svg +1 -0
  108. package/homebridge-ui/public/assets/icons/sensors_off.svg +1 -0
  109. package/homebridge-ui/public/assets/icons/settings_photo_camera.svg +1 -0
  110. package/homebridge-ui/public/assets/icons/solar_power.svg +1 -0
  111. package/homebridge-ui/public/assets/icons/stop.svg +1 -0
  112. package/homebridge-ui/public/assets/icons/videocam_off.svg +1 -0
  113. package/homebridge-ui/public/i18n/en.json +160 -82
  114. package/homebridge-ui/public/i18n/fr.json +161 -83
  115. package/homebridge-ui/public/index.html +225 -96
  116. package/homebridge-ui/public/js/app.js +814 -435
  117. package/homebridge-ui/public/js/dashboard.js +148 -31
  118. package/i18n/runtime/en.json +10 -3
  119. package/package.json +10 -11
  120. package/homebridge-ui/public/js/legacy-settings.js +0 -37
  121. package/homebridge-ui/public/js/profile-wizard.js +0 -61
@@ -1,88 +1,76 @@
1
1
  /**
2
- * Which claim holds each station's one live channel, and who yields to whom.
2
+ * The claims served over a connection of their own, which therefore contend with nothing on the station.
3
3
  *
4
- * A HomeBase fans several cameras over one session and serves them ONE at a time, and the SDK refuses a second
5
- * camera rather than admitting it and degrading both. Deciding which camera deserves the station is this
6
- * plugin's, because it depends on what HomeKit shows at once and on what the operator is looking at, neither of
7
- * which the SDK can know. A standalone camera is its own station and contends with nobody.
8
- *
9
- * The order is `live`, then `recording`, then `snapshot`:
4
+ * A live view and a recording each get their own connection to the station, so both run at full rate together.
5
+ * A still opens none: it rides the station's own session and takes it from whatever that session carries, so it
6
+ * is the one claim that stands aside and the one claim that is asked to.
7
+ */
8
+ const CONTINUOUS = new Set(['live', 'recording']);
9
+ /**
10
+ * The one registry of the work each station's own session is carrying, keyed by station serial.
10
11
  *
11
- * - A live view is on a screen now. Jitter there is the one degradation nobody can absorb, and an operator
12
- * who opened a camera is telling us which one matters.
13
- * - A recording writes to a file, so it survives being interrupted less well than being jittery, but it is
14
- * not free to abandon the way a still is: a missed event cannot be re-taken.
15
- * - A still fills a tile that is off screen exactly while a live view is on it, and re-running it costs
16
- * nobody anything. Where it cannot run, the last good image stands in.
12
+ * Both sides of the question read it: HomeKit records a live view and a recording on their camera's station,
13
+ * and snapshot acquisition asks whether a station is carrying anything before opening a burst on it.
17
14
  *
18
- * A stronger claim ASKS the weaker holders to yield rather than seizing the station: each holder registered how
19
- * to abandon its own work, and abandoning is what frees the channel the SDK will otherwise refuse. A holder
20
- * that registered no way to yield is left alone, so nothing is dropped that cannot be stopped cleanly.
15
+ * A still fills a tile that is off screen exactly while continuous work is running, re-running it costs nobody
16
+ * anything, and the last good image stands in where it cannot run — so it defers and nothing defers to it. A
17
+ * still asks a holder to yield rather than seizing the station: each holder registered how to abandon its own
18
+ * work, and a holder that registered none is left alone.
21
19
  *
22
20
  * None of it applies WITHIN one camera. Every egress on a camera shares one pull, so a recording and a live
23
- * view of the same camera are served together and neither yields to the other. That is what a motion
24
- * notification produces once the operator taps the tile, and it is the common shape rather than the exception.
25
- */
26
- const CLAIM_RANK = { live: 3, recording: 2, snapshot: 1 };
27
- /**
28
- * The one registry of live sessions a station is serving, keyed by station serial.
29
- *
30
- * Both sides of the question read it: HomeKit records a live session on its camera's station, and snapshot
31
- * acquisition asks whether a station is already serving one before opening a burst on it.
21
+ * view of the same camera are served together and neither yields to the other.
32
22
  */
33
23
  export class StationLiveSessions {
24
+ decided;
34
25
  sessions = new Map();
35
- /** How many stations are currently holding at least one session. */
36
- get held() {
37
- return this.sessions.size;
38
- }
39
- /** The strongest claim currently held on `stationSn`, or `undefined` where nothing holds it. */
40
- heldFor(stationSn) {
41
- let strongest;
42
- for (const session of this.sessions.get(stationSn) ?? []) {
43
- if (strongest === undefined || CLAIM_RANK[session.claim] > CLAIM_RANK[strongest]) {
44
- strongest = session.claim;
45
- }
46
- }
47
- return strongest;
26
+ constructor(decided = () => undefined) {
27
+ this.decided = decided;
48
28
  }
49
29
  /**
50
30
  * Whether `claim` may take this station now.
51
31
  *
52
- * Equal claims do not displace each other: a second live view does not evict the first, and the SDK refuses
53
- * it, which is the honest answer for a station that cannot serve both.
32
+ * A continuous pull is never refused: it opens a connection of its own. A still is refused while any other
33
+ * camera holds the station, including for another still, because a capture rides the station's own session.
54
34
  */
55
35
  admits(stationSn, camera, claim) {
56
- let strongestElsewhere;
36
+ let holderElsewhere;
57
37
  for (const session of this.sessions.get(stationSn) ?? []) {
58
38
  if (session.camera === camera) {
59
39
  return true;
60
40
  }
61
- if (strongestElsewhere === undefined || CLAIM_RANK[session.claim] > CLAIM_RANK[strongestElsewhere]) {
62
- strongestElsewhere = session.claim;
41
+ if (holderElsewhere === undefined || CONTINUOUS.has(session.claim)) {
42
+ holderElsewhere = session.claim;
63
43
  }
64
44
  }
65
- return strongestElsewhere === undefined || CLAIM_RANK[claim] > CLAIM_RANK[strongestElsewhere];
45
+ if (CONTINUOUS.has(claim) || holderElsewhere === undefined) {
46
+ return true;
47
+ }
48
+ this.decided({ action: 'refused', claim, by: holderElsewhere });
49
+ return false;
66
50
  }
67
51
  /**
68
- * Record one session on `stationSn`, asking anything weaker to yield first, and answer the release that ends
69
- * it.
52
+ * Record one session on `stationSn`, asking any still on another camera to yield first, and answer the
53
+ * release that ends it.
70
54
  *
71
55
  * `abandon` is how this session gives the station back before it would have finished. It is called at most
72
56
  * once, and never on the session that is taking the station.
73
57
  */
74
58
  hold(stationSn, camera, claim, abandon) {
75
- const yielding = [...(this.sessions.get(stationSn) ?? [])].filter((session) => session.camera !== camera && CLAIM_RANK[claim] > CLAIM_RANK[session.claim]);
59
+ const yielding = CONTINUOUS.has(claim)
60
+ ? [...(this.sessions.get(stationSn) ?? [])].filter((session) => session.camera !== camera && !CONTINUOUS.has(session.claim))
61
+ : [];
76
62
  const session = abandon ? { camera, claim, abandon } : { camera, claim };
77
63
  const held = this.sessions.get(stationSn) ?? new Set();
78
64
  held.add(session);
79
65
  this.sessions.set(stationSn, held);
80
- for (const weaker of yielding) {
81
- if (weaker.asked) {
66
+ this.decided({ action: 'held', claim });
67
+ for (const standing of yielding) {
68
+ if (standing.asked) {
82
69
  continue;
83
70
  }
84
- weaker.asked = true;
85
- weaker.abandon?.();
71
+ standing.asked = true;
72
+ this.decided({ action: 'yielded', claim: standing.claim, to: claim });
73
+ standing.abandon?.();
86
74
  }
87
75
  let released = false;
88
76
  return () => {
@@ -90,6 +78,7 @@ export class StationLiveSessions {
90
78
  return;
91
79
  }
92
80
  released = true;
81
+ this.decided({ action: 'released', claim });
93
82
  const remaining = this.sessions.get(stationSn);
94
83
  remaining?.delete(session);
95
84
  if (remaining && remaining.size === 0) {
@@ -1 +1 @@
1
- {"version":3,"file":"station-live-sessions.js","sourceRoot":"","sources":["../../src/media/station-live-sessions.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"station-live-sessions.js","sourceRoot":"","sources":["../../src/media/station-live-sessions.ts"],"names":[],"mappings":"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"}
package/dist/platform.js CHANGED
@@ -1,10 +1,12 @@
1
- import { ffmpegPathSource, parseConfig } from './configuration.js';
2
- import { createDiagnosticLogger, DiagnosticConditions, recordFfmpegEnvironment, reportAdaptationNotice, reportDiscardedV4Settings, reportHomeKitEvent, unconfirmedWriteCondition, reportInvalidSnapshotCache, } from './diagnostics.js';
1
+ import { ffmpegPathSource, parseConfig, resolveLiveVideoSettings } from './configuration.js';
2
+ import { createDiagnosticLogger, DiagnosticConditions, recordFleet, recordHostEnvironment, reportAdaptationNotice, reportLivePreview, reportLiveVideoEncoders, reportHomeKitEvent, unconfirmedWriteCondition, reportRuntimeNotice, reportStationClaim, } from './diagnostics.js';
3
3
  import { deviceSnapshotLabel } from './device/snapshot.js';
4
4
  import { HomeKitReconciler } from './homekit/reconciler.js';
5
- import { FfmpegLiveMedia, resolveFfmpegIdentity } from './media/live-stream.js';
5
+ import { describeHomeKitRepresentation } from './homekit/representation.js';
6
+ import { FfmpegLiveMedia, resolveFfmpegIdentity, SMALL_VIDEO_PACKET_SIZE } from './media/live-stream.js';
6
7
  import { FfmpegRecordingMedia } from './media/recording.js';
7
8
  import { PersistedLastSuccessfulImages } from './media/last-successful-image.js';
9
+ import { startLivePreview } from './media/live-preview.js';
8
10
  import { SnapshotAcquisition } from './media/snapshot.js';
9
11
  import { DeclaredMediaSessionBudget } from './media/session-budget.js';
10
12
  import { StationLiveSessions } from './media/station-live-sessions.js';
@@ -18,6 +20,7 @@ export function createEufyPlatform(clientFactory, shutdownTimeoutMs = 10_000, si
18
20
  cachedAccessories = [];
19
21
  reconciler;
20
22
  unconfirmedWrites;
23
+ fleet;
21
24
  constructor(log, config, api) {
22
25
  const configuredConfig = parseConfig(config);
23
26
  const storageRoot = api.user ? resolveStorageRoot(api.user.storagePath()) : undefined;
@@ -30,24 +33,54 @@ export function createEufyPlatform(clientFactory, shutdownTimeoutMs = 10_000, si
30
33
  report: (notice) => reportAdaptationNotice(diagnosticLog, notice),
31
34
  };
32
35
  const liveMedia = configuredConfig.ffmpegPath
33
- ? new FfmpegLiveMedia(configuredConfig.ffmpegPath, adaptationDiagnostics)
36
+ ? new FfmpegLiveMedia(configuredConfig.ffmpegPath, adaptationDiagnostics, undefined, undefined, undefined, configuredConfig.smallVideoPackets ? SMALL_VIDEO_PACKET_SIZE : undefined, configuredConfig.liveVideoPassthrough, configuredConfig.ignoreHomeBitRate)
34
37
  : undefined;
35
38
  const recordingMedia = configuredConfig.ffmpegPath
36
39
  ? new FfmpegRecordingMedia(configuredConfig.ffmpegPath, adaptationDiagnostics)
37
40
  : undefined;
38
41
  const mediaBudget = new DeclaredMediaSessionBudget(configuredConfig.maxConcurrentMediaSessions);
39
- const stationLiveSessions = new StationLiveSessions();
42
+ const stationLiveSessions = new StationLiveSessions((decision) => reportStationClaim(diagnosticLog, decision));
40
43
  const snapshotMedia = new SnapshotAcquisition(storageRoot
41
- ? new PersistedLastSuccessfulImages(storageRoot, () => reportInvalidSnapshotCache(diagnosticLog))
44
+ ? new PersistedLastSuccessfulImages(storageRoot, () => reportRuntimeNotice(diagnosticLog, 'camera-snapshot-cache-invalid'))
42
45
  : undefined, mediaBudget, undefined, undefined, stationLiveSessions);
43
46
  if (configuredConfig.discardedV4Settings.length > 0 && !configuredConfig.discardedV4Acknowledged) {
44
- reportDiscardedV4Settings(diagnosticLog);
47
+ reportRuntimeNotice(diagnosticLog, 'discarded-v4-settings-unacknowledged');
45
48
  }
46
49
  this.runtime = new RuntimeOwner(diagnosticLog, configuredConfig, clientFactory, {
47
50
  storageRoot,
48
51
  shutdownTimeoutMs,
52
+ conditions: () => diagnostics.current(),
53
+ livePreview: (device, adaptation, onPicture, onEnd) => {
54
+ const camera = device.camera?.();
55
+ const ffmpegPath = configuredConfig.ffmpegPath;
56
+ if (!ffmpegPath || !liveMedia || typeof camera?.live !== 'function')
57
+ return undefined;
58
+ const live = camera.live.bind(camera);
59
+ const claim = mediaBudget.claim();
60
+ if (!claim)
61
+ return undefined;
62
+ const releaseStation = stationLiveSessions.hold(device.stationSn, device.sn, 'live');
63
+ return startLivePreview(ffmpegPath, liveMedia, { live }, adaptation, onPicture, (result) => reportLivePreview(diagnosticLog, { ...result, accessory: diagnostics.aliasFor(device.sn) }), (unplayable) => {
64
+ claim.release();
65
+ releaseStation();
66
+ onEnd(unplayable);
67
+ }, adaptationDiagnostics);
68
+ },
49
69
  });
50
70
  this.runtime.subscribeState((state) => diagnostics.reportRuntimeState(state));
71
+ if (storageRoot) {
72
+ this.fleet ??= this.runtime.subscribeRegistry((view) => recordFleet(storageRoot, view.snapshot.devices.map((manifest) => {
73
+ const admission = describeHomeKitRepresentation(manifest);
74
+ const station = view.registry.get(manifest.sn)?.stationSn;
75
+ return {
76
+ accessory: diagnostics.aliasFor(manifest.sn) ?? 'accessory-unaliased',
77
+ ...(manifest.model === undefined ? {} : { model: manifest.model }),
78
+ represented: admission.represented,
79
+ attached: station !== undefined && station !== manifest.sn,
80
+ services: admission.services,
81
+ };
82
+ })));
83
+ }
51
84
  const signals = ['SIGHUP', 'SIGINT', 'SIGTERM'];
52
85
  let listeningForSignals = Boolean(signalTarget);
53
86
  const stop = () => {
@@ -71,12 +104,30 @@ export function createEufyPlatform(clientFactory, shutdownTimeoutMs = 10_000, si
71
104
  });
72
105
  api.on('didFinishLaunching', () => {
73
106
  const ffmpegPath = configuredConfig.ffmpegPath;
74
- if (ffmpegPath && storageRoot) {
75
- void resolveFfmpegIdentity(ffmpegPath, ffmpegPathSource(ffmpegPath)).then((identity) => recordFfmpegEnvironment(storageRoot, identity));
107
+ const qualification = ffmpegPath && liveMedia && configuredConfig.hardwareVideoEncoder
108
+ ? liveMedia.qualify({
109
+ platform: process.platform,
110
+ arch: process.arch,
111
+ configured: ffmpegPathSource(ffmpegPath) === 'configured',
112
+ })
113
+ : undefined;
114
+ void qualification?.then((encoders) => reportLiveVideoEncoders(diagnosticLog, encoders));
115
+ if (storageRoot) {
116
+ const homebridge = typeof api.serverVersion === 'string' ? { homebridge: api.serverVersion } : {};
117
+ recordHostEnvironment(storageRoot, homebridge);
118
+ if (ffmpegPath) {
119
+ void resolveFfmpegIdentity(ffmpegPath, ffmpegPathSource(ffmpegPath)).then(async (ffmpeg) => {
120
+ recordHostEnvironment(storageRoot, { ...homebridge, ffmpeg });
121
+ const encoders = await qualification;
122
+ if (encoders) {
123
+ recordHostEnvironment(storageRoot, { ...homebridge, ffmpeg: { ...ffmpeg, encoders } });
124
+ }
125
+ });
126
+ }
76
127
  }
77
128
  const accessoryStore = createAccessoryStore(api);
78
129
  if (accessoryStore) {
79
- this.reconciler ??= new HomeKitReconciler(this.runtime, accessoryStore, (diagnostic, affectedDeviceIds = []) => diagnostics.reportHomeKit(diagnostic, affectedDeviceIds), this.cachedAccessories, (trace) => reportHomeKitEvent(diagnosticLog, trace), configuredConfig.entityPreferences, liveMedia, snapshotMedia, recordingMedia, mediaBudget, stationLiveSessions);
130
+ this.reconciler ??= new HomeKitReconciler(this.runtime, accessoryStore, (diagnostic, affectedDeviceIds = []) => diagnostics.reportHomeKit(diagnostic, affectedDeviceIds), this.cachedAccessories, (trace) => reportHomeKitEvent(diagnosticLog, trace, (serial) => diagnostics.aliasFor(serial)), configuredConfig.entityPreferences, liveMedia, snapshotMedia, recordingMedia, mediaBudget, stationLiveSessions, configuredConfig.hdLiveVideo, (serial) => resolveLiveVideoSettings(configuredConfig, serial));
80
131
  this.reconciler.start();
81
132
  }
82
133
  void this.runtime.start();
@@ -1 +1 @@
1
- {"version":3,"file":"platform.js","sourceRoot":"","sources":["../src/platform.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"platform.js","sourceRoot":"","sources":["../src/platform.ts"],"names":[],"mappings":"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"}