Merge lp:~axwalk/juju-core/lp1319652-instancepoller-testbatching into lp:~go-bot/juju-core/trunk

Proposed by Andrew Wilkins
Status: Merged
Approved by: Andrew Wilkins
Approved revision: no longer in the source branch.
Merged at revision: 2747
Proposed branch: lp:~axwalk/juju-core/lp1319652-instancepoller-testbatching
Merge into: lp:~go-bot/juju-core/trunk
Diff against target: 82 lines (+46/-24)
1 file modified
worker/instancepoller/aggregate_test.go (+46/-24)
To merge this branch: bzr merge lp:~axwalk/juju-core/lp1319652-instancepoller-testbatching
Reviewer Review Type Date Requested Status
Juju Engineering Pending
Review via email: mp+220014@code.launchpad.net

Commit message

worker/instancepoller: TestBatching less race-y

The existing TestBatching test was very prone to
failure due to the nature of the test. The test
ensures that requests to Instances are batched
using a token bucket.

Whereas the existing test streamed requests, the
new implementation compresses the addition of
requests into the point where we service an
Instances call. We can thus reliably determine
the number of batches that will be made, as calls
to Instances must complete before additional
requests are gathered.

Fixes lp:1319652

https://codereview.appspot.com/96440043/

Description of the change

worker/instancepoller: TestBatching less race-y

The existing TestBatching test was very prone to
failure due to the nature of the test. The test
ensures that requests to Instances are batched
using a token bucket.

Whereas the existing test streamed requests, the
new implementation compresses the addition of
requests into the point where we service an
Instances call. We can thus reliably determine
the number of batches that will be made, as calls
to Instances must complete before additional
requests are gathered.

Fixes lp:1319652

https://codereview.appspot.com/96440043/

To post a comment you must log in.
Revision history for this message
Andrew Wilkins (axwalk) wrote :
Download full text (3.7 KiB)

Reviewers: mp+220014_code.launchpad.net,

Message:
Please take a look.

Description:
worker/instancepoller: TestBatching less race-y

The existing TestBatching test was very prone to
failure due to the nature of the test. The test
ensures that requests to Instances are batched
using a token bucket.

Whereas the existing test streamed requests, the
new implementation compresses the addition of
requests into the point where we service an
Instances call. We can thus reliably determine
the number of batches that will be made, as calls
to Instances must complete before additional
requests are gathered.

Fixes lp:1319652

https://code.launchpad.net/~axwalk/juju-core/lp1319652-instancepoller-testbatching/+merge/220014

(do not edit description out of merge proposal)

Please review this at https://codereview.appspot.com/96440043/

Affected files (+48, -24 lines):
   A [revision details]
   M worker/instancepoller/aggregate_test.go

Index: [revision details]
=== added file '[revision details]'
--- [revision details] 2012-01-01 00:00:00 +0000
+++ [revision details] 2012-01-01 00:00:00 +0000
@@ -0,0 +1,2 @@
+Old revision: tarmac-20140519073812-9ribeb9ud0q2glco
+New revision: <email address hidden>

Index: worker/instancepoller/aggregate_test.go
=== modified file 'worker/instancepoller/aggregate_test.go'
--- worker/instancepoller/aggregate_test.go 2014-05-13 06:12:51 +0000
+++ worker/instancepoller/aggregate_test.go 2014-05-19 11:11:39 +0000
@@ -116,32 +116,54 @@
   c.Assert(len(testGetter.ids), gc.DeepEquals, 2)
  }

+type batchingInstanceGetter struct {
+ testInstanceGetter
+ wg sync.WaitGroup
+ aggregator *aggregator
+ batchSize int
+ started int
+}
+
+func (g *batchingInstanceGetter) Instances(ids []instance.Id)
([]instance.Instance, error) {
+ insts, err := g.testInstanceGetter.Instances(ids)
+ g.startRequests()
+ return insts, err
+}
+
+func (g *batchingInstanceGetter) startRequests() {
+ n := len(g.results) - g.started
+ if n > g.batchSize {
+ n = g.batchSize
+ }
+ for i := 0; i < n; i++ {
+ g.startRequest()
+ }
+}
+
+func (g *batchingInstanceGetter) startRequest() {
+ g.started++
+ go func() {
+ _, err := g.aggregator.instanceInfo("foo")
+ if err != nil {
+ panic(err)
+ }
+ g.wg.Done()
+ }()
+}
+
  func (s *aggregateSuite) TestBatching(c *gc.C) {
   s.PatchValue(&gatherTime, 10*time.Millisecond)
- testGetter := new(testInstanceGetter)
-
- aggregator := newAggregator(testGetter)
- for i := 0; i < 100; i++ {
- testGetter.results = append(testGetter.results,
newTestInstance("foobar", []string{"127.0.0.1", "192.168.1.1"}))
- }
- var wg sync.WaitGroup
- makeRequest := func() {
- _, err := aggregator.instanceInfo("foo")
- c.Check(err, gc.IsNil)
- wg.Done()
- }
- startTime := time.Now()
- wg.Add(100)
- for i := 0; i < 100; i++ {
- go makeRequest()
- time.Sleep(time.Millisecond)
- }
- wg.Wait()
- totalTime := time.Now().Sub(startTime)
- // +1 because we expect one extra call for the first request
- expectedMax := int32((totalTime / (10 * time.Millisecond)) + 1)
- c.Assert(testGetter.counter, jc.LessThan, expectedMax+1)
- c.Assert(testGetter.counter, jc.GreaterThan, 10)
+ var testGetter...

Read more...

Revision history for this message
Ian Booth (wallyworld) wrote :

Preview Diff

[H/L] Next/Prev Comment, [J/K] Next/Prev File, [N/P] Next/Prev Hunk
=== modified file 'worker/instancepoller/aggregate_test.go'
--- worker/instancepoller/aggregate_test.go 2014-05-13 06:12:51 +0000
+++ worker/instancepoller/aggregate_test.go 2014-05-19 11:20:56 +0000
@@ -116,32 +116,54 @@
116 c.Assert(len(testGetter.ids), gc.DeepEquals, 2)116 c.Assert(len(testGetter.ids), gc.DeepEquals, 2)
117}117}
118118
119type batchingInstanceGetter struct {
120 testInstanceGetter
121 wg sync.WaitGroup
122 aggregator *aggregator
123 batchSize int
124 started int
125}
126
127func (g *batchingInstanceGetter) Instances(ids []instance.Id) ([]instance.Instance, error) {
128 insts, err := g.testInstanceGetter.Instances(ids)
129 g.startRequests()
130 return insts, err
131}
132
133func (g *batchingInstanceGetter) startRequests() {
134 n := len(g.results) - g.started
135 if n > g.batchSize {
136 n = g.batchSize
137 }
138 for i := 0; i < n; i++ {
139 g.startRequest()
140 }
141}
142
143func (g *batchingInstanceGetter) startRequest() {
144 g.started++
145 go func() {
146 _, err := g.aggregator.instanceInfo("foo")
147 if err != nil {
148 panic(err)
149 }
150 g.wg.Done()
151 }()
152}
153
119func (s *aggregateSuite) TestBatching(c *gc.C) {154func (s *aggregateSuite) TestBatching(c *gc.C) {
120 s.PatchValue(&gatherTime, 10*time.Millisecond)155 s.PatchValue(&gatherTime, 10*time.Millisecond)
121 testGetter := new(testInstanceGetter)156 var testGetter batchingInstanceGetter
122157 testGetter.aggregator = newAggregator(&testGetter)
123 aggregator := newAggregator(testGetter)158 testGetter.results = make([]instance.Instance, 100)
124 for i := 0; i < 100; i++ {159 for i := range testGetter.results {
125 testGetter.results = append(testGetter.results, newTestInstance("foobar", []string{"127.0.0.1", "192.168.1.1"}))160 testGetter.results[i] = newTestInstance("foobar", []string{"127.0.0.1", "192.168.1.1"})
126 }161 }
127 var wg sync.WaitGroup162 testGetter.batchSize = 10
128 makeRequest := func() {163 testGetter.wg.Add(len(testGetter.results))
129 _, err := aggregator.instanceInfo("foo")164 testGetter.startRequest()
130 c.Check(err, gc.IsNil)165 testGetter.wg.Wait()
131 wg.Done()166 c.Assert(testGetter.counter, gc.Equals, int32(len(testGetter.results)/testGetter.batchSize)+1)
132 }
133 startTime := time.Now()
134 wg.Add(100)
135 for i := 0; i < 100; i++ {
136 go makeRequest()
137 time.Sleep(time.Millisecond)
138 }
139 wg.Wait()
140 totalTime := time.Now().Sub(startTime)
141 // +1 because we expect one extra call for the first request
142 expectedMax := int32((totalTime / (10 * time.Millisecond)) + 1)
143 c.Assert(testGetter.counter, jc.LessThan, expectedMax+1)
144 c.Assert(testGetter.counter, jc.GreaterThan, 10)
145}167}
146168
147func (s *aggregateSuite) TestError(c *gc.C) {169func (s *aggregateSuite) TestError(c *gc.C) {

Subscribers

People subscribed via source and target branches

to status/vote changes: