bugfix-4
All checks were successful
release-tag / release-image (push) Successful in 1m57s

This commit is contained in:
2025-09-21 19:36:17 +02:00
parent 6882453b6a
commit f62d7e62c5

View File

@@ -1,4 +1,4 @@
(function(){ (function () {
const name = document.documentElement.dataset.stream; const name = document.documentElement.dataset.stream;
const v = document.getElementById('v'); const v = document.getElementById('v');
const liveEl = document.getElementById('live'); const liveEl = document.getElementById('live');
@@ -7,72 +7,73 @@
const manifest = '/hls/' + encodeURIComponent(name) + '/index.m3u8'; const manifest = '/hls/' + encodeURIComponent(name) + '/index.m3u8';
function setLive(l){ function setLive(on){
liveEl.className = 'pill ' + (l ? 'live' : 'off'); liveEl.className = 'pill ' + (on ? 'live' : 'off');
liveEl.textContent = l ? 'LIVE' : 'Offline'; liveEl.textContent = on ? 'LIVE' : 'Offline';
} }
async function head(url){ async function head(u){
try { try { const r = await fetch(u, {method:'HEAD', cache:'no-store'}); return r.ok; }
const r = await fetch(url, { method: 'HEAD', cache:'no-store' }); catch { return false; }
return r.ok;
} catch (_) { return false; }
} }
async function tryInitPlayer(){ async function initPlayer() {
// 1) Manifest erreichbar?
const ok = await head(manifest);
srcEl.textContent = manifest; srcEl.textContent = manifest;
const ok = await head(manifest);
setLive(ok); setLive(ok);
if (!ok) return false; if (!ok) return false;
// 2) Player initialisieren // Autoplay-Chance verbessern
try { try { v.muted = true; } catch(_) {}
if (window.Hls && Hls.isSupported()) { try { v.playsInline = true; } catch(_) {}
if (!window._hls) {
window._hls = new Hls({ maxLiveSyncPlaybackRate: 1.0 }); if (window.Hls && Hls.isSupported()) {
window._hls.on(Hls.Events.ERROR, (_, data)=>console.warn('hls.js error', data)); if (!window._hls) {
window._hls.attachMedia(v); window._hls = new Hls({ liveDurationInfinity: true });
} window._hls.on(Hls.Events.MANIFEST_PARSED, (_e, data) => {
window._hls.loadSource(manifest); console.log('HLS manifest parsed. levels=', data.levels?.length);
} else if (v.canPlayType('application/vnd.apple.mpegurl')) { });
v.src = manifest; // Safari / iOS window._hls.on(Hls.Events.ERROR, (_e, data) => {
} else { console.warn('hls.js error', data);
console.warn('HLS nicht unterstützt'); });
return false; window._hls.attachMedia(v);
} }
return true; window._hls.loadSource(manifest);
} catch (e) { } else if (v.canPlayType('application/vnd.apple.mpegurl')) {
console.warn('Player init fail', e); v.src = manifest; // Safari / iOS
} else {
console.warn('HLS nicht unterstützt');
return false; return false;
} }
// Autoplay versuchen (wird bei Desktop-Browsern oft blockiert; Controls bleiben)
try { await v.play(); } catch(e) { console.log('autoplay blockiert (ok):', e?.name||e); }
return true;
} }
async function refreshMeta(){ async function refreshMeta(){
// UI-Infos (viewer count etc.) optional, darf nie Player blockieren
try { try {
const r = await fetch('/api/streams', { cache:'no-store' }); const r = await fetch('/api/streams', {cache:'no-store'});
if (!r.ok) return; if (!r.ok) return;
const d = await r.json(); const d = await r.json();
const it = d.items.find(x=>x.name===name); const it = d.items.find(x => x.name === name);
if (it) { if (it) {
setLive(!!it.live); setLive(!!it.live);
viewersEl.textContent = 'Zuschauer: ' + it.viewers; viewersEl.textContent = 'Zuschauer: ' + it.viewers;
} }
} catch (_) {} } catch {}
} }
// Video-Fehler sichtbar loggen v.addEventListener('error', e => console.warn('video error', e));
v.addEventListener('error', (e)=>console.warn('video error', e)); v.addEventListener('loadedmetadata', () => console.log('loadedmetadata'));
v.addEventListener('loadedmetadata', ()=>console.log('metadata loaded')); v.addEventListener('playing', () => console.log('playing'));
v.addEventListener('playing', ()=>console.log('playing'));
// Boot-Sequenz mit Retries
(async function boot(){ (async function boot(){
for (let i=0; i<10; i++) { for (let i=0; i<10; i++) {
const ok = await tryInitPlayer(); const ok = await initPlayer();
if (ok) break; if (ok) break;
await new Promise(r=>setTimeout(r, 1500)); // kurz warten, bis HLS bereit ist await new Promise(r => setTimeout(r, 1500));
} }
refreshMeta(); refreshMeta();
setInterval(refreshMeta, 2500); setInterval(refreshMeta, 2500);