Fix incorrect handling of gen.SupervisorStrategyRestartTransient restart strategy
parent
ea6f5751c2
commit
2e85c20042
|
@ -225,7 +225,7 @@ func startChild(supervisor Process, name string, child ProcessBehavior, opts Pro
|
|||
process, err := supervisor.Spawn(name, opts, child, args...)
|
||||
|
||||
if err != nil {
|
||||
panic(err)
|
||||
panic(err.Error())
|
||||
}
|
||||
|
||||
supervisor.Link(process.Self())
|
||||
|
@ -321,13 +321,16 @@ func handleMessageExit(p Process, exit ProcessGracefulExitRequest, spec *Supervi
|
|||
}
|
||||
|
||||
spec.Children[i].process = nil
|
||||
if child.Self() == terminated {
|
||||
if haveToDisableChild(spec.Strategy.Restart, reason) {
|
||||
spec.Children[i].state = supervisorChildStateDisabled
|
||||
} else {
|
||||
spec.Children[i].state = supervisorChildStateStart
|
||||
}
|
||||
if haveToDisableChild(spec.Strategy.Restart, reason) {
|
||||
spec.Children[i].state = supervisorChildStateDisabled
|
||||
break
|
||||
}
|
||||
|
||||
if spec.Children[i].state == supervisorChildStateDisabled {
|
||||
continue
|
||||
}
|
||||
spec.Children[i].state = supervisorChildStateStart
|
||||
if child.Self() == terminated {
|
||||
if len(spec.Children) == i+1 && len(wait) == 0 {
|
||||
// it was the last one. nothing to waiting for
|
||||
startChildren(p, spec)
|
||||
|
@ -335,11 +338,6 @@ func handleMessageExit(p Process, exit ProcessGracefulExitRequest, spec *Supervi
|
|||
continue
|
||||
}
|
||||
|
||||
if haveToDisableChild(spec.Strategy.Restart, "restart") {
|
||||
spec.Children[i].state = supervisorChildStateDisabled
|
||||
} else {
|
||||
spec.Children[i].state = supervisorChildStateStart
|
||||
}
|
||||
child.Exit("restart")
|
||||
|
||||
wait = append(wait, child.Self())
|
||||
|
@ -357,6 +355,7 @@ func handleMessageExit(p Process, exit ProcessGracefulExitRequest, spec *Supervi
|
|||
spec.Children[i].process = nil
|
||||
if haveToDisableChild(spec.Strategy.Restart, reason) {
|
||||
spec.Children[i].state = supervisorChildStateDisabled
|
||||
break
|
||||
} else {
|
||||
spec.Children[i].state = supervisorChildStateStart
|
||||
}
|
||||
|
@ -421,6 +420,18 @@ func handleMessageExit(p Process, exit ProcessGracefulExitRequest, spec *Supervi
|
|||
}
|
||||
}
|
||||
}
|
||||
// check if all children are disabled. stop this process with reason "normal"
|
||||
shouldStop := true
|
||||
for i := range spec.Children {
|
||||
if spec.Children[i].state == supervisorChildStateDisabled {
|
||||
continue
|
||||
}
|
||||
shouldStop = false
|
||||
break
|
||||
}
|
||||
if shouldStop {
|
||||
p.Exit("normal")
|
||||
}
|
||||
return wait
|
||||
}
|
||||
|
||||
|
|
|
@ -196,7 +196,6 @@ func (tr *testRaft) HandleSerial(process *gen.RaftProcess, ref etf.Ref, serial u
|
|||
return gen.RaftStatusOK
|
||||
}
|
||||
func (tr *testRaft) HandleCancel(process *gen.RaftProcess, ref etf.Ref, reason string) gen.RaftStatus {
|
||||
fmt.Println("CCC cancel", ref, reason)
|
||||
return gen.RaftStatusOK
|
||||
}
|
||||
|
||||
|
|
|
@ -157,8 +157,8 @@ func TestSupervisorOneForAll(t *testing.T) {
|
|||
testCases = []ChildrenTestCase{
|
||||
{
|
||||
reason: "normal",
|
||||
statuses: []string{"empty", "new", "new"},
|
||||
events: 5, // waiting for 3 terminates and 2 starts
|
||||
statuses: []string{"empty", "old", "old"},
|
||||
events: 1, // waiting for 1 terminate
|
||||
},
|
||||
{
|
||||
reason: "abnormal",
|
||||
|
@ -167,12 +167,12 @@ func TestSupervisorOneForAll(t *testing.T) {
|
|||
},
|
||||
{
|
||||
reason: "shutdown",
|
||||
statuses: []string{"empty", "new", "empty"},
|
||||
events: 3, // waiting for 2 terminates and 1 start
|
||||
statuses: []string{"empty", "old", "empty"},
|
||||
events: 1, // waiting for 1 terminate
|
||||
},
|
||||
}
|
||||
for i := range children {
|
||||
fmt.Printf("... stopping child %d with '%s' reason and waiting for restarting all of them ... ", i+1, testCases[i].reason)
|
||||
fmt.Printf("... stopping child %d with '%s' reason and waiting for restarting all of them if reason != normal ... ", i+1, testCases[i].reason)
|
||||
processSV.Send(children[i], testCases[i].reason) // stopping child
|
||||
|
||||
if children1, err := waitNeventsSupervisorChildren(sv.ch, testCases[i].events, children); err != nil {
|
||||
|
@ -213,18 +213,18 @@ func TestSupervisorOneForAll(t *testing.T) {
|
|||
testCases = []ChildrenTestCase{
|
||||
{
|
||||
reason: "normal",
|
||||
statuses: []string{"empty", "empty", "empty"},
|
||||
events: 3, // waiting for 3 terminates
|
||||
statuses: []string{"empty", "old", "old"},
|
||||
events: 1, // waiting for 1 terminate
|
||||
},
|
||||
{
|
||||
reason: "abnormal",
|
||||
statuses: []string{"empty", "empty", "empty"},
|
||||
events: 3, // waiting for 3 terminates
|
||||
statuses: []string{"old", "empty", "old"},
|
||||
events: 1, // waiting for 1 terminate
|
||||
},
|
||||
{
|
||||
reason: "shutdown",
|
||||
statuses: []string{"empty", "empty", "empty"},
|
||||
events: 3, // waiting for 3 terminate
|
||||
statuses: []string{"old", "old", "empty"},
|
||||
events: 1, // waiting for 1 terminate
|
||||
},
|
||||
}
|
||||
|
||||
|
@ -241,7 +241,7 @@ func TestSupervisorOneForAll(t *testing.T) {
|
|||
fmt.Println("OK")
|
||||
}
|
||||
|
||||
fmt.Printf("... stopping child %d with '%s' reason and waiting for restarting all of them ... ", i+1, testCases[i].reason)
|
||||
fmt.Printf("... stopping child %d with '%s' reason and no one should be restarted ... ", i+1, testCases[i].reason)
|
||||
processSV.Send(children[i], testCases[i].reason) // stopping child
|
||||
|
||||
if children1, err := waitNeventsSupervisorChildren(sv.ch, testCases[i].events, children); err != nil {
|
||||
|
@ -258,7 +258,7 @@ func TestSupervisorOneForAll(t *testing.T) {
|
|||
|
||||
fmt.Printf("Stopping supervisor 'testSupervisorTemporary' (%s)... ", gen.SupervisorStrategyRestartTemporary)
|
||||
processSV.Exit("x")
|
||||
if children1, err := waitNeventsSupervisorChildren(sv.ch, 0, children); err != nil {
|
||||
if children1, err := waitNeventsSupervisorChildren(sv.ch, len(children)-testCases[i].events, children); err != nil {
|
||||
t.Fatal(err)
|
||||
} else {
|
||||
statuses := []string{"empty", "empty", "empty"}
|
||||
|
|
|
@ -165,8 +165,8 @@ func TestSupervisorRestForOne(t *testing.T) {
|
|||
},
|
||||
{
|
||||
reason: "normal",
|
||||
statuses: []string{"old", "empty", "new"},
|
||||
events: 3, // waiting for 2 terminates and 1 starts
|
||||
statuses: []string{"old", "empty", "old"},
|
||||
events: 1, // waiting for 1 terminate
|
||||
},
|
||||
{
|
||||
reason: "shutdown",
|
||||
|
@ -175,7 +175,7 @@ func TestSupervisorRestForOne(t *testing.T) {
|
|||
},
|
||||
}
|
||||
for i := range children {
|
||||
fmt.Printf("... stopping child %d with '%s' reason and waiting for restarting rest of them ... ", i+1, testCases[i].reason)
|
||||
fmt.Printf("... stopping child %d with '%s' reason and waiting for restarting if reason != normal ... ", i+1, testCases[i].reason)
|
||||
processSV.Send(children[i], testCases[i].reason) // stopping child
|
||||
|
||||
if children1, err := waitNeventsSupervisorChildren(sv.ch, testCases[i].events, children); err != nil {
|
||||
|
@ -216,13 +216,13 @@ func TestSupervisorRestForOne(t *testing.T) {
|
|||
testCases = []ChildrenTestCase{
|
||||
{
|
||||
reason: "normal",
|
||||
statuses: []string{"empty", "empty", "empty"},
|
||||
events: 3, // waiting for 3 terminates
|
||||
statuses: []string{"empty", "old", "old"},
|
||||
events: 1, // waiting for 1 terminate
|
||||
},
|
||||
{
|
||||
reason: "abnormal",
|
||||
statuses: []string{"old", "empty", "empty"},
|
||||
events: 2, // waiting for 2 terminates
|
||||
statuses: []string{"old", "empty", "old"},
|
||||
events: 1, // waiting for 1 terminate
|
||||
},
|
||||
{
|
||||
reason: "shutdown",
|
||||
|
|
Loading…
Reference in New Issue