v3_barrier_test.go 2.1 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374
  1. // Copyright 2016 CoreOS, Inc.
  2. //
  3. // Licensed under the Apache License, Version 2.0 (the "License");
  4. // you may not use this file except in compliance with the License.
  5. // You may obtain a copy of the License at
  6. //
  7. // http://www.apache.org/licenses/LICENSE-2.0
  8. //
  9. // Unless required by applicable law or agreed to in writing, software
  10. // distributed under the License is distributed on an "AS IS" BASIS,
  11. // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
  12. // See the License for the specific language governing permissions and
  13. // limitations under the License.package recipe
  14. package integration
  15. import (
  16. "testing"
  17. "time"
  18. "github.com/coreos/etcd/Godeps/_workspace/src/google.golang.org/grpc"
  19. "github.com/coreos/etcd/contrib/recipes"
  20. )
  21. func TestBarrierSingleNode(t *testing.T) {
  22. clus := newClusterGRPC(t, &clusterConfig{size: 3})
  23. defer clus.Terminate(t)
  24. testBarrier(t, 5, func() *grpc.ClientConn { return clus.conns[0] })
  25. }
  26. func TestBarrierMultiNode(t *testing.T) {
  27. clus := newClusterGRPC(t, &clusterConfig{size: 3})
  28. defer clus.Terminate(t)
  29. testBarrier(t, 5, func() *grpc.ClientConn { return clus.RandConn() })
  30. }
  31. func testBarrier(t *testing.T, waiters int, chooseConn func() *grpc.ClientConn) {
  32. b := recipe.NewBarrier(recipe.NewEtcdClient(chooseConn()), "test-barrier")
  33. if err := b.Hold(); err != nil {
  34. t.Fatalf("could not hold barrier (%v)", err)
  35. }
  36. if err := b.Hold(); err == nil {
  37. t.Fatalf("able to double-hold barrier")
  38. }
  39. donec := make(chan struct{})
  40. for i := 0; i < waiters; i++ {
  41. go func() {
  42. br := recipe.NewBarrier(recipe.NewEtcdClient(chooseConn()), "test-barrier")
  43. if err := br.Wait(); err != nil {
  44. t.Fatalf("could not wait on barrier (%v)", err)
  45. }
  46. donec <- struct{}{}
  47. }()
  48. }
  49. select {
  50. case <-donec:
  51. t.Fatalf("barrier did not wait")
  52. default:
  53. }
  54. if err := b.Release(); err != nil {
  55. t.Fatalf("could not release barrier (%v)", err)
  56. }
  57. timerC := time.After(time.Duration(waiters*100) * time.Millisecond)
  58. for i := 0; i < waiters; i++ {
  59. select {
  60. case <-timerC:
  61. t.Fatalf("barrier timed out")
  62. case <-donec:
  63. }
  64. }
  65. }