Web changes: Split shared helpers, bootstrap logic, route groups, and upload-sync behavior out of web.js. Kept web.js focused on wiring and server startup. Fixed screen playlist reassignment so changing a screen’s playlist now triggers a refresh. Fixed single-slide playlist refresh behavior so updates do not get stuck behind the current slide. Player changes: Split websocket/runtime handling into runtime.js. Split playlist assembly and revision hashing into playlist.js. Split onboarding and player HTTP routes into dedicated modules. Split render utilities and template loading into render-helpers.js. Kept player.js mostly as startup/orchestration. Validation: Rebuilt both services with Docker Compose. Smoke-checked web and player routes after the refactor. Verified get_errors was clean on the touched modules.
99 lines
3.2 KiB
HTML
99 lines
3.2 KiB
HTML
<script>
|
|
let onboardingClientName = null;
|
|
let onboardingClientNameSyncPromise = null;
|
|
const onboardingClientNameStorageKey = 'pulse-signage-player-client-name';
|
|
const onboardingDeviceIdStorageKey = 'pulse-signage-player-device-id';
|
|
|
|
function getOnboardingDeviceId() {
|
|
try {
|
|
var storedDeviceId = window.localStorage.getItem(onboardingDeviceIdStorageKey) || '';
|
|
return String(storedDeviceId || '').trim();
|
|
} catch (_error) {
|
|
return '';
|
|
}
|
|
}
|
|
|
|
// Return the onboarding client name when one was assigned, otherwise a stable client id.
|
|
function getOnboardingClientName() {
|
|
if (onboardingClientName) {
|
|
return onboardingClientName;
|
|
}
|
|
try {
|
|
var storedClientName = window.localStorage.getItem(onboardingClientNameStorageKey);
|
|
if (storedClientName) {
|
|
onboardingClientName = storedClientName;
|
|
try {
|
|
window.localStorage.setItem('pulse-signage-player-client-name', storedClientName);
|
|
} catch (_mirrorError) {
|
|
// ignore storage errors
|
|
}
|
|
return onboardingClientName;
|
|
}
|
|
var genericClientName = window.localStorage.getItem('pulse-signage-player-client-name');
|
|
if (genericClientName) {
|
|
onboardingClientName = genericClientName;
|
|
try {
|
|
window.localStorage.setItem(onboardingClientNameStorageKey, genericClientName);
|
|
} catch (_error) {
|
|
// ignore storage errors
|
|
}
|
|
return onboardingClientName;
|
|
}
|
|
} catch (_error) {
|
|
// fall through to client id generation
|
|
}
|
|
return '';
|
|
}
|
|
|
|
function applyOnboardingClientName(renamedClientName, socket) {
|
|
var normalizedName = String(renamedClientName || '').trim();
|
|
if (!normalizedName) {
|
|
return;
|
|
}
|
|
onboardingClientName = normalizedName;
|
|
try {
|
|
window.localStorage.setItem('pulse-signage-player-client-name', normalizedName);
|
|
window.localStorage.setItem(onboardingClientNameStorageKey, normalizedName);
|
|
} catch (_error) {
|
|
// ignore storage errors
|
|
}
|
|
if (socket && socket.readyState === WebSocket.OPEN) {
|
|
sendCommandHello(socket);
|
|
}
|
|
}
|
|
|
|
function syncOnboardingClientNameFromServer(socket) {
|
|
var deviceId = getOnboardingDeviceId();
|
|
if (!deviceId) {
|
|
return Promise.resolve(getOnboardingClientName());
|
|
}
|
|
|
|
if (onboardingClientNameSyncPromise) {
|
|
return onboardingClientNameSyncPromise;
|
|
}
|
|
|
|
onboardingClientNameSyncPromise = fetch('/api/onboarding/status?deviceId=' + encodeURIComponent(deviceId), {
|
|
cache: 'no-store'
|
|
}).then(function (response) {
|
|
if (!response.ok) {
|
|
return null;
|
|
}
|
|
return response.json().catch(function () {
|
|
return null;
|
|
});
|
|
}).then(function (payload) {
|
|
var serverName = payload && payload.clientName ? String(payload.clientName).trim() : '';
|
|
if (serverName) {
|
|
applyOnboardingClientName(serverName, null);
|
|
}
|
|
return onboardingClientName || getOnboardingClientName();
|
|
}).catch(function () {
|
|
return onboardingClientName || getOnboardingClientName();
|
|
}).finally(function () {
|
|
onboardingClientNameSyncPromise = null;
|
|
});
|
|
|
|
return onboardingClientNameSyncPromise;
|
|
}
|
|
</script>
|