fix(19.7): RA-IN-04 the non-reserving store fallback writes the record first
For a store without Reserve (only a test wrapper reaches this; both shipped stores reserve), serveNew now calls Put right after the Count check and before the server is built, and a failed connect or initialize deletes the record again. The session is therefore never in the local map without its record, so a reaper pass in between cannot close it as expired. The cap of this fallback stays check-then-act, as its comment now says.
This commit is contained in:
@@ -146,7 +146,11 @@ func (sr *sessionRouter) serveNew(w http.ResponseWriter, r *http.Request, id Ide
|
||||
sid := rand.Text()
|
||||
rec := Record{Binding: id.Binding, Created: time.Now().UTC()}
|
||||
// The slot is reserved atomically before the server is built
|
||||
// (A-WR-03); a store without Reserve falls back to Count then Put.
|
||||
// (A-WR-03). A store without Reserve (only a test wrapper; both shipped
|
||||
// stores reserve) falls back to Count then Put, still before the server
|
||||
// is built, so the session is never in sr.local without its record (a
|
||||
// reaper pass would close it as expired); its cap stays check-then-act
|
||||
// (RA-IN-04).
|
||||
res, reserves := sr.p.store.(reserver)
|
||||
if reserves {
|
||||
ok, err := res.Reserve(ctx, id.Binding, sid, rec, sr.p.cfg.MaxPerBinding, sr.p.cfg.IdleTTL)
|
||||
@@ -168,6 +172,10 @@ func (sr *sessionRouter) serveNew(w http.ResponseWriter, r *http.Request, id Ide
|
||||
sr.tooMany(w)
|
||||
return
|
||||
}
|
||||
if err := sr.p.store.Put(ctx, sid, rec, sr.p.cfg.IdleTTL); err != nil {
|
||||
sr.p.storeUnavailable(w, err)
|
||||
return
|
||||
}
|
||||
}
|
||||
release := func() {
|
||||
if reserves {
|
||||
@@ -189,13 +197,6 @@ func (sr *sessionRouter) serveNew(w http.ResponseWriter, r *http.Request, id Ide
|
||||
sr.mu.Lock()
|
||||
sr.local[sid] = ls
|
||||
sr.mu.Unlock()
|
||||
if !reserves {
|
||||
if err := sr.p.store.Put(ctx, sid, rec, sr.p.cfg.IdleTTL); err != nil {
|
||||
sr.closeLocal(sid)
|
||||
sr.p.storeUnavailable(w, err)
|
||||
return
|
||||
}
|
||||
}
|
||||
logSession(logger(), "open", sid, id.Binding)
|
||||
ls.transport.ServeHTTP(w, r)
|
||||
if ls.ss.InitializeParams() == nil {
|
||||
|
||||
Reference in New Issue
Block a user