playlist retry-exhaustion handling
This commit is contained in:
@@ -7,10 +7,22 @@ import (
|
||||
"time"
|
||||
)
|
||||
|
||||
type PlaylistReadiness struct {
|
||||
type PlaylistEventKind uint8
|
||||
|
||||
const (
|
||||
PlaylistEventReady PlaylistEventKind = iota
|
||||
PlaylistEventFailed
|
||||
)
|
||||
|
||||
type PlaylistEvent struct {
|
||||
Revision uint64
|
||||
Kind PlaylistEventKind
|
||||
}
|
||||
|
||||
// PlaylistReadiness is retained as an alias for callers that only publish
|
||||
// ready events. Its zero Kind is PlaylistEventReady.
|
||||
type PlaylistReadiness = PlaylistEvent
|
||||
|
||||
type playlistTimer interface {
|
||||
C() <-chan time.Time
|
||||
Stop() bool
|
||||
@@ -162,6 +174,40 @@ func (c *PlaylistController) Run(
|
||||
readiness = nil
|
||||
continue
|
||||
}
|
||||
if ready.Kind == PlaylistEventFailed {
|
||||
if ready.Revision != revision {
|
||||
continue
|
||||
}
|
||||
stopTimer()
|
||||
// A failed entry must not retain a live or apparently active
|
||||
// duration clock, even when the policy is to wait.
|
||||
timing = NewPlaylistTiming(revision, timing.Duration)
|
||||
if c.playlist.OnFailure != PlaylistFailureNext {
|
||||
c.publish(state, revision, timing)
|
||||
continue
|
||||
}
|
||||
next, sessionCommand, apply, err := ApplyPlaylistSelection(
|
||||
c.playlist,
|
||||
state,
|
||||
PlaylistCommand{Kind: PlaylistNext},
|
||||
c.retry,
|
||||
)
|
||||
if err != nil || !apply {
|
||||
c.publish(state, revision, timing)
|
||||
continue
|
||||
}
|
||||
select {
|
||||
case <-ctx.Done():
|
||||
return ctx.Err()
|
||||
case c.sessions <- sessionCommand:
|
||||
}
|
||||
revision++
|
||||
state = next
|
||||
entry, _ := next.Entry(c.playlist)
|
||||
timing = NewPlaylistTiming(revision, entry.Duration)
|
||||
c.publish(state, revision, timing)
|
||||
continue
|
||||
}
|
||||
if timing.Paused &&
|
||||
ready.Revision == timing.Revision &&
|
||||
timing.Duration > 0 &&
|
||||
|
||||
Reference in New Issue
Block a user