Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(156)

Side by Side Diff: common/clock/testclock/testclock_test.go

Issue 1679023005: Add Context cancellation to clock. (Closed) Base URL: https://github.com/luci/luci-go@master
Patch Set: Cleanup memlock, restore old determinism, better name. Created 4 years, 10 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
OLDNEW
1 // Copyright 2015 The Chromium Authors. All rights reserved. 1 // Copyright 2015 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be 2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file. 3 // found in the LICENSE file.
4 4
5 package testclock 5 package testclock
6 6
7 import ( 7 import (
8 "fmt"
9 "strings"
10 "sync"
8 "testing" 11 "testing"
9 "time" 12 "time"
10 13
11 "github.com/luci/luci-go/common/clock" 14 "github.com/luci/luci-go/common/clock"
12 . "github.com/smartystreets/goconvey/convey" 15 . "github.com/smartystreets/goconvey/convey"
16 "golang.org/x/net/context"
13 ) 17 )
14 18
19 // trashTimer is a useless implementation of clock.Timer specifically designed
20 // to exist and not be a test timer type.
21 type trashTimer struct {
22 clock.Timer
23 }
24
15 func TestTestClock(t *testing.T) { 25 func TestTestClock(t *testing.T) {
16 t.Parallel() 26 t.Parallel()
17 27
18 Convey(`A testing clock instance`, t, func() { 28 Convey(`A testing clock instance`, t, func() {
19 now := time.Date(2015, 01, 01, 00, 00, 00, 00, time.UTC) 29 now := time.Date(2015, 01, 01, 00, 00, 00, 00, time.UTC)
20 c := New(now) 30 c := New(now)
31 ctx := context.Background()
21 32
22 Convey(`Returns the current time.`, func() { 33 Convey(`Returns the current time.`, func() {
23 So(c.Now(), ShouldResemble, now) 34 So(c.Now(), ShouldResemble, now)
24 }) 35 })
25 36
26 Convey(`When sleeping with a time of zero, immediately awakens.` , func() { 37 Convey(`When sleeping with a time of zero, immediately awakens.` , func() {
27 » » » c.Sleep(0) 38 » » » c.Sleep(ctx, 0)
28 So(c.Now(), ShouldResemble, now) 39 So(c.Now(), ShouldResemble, now)
29 }) 40 })
30 41
42 Convey(`Will panic if going backwards in time.`, func() {
43 So(func() { c.Add(-1 * time.Second) }, ShouldPanic)
44 })
45
31 Convey(`When sleeping for a period of time, awakens when signall ed.`, func() { 46 Convey(`When sleeping for a period of time, awakens when signall ed.`, func() {
32 sleepingC := make(chan struct{}) 47 sleepingC := make(chan struct{})
33 c.SetTimerCallback(func(_ time.Duration, _ clock.Timer) { 48 c.SetTimerCallback(func(_ time.Duration, _ clock.Timer) {
34 close(sleepingC) 49 close(sleepingC)
35 }) 50 })
36 51
37 awakeC := make(chan time.Time) 52 awakeC := make(chan time.Time)
38 go func() { 53 go func() {
39 » » » » c.Sleep(2 * time.Second) 54 » » » » c.Sleep(ctx, 2*time.Second)
40 awakeC <- c.Now() 55 awakeC <- c.Now()
41 }() 56 }()
42 57
43 <-sleepingC 58 <-sleepingC
44 c.Set(now.Add(1 * time.Second)) 59 c.Set(now.Add(1 * time.Second))
45 c.Set(now.Add(2 * time.Second)) 60 c.Set(now.Add(2 * time.Second))
46 So(<-awakeC, ShouldResemble, now.Add(2*time.Second)) 61 So(<-awakeC, ShouldResemble, now.Add(2*time.Second))
47 }) 62 })
48 63
49 Convey(`Awakens after a period of time.`, func() { 64 Convey(`Awakens after a period of time.`, func() {
50 » » » afterC := c.After(2 * time.Second) 65 » » » afterC := c.After(ctx, 2*time.Second)
51 66
52 c.Set(now.Add(1 * time.Second)) 67 c.Set(now.Add(1 * time.Second))
53 c.Set(now.Add(2 * time.Second)) 68 c.Set(now.Add(2 * time.Second))
54 » » » So(<-afterC, ShouldResemble, now.Add(2*time.Second)) 69 » » » So(<-afterC, ShouldResemble, clock.TimerResult{now.Add(2 * time.Second), nil})
70 » » })
71
72 » » Convey(`When sleeping, awakens if canceled.`, func() {
73 » » » ctx, cancelFunc := context.WithCancel(ctx)
74
75 » » » c.SetTimerCallback(func(_ time.Duration, _ clock.Timer) {
76 » » » » cancelFunc()
77 » » » })
78
79 » » » So(c.Sleep(ctx, time.Second), ShouldEqual, context.Cance led)
80 » » })
81
82 » » Convey(`Can set and retrieve timer tags.`, func() {
83 » » » var tagMu sync.Mutex
84 » » » tagMap := map[string]struct{}{}
85
86 » » » // On the last timer callback, advance time past the tim er threshold.
87 » » » timers := make([]clock.Timer, 10)
88 » » » count := 0
89 » » » c.SetTimerCallback(func(_ time.Duration, t clock.Timer) {
90 » » » » tagMu.Lock()
91 » » » » defer tagMu.Unlock()
92
93 » » » » tagMap[strings.Join(GetTags(t), "")] = struct{}{ }
94 » » » » count++
95 » » » » if count == len(timers) {
96 » » » » » c.Add(time.Second)
97 » » » » }
98 » » » })
99
100 » » » for i := range timers {
101 » » » » t := c.NewTimer(clock.Tag(ctx, fmt.Sprintf("%d", i)))
102 » » » » t.Reset(time.Second)
103 » » » » timers[i] = t
104 » » » }
105
106 » » » // Wait until all timers have expired.
107 » » » for _, t := range timers {
108 » » » » <-t.GetC()
109 » » » }
110
111 » » » // Did we see all of their tags?
112 » » » for i := range timers {
113 » » » » _, ok := tagMap[fmt.Sprintf("%d", i)]
114 » » » » So(ok, ShouldBeTrue)
115 » » » }
116 » » })
117
118 » » Convey(`A non-test timer has a nil tag.`, func() {
119 » » » t := trashTimer{}
120 » » » So(GetTags(t), ShouldBeNil)
55 }) 121 })
56 }) 122 })
57 } 123 }
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698