29d3c533aa
gates / gates (push) Successful in 28s
Red-proofs RP43, RP44. MinAgent 0.131.0 (unchanged). Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_0159rPz1ZhFKsS53msqPYxtS
37 lines
1.1 KiB
Go
37 lines
1.1 KiB
Go
package backup
|
|
|
|
import (
|
|
"io"
|
|
"log"
|
|
"path/filepath"
|
|
"testing"
|
|
)
|
|
|
|
type stoppedStarter struct {
|
|
fakeStarter
|
|
stopped map[string]bool
|
|
}
|
|
|
|
func (s *stoppedStarter) WantsStopped(n string) bool { return s.stopped[n] }
|
|
|
|
// R-721 (v0.283.1): a controller crash during a volume dump leaves a marker owing the app a restart; if the
|
|
// household pressed Stop meanwhile, the startup recovery does not start it — and the marker still clears.
|
|
// COMPANION RED-PROOF: remove the WantsStopped skip in Recover → started=[immich].
|
|
func TestR721_CrashRecoveryKeepsTheHouseholdsStop(t *testing.T) {
|
|
dir := t.TempDir()
|
|
g1, _ := newGuard(t, dir)
|
|
if err := g1.Begin("volume-dump:immich", ReasonVolumeDump, []string{"immich"}); err != nil {
|
|
t.Fatal(err)
|
|
}
|
|
s := &stoppedStarter{stopped: map[string]bool{"immich": true}}
|
|
g2 := NewAppStopGuard(filepath.Join(dir, "appstop-state.json"), log.New(io.Discard, "", 0))
|
|
g2.SetStarter(s)
|
|
g2.Recover()
|
|
if len(s.starts) != 0 {
|
|
t.Fatalf("the crash recovery started %v — the household stopped it (R-721)", s.starts)
|
|
}
|
|
if markerExists(t, dir) {
|
|
t.Fatal("the marker survived — the next boot would try again")
|
|
}
|
|
}
|