直播观众:negotiate 失败后恢复轮询;防并发 poll;长时 502 提示

Made-with: Cursor
This commit is contained in:
whm
2026-03-25 16:55:05 +08:00
parent 7e24a965bc
commit da0bcae823

View File

@@ -47,6 +47,8 @@ export function startViewing(videoEl, opts = {}) {
let ws = null let ws = null
let pollTimer = null let pollTimer = null
let currentPollMs = pollMs let currentPollMs = pollMs
let pollInFlight = false
let upstreamErrorStreak = 0
let stopped = false let stopped = false
let blackFrameTimer = null let blackFrameTimer = null
@@ -109,8 +111,12 @@ export function startViewing(videoEl, opts = {}) {
if (pollTimer) return if (pollTimer) return
rebuildPeer() rebuildPeer()
currentPollMs = pollMs currentPollMs = pollMs
upstreamErrorStreak = 0
schedulePollLoop() schedulePollLoop()
poll() // 下一轮再 poll避免从 poll() 内同步调用时 pollInFlight 仍为 true 导致被跳过
setTimeout(() => {
if (!stopped) poll()
}, 0)
} }
async function negotiate() { async function negotiate() {
@@ -173,10 +179,17 @@ export function startViewing(videoEl, opts = {}) {
async function poll() { async function poll() {
if (stopped) return if (stopped) return
if (pollInFlight) return
pollInFlight = true
try { try {
const { live, upstreamError } = await fetchLiveStatus() const { live, upstreamError } = await fetchLiveStatus()
if (upstreamError) { if (upstreamError) {
onStatus('无法连接服务器(网关 502/离线),将放慢重试…') upstreamErrorStreak += 1
const extra =
upstreamErrorStreak >= 6
? ' 若长时间如此,多为服务端未启动或网关异常,请刷新页面或联系管理员。'
: ''
onStatus(`无法连接服务器(网关 502/离线),将放慢重试…${extra}`)
const next = Math.min(Math.round(currentPollMs * 1.5), 30000) const next = Math.min(Math.round(currentPollMs * 1.5), 30000)
if (next !== currentPollMs) { if (next !== currentPollMs) {
currentPollMs = next currentPollMs = next
@@ -184,6 +197,7 @@ export function startViewing(videoEl, opts = {}) {
} }
return return
} }
upstreamErrorStreak = 0
if (currentPollMs !== pollMs) { if (currentPollMs !== pollMs) {
currentPollMs = pollMs currentPollMs = pollMs
schedulePollLoop() schedulePollLoop()
@@ -195,12 +209,23 @@ export function startViewing(videoEl, opts = {}) {
} }
onLive() onLive()
onStatus('检测到直播,正在连接…') onStatus('检测到直播,正在连接…')
try {
await negotiate() await negotiate()
} catch (err) {
onStatus(
err?.message
? `拉流连接失败:${err.message}`
: '拉流连接失败,将恢复轮询…'
)
resumePollingAfterDisconnect('')
}
return return
} }
onStatus('等待主播开播…') onStatus('等待主播开播…')
} catch { } catch {
onStatus('无法获取直播状态') onStatus('无法获取直播状态')
} finally {
pollInFlight = false
} }
} }