Merge pull request #12121 from hashicorp/jbardin/dag-tests

Fix some intermittent dag test failures
This commit is contained in:
James Bardin 2017-02-21 11:14:07 -05:00 committed by GitHub
commit be5230c673
1 changed files with 144 additions and 138 deletions

View File

@ -92,19 +92,31 @@ func TestWalker_error(t *testing.T) {
} }
func TestWalker_newVertex(t *testing.T) { func TestWalker_newVertex(t *testing.T) {
// Run it a bunch of times since it is timing dependent
for i := 0; i < 50; i++ {
var g AcyclicGraph var g AcyclicGraph
g.Add(1) g.Add(1)
g.Add(2) g.Add(2)
g.Connect(BasicEdge(1, 2)) g.Connect(BasicEdge(1, 2))
// Record function
var order []interface{} var order []interface{}
w := &Walker{Callback: walkCbRecord(&order)} recordF := walkCbRecord(&order)
done2 := make(chan int)
// Build a callback that notifies us when 2 has been walked
var w *Walker
cb := func(v Vertex) error {
if v == 2 {
defer close(done2)
}
return recordF(v)
}
// Add the initial vertices
w = &Walker{Callback: cb}
w.Update(&g) w.Update(&g)
// Wait a bit // if 2 has been visited, the walk is complete so far
time.Sleep(10 * time.Millisecond) <-done2
// Update the graph // Update the graph
g.Add(3) g.Add(3)
@ -125,11 +137,8 @@ func TestWalker_newVertex(t *testing.T) {
t.Fatalf("bad: %#v", order) t.Fatalf("bad: %#v", order)
} }
} }
}
func TestWalker_removeVertex(t *testing.T) { func TestWalker_removeVertex(t *testing.T) {
// Run it a bunch of times since it is timing dependent
for i := 0; i < 50; i++ {
var g AcyclicGraph var g AcyclicGraph
g.Add(1) g.Add(1)
g.Add(2) g.Add(2)
@ -139,7 +148,6 @@ func TestWalker_removeVertex(t *testing.T) {
var order []interface{} var order []interface{}
recordF := walkCbRecord(&order) recordF := walkCbRecord(&order)
// Build a callback that delays until we close a channel
var w *Walker var w *Walker
cb := func(v Vertex) error { cb := func(v Vertex) error {
if v == 1 { if v == 1 {
@ -165,11 +173,8 @@ func TestWalker_removeVertex(t *testing.T) {
t.Fatalf("bad: %#v", order) t.Fatalf("bad: %#v", order)
} }
} }
}
func TestWalker_newEdge(t *testing.T) { func TestWalker_newEdge(t *testing.T) {
// Run it a bunch of times since it is timing dependent
for i := 0; i < 50; i++ {
var g AcyclicGraph var g AcyclicGraph
g.Add(1) g.Add(1)
g.Add(2) g.Add(2)
@ -179,16 +184,18 @@ func TestWalker_newEdge(t *testing.T) {
var order []interface{} var order []interface{}
recordF := walkCbRecord(&order) recordF := walkCbRecord(&order)
// Build a callback that delays until we close a channel
var w *Walker var w *Walker
cb := func(v Vertex) error { cb := func(v Vertex) error {
// record where we are first, otherwise the Updated vertex may get
// walked before the first visit.
err := recordF(v)
if v == 1 { if v == 1 {
g.Add(3) g.Add(3)
g.Connect(BasicEdge(3, 2)) g.Connect(BasicEdge(3, 2))
w.Update(&g) w.Update(&g)
} }
return err
return recordF(v)
} }
// Add the initial vertices // Add the initial vertices
@ -206,16 +213,14 @@ func TestWalker_newEdge(t *testing.T) {
t.Fatalf("bad: %#v", order) t.Fatalf("bad: %#v", order)
} }
} }
}
func TestWalker_removeEdge(t *testing.T) { func TestWalker_removeEdge(t *testing.T) {
// Run it a bunch of times since it is timing dependent
for i := 0; i < 50; i++ {
var g AcyclicGraph var g AcyclicGraph
g.Add(1) g.Add(1)
g.Add(2) g.Add(2)
g.Add(3) g.Add(3)
g.Connect(BasicEdge(1, 2)) g.Connect(BasicEdge(1, 2))
g.Connect(BasicEdge(1, 3))
g.Connect(BasicEdge(3, 2)) g.Connect(BasicEdge(3, 2))
// Record function // Record function
@ -232,16 +237,18 @@ func TestWalker_removeEdge(t *testing.T) {
var w *Walker var w *Walker
gateCh := make(chan struct{}) gateCh := make(chan struct{})
cb := func(v Vertex) error { cb := func(v Vertex) error {
if v == 1 { switch v {
case 1:
g.RemoveEdge(BasicEdge(3, 2)) g.RemoveEdge(BasicEdge(3, 2))
w.Update(&g) w.Update(&g)
}
if v == 2 { case 2:
close(gateCh) // this visit isn't completed until we've recorded it
} // Once the visit is official, we can then close the gate to
// let 3 continue.
defer close(gateCh)
if v == 3 { case 3:
select { select {
case <-gateCh: case <-gateCh:
case <-time.After(50 * time.Millisecond): case <-time.After(50 * time.Millisecond):
@ -267,7 +274,6 @@ func TestWalker_removeEdge(t *testing.T) {
t.Fatalf("bad: %#v", order) t.Fatalf("bad: %#v", order)
} }
} }
}
// walkCbRecord is a test helper callback that just records the order called. // walkCbRecord is a test helper callback that just records the order called.
func walkCbRecord(order *[]interface{}) WalkFunc { func walkCbRecord(order *[]interface{}) WalkFunc {