0.2.64 update
This commit is contained in:
@@ -0,0 +1,56 @@
|
||||
package credits
|
||||
|
||||
import "sync"
|
||||
|
||||
// A minimal single-flight, because four signals can name the same episode.
|
||||
//
|
||||
// Live playback, a predicted next episode, another viewer's prediction and a refresh cycle
|
||||
// all legitimately want the same media version at the same moment, and each of them arriving
|
||||
// as its own scan is the one way this subsystem could become expensive. The queue already
|
||||
// deduplicates by item; this closes the gap for anything that reaches Process directly — a
|
||||
// forced scan from the console, the benchmark, or a live push racing the worker.
|
||||
//
|
||||
// Written rather than taken from golang.org/x/sync so the gateway keeps its two direct
|
||||
// dependencies. It is thirty lines and the semantics are not subtle: the first caller does
|
||||
// the work, everybody else waits and receives the same answer.
|
||||
type flightGroup struct {
|
||||
mu sync.Mutex
|
||||
calls map[string]*flightCall
|
||||
}
|
||||
|
||||
type flightCall struct {
|
||||
done chan struct{}
|
||||
value any
|
||||
err error
|
||||
}
|
||||
|
||||
func newFlightGroup() *flightGroup {
|
||||
return &flightGroup{calls: map[string]*flightCall{}}
|
||||
}
|
||||
|
||||
// Do runs fn unless an identical key is already in flight, in which case it waits for that
|
||||
// one and returns its result.
|
||||
func (g *flightGroup) Do(key string, fn func() (any, error)) (any, error) {
|
||||
g.mu.Lock()
|
||||
if existing, found := g.calls[key]; found {
|
||||
g.mu.Unlock()
|
||||
<-existing.done
|
||||
return existing.value, existing.err
|
||||
}
|
||||
call := &flightCall{done: make(chan struct{})}
|
||||
g.calls[key] = call
|
||||
g.mu.Unlock()
|
||||
|
||||
// The deferred cleanup matters more than it looks: a detector that panics must not leave
|
||||
// a key permanently in flight, which would make that episode unscannable for the life of
|
||||
// the process and give every later caller a channel that never closes.
|
||||
defer func() {
|
||||
g.mu.Lock()
|
||||
delete(g.calls, key)
|
||||
g.mu.Unlock()
|
||||
close(call.done)
|
||||
}()
|
||||
|
||||
call.value, call.err = fn()
|
||||
return call.value, call.err
|
||||
}
|
||||
Reference in New Issue
Block a user