1
// Copyright 2015 Canonical Ltd.
2
// Licensed under the AGPLv3, see LICENCE file for details.
9
"github.com/juju/errors"
10
"github.com/juju/testing"
11
jc "github.com/juju/testing/checkers"
12
gc "gopkg.in/check.v1"
14
corelease "github.com/juju/juju/core/lease"
15
coretesting "github.com/juju/juju/testing"
16
"github.com/juju/juju/worker/lease"
19
type ExpireSuite struct {
20
testing.IsolationSuite
23
var _ = gc.Suite(&ExpireSuite{})
25
func (s *ExpireSuite) TestStartup_ExpiryInPast(c *gc.C) {
27
leases: map[string]corelease.Info{
28
"redis": corelease.Info{Expiry: offset(-time.Second)},
33
method: "ExpireLease",
34
args: []interface{}{"redis"},
35
callback: func(leases map[string]corelease.Info) {
36
delete(leases, "redis")
40
fix.RunTest(c, func(_ *lease.Manager, _ *coretesting.Clock) {})
43
func (s *ExpireSuite) TestStartup_ExpiryInFuture(c *gc.C) {
45
leases: map[string]corelease.Info{
46
"redis": corelease.Info{Expiry: offset(time.Second)},
49
fix.RunTest(c, func(_ *lease.Manager, clock *coretesting.Clock) {
50
clock.Advance(almostSeconds(1))
54
func (s *ExpireSuite) TestStartup_ExpiryInFuture_TimePasses(c *gc.C) {
56
leases: map[string]corelease.Info{
57
"redis": corelease.Info{Expiry: offset(time.Second)},
62
method: "ExpireLease",
63
args: []interface{}{"redis"},
64
callback: func(leases map[string]corelease.Info) {
65
delete(leases, "redis")
69
fix.RunTest(c, func(_ *lease.Manager, clock *coretesting.Clock) {
70
clock.Advance(time.Second)
74
func (s *ExpireSuite) TestStartup_NoExpiry_NotLongEnough(c *gc.C) {
76
fix.RunTest(c, func(_ *lease.Manager, clock *coretesting.Clock) {
77
clock.Advance(almostSeconds(3600))
81
func (s *ExpireSuite) TestStartup_NoExpiry_LongEnough(c *gc.C) {
83
leases: map[string]corelease.Info{
84
"goose": corelease.Info{Expiry: offset(3 * time.Hour)},
88
callback: func(leases map[string]corelease.Info) {
89
leases["redis"] = corelease.Info{
90
Expiry: offset(time.Minute),
94
method: "ExpireLease",
95
args: []interface{}{"redis"},
96
callback: func(leases map[string]corelease.Info) {
97
delete(leases, "redis")
101
fix.RunTest(c, func(_ *lease.Manager, clock *coretesting.Clock) {
102
clock.Advance(time.Hour)
106
func (s *ExpireSuite) TestExpire_ErrInvalid_Expired(c *gc.C) {
108
leases: map[string]corelease.Info{
109
"redis": corelease.Info{Expiry: offset(time.Second)},
111
expectCalls: []call{{
114
method: "ExpireLease",
115
args: []interface{}{"redis"},
116
err: corelease.ErrInvalid,
117
callback: func(leases map[string]corelease.Info) {
118
delete(leases, "redis")
122
fix.RunTest(c, func(_ *lease.Manager, clock *coretesting.Clock) {
123
clock.Advance(time.Second)
127
func (s *ExpireSuite) TestExpire_ErrInvalid_Updated(c *gc.C) {
129
leases: map[string]corelease.Info{
130
"redis": corelease.Info{Expiry: offset(time.Second)},
132
expectCalls: []call{{
135
method: "ExpireLease",
136
args: []interface{}{"redis"},
137
err: corelease.ErrInvalid,
138
callback: func(leases map[string]corelease.Info) {
139
leases["redis"] = corelease.Info{Expiry: offset(time.Minute)}
143
fix.RunTest(c, func(_ *lease.Manager, clock *coretesting.Clock) {
144
clock.Advance(time.Second)
148
func (s *ExpireSuite) TestExpire_OtherError(c *gc.C) {
150
leases: map[string]corelease.Info{
151
"redis": corelease.Info{Expiry: offset(time.Second)},
153
expectCalls: []call{{
156
method: "ExpireLease",
157
args: []interface{}{"redis"},
158
err: errors.New("snarfblat hobalob"),
162
fix.RunTest(c, func(manager *lease.Manager, clock *coretesting.Clock) {
163
clock.Advance(time.Second)
164
err := manager.Wait()
165
c.Check(err, gc.ErrorMatches, "snarfblat hobalob")
169
func (s *ExpireSuite) TestClaim_ExpiryInFuture(c *gc.C) {
171
expectCalls: []call{{
172
method: "ClaimLease",
173
args: []interface{}{"redis", corelease.Request{"redis/0", time.Minute}},
174
callback: func(leases map[string]corelease.Info) {
175
leases["redis"] = corelease.Info{
177
Expiry: offset(63 * time.Second),
182
fix.RunTest(c, func(manager *lease.Manager, clock *coretesting.Clock) {
183
// Ask for a minute, actually get 63s. Don't expire early.
184
err := manager.Claim("redis", "redis/0", time.Minute)
185
c.Assert(err, jc.ErrorIsNil)
186
clock.Advance(almostSeconds(63))
190
func (s *ExpireSuite) TestClaim_ExpiryInFuture_TimePasses(c *gc.C) {
192
expectCalls: []call{{
193
method: "ClaimLease",
194
args: []interface{}{"redis", corelease.Request{"redis/0", time.Minute}},
195
callback: func(leases map[string]corelease.Info) {
196
leases["redis"] = corelease.Info{
198
Expiry: offset(63 * time.Second),
204
method: "ExpireLease",
205
args: []interface{}{"redis"},
206
callback: func(leases map[string]corelease.Info) {
207
delete(leases, "redis")
211
fix.RunTest(c, func(manager *lease.Manager, clock *coretesting.Clock) {
212
// Ask for a minute, actually get 63s. Expire on time.
213
err := manager.Claim("redis", "redis/0", time.Minute)
214
c.Assert(err, jc.ErrorIsNil)
215
clock.Advance(63 * time.Second)
219
func (s *ExpireSuite) TestExtend_ExpiryInFuture(c *gc.C) {
221
leases: map[string]corelease.Info{
222
"redis": corelease.Info{
224
Expiry: offset(time.Second),
227
expectCalls: []call{{
228
method: "ExtendLease",
229
args: []interface{}{"redis", corelease.Request{"redis/0", time.Minute}},
230
callback: func(leases map[string]corelease.Info) {
231
leases["redis"] = corelease.Info{
233
Expiry: offset(63 * time.Second),
238
fix.RunTest(c, func(manager *lease.Manager, clock *coretesting.Clock) {
239
// Ask for a minute, actually get 63s. Don't expire early.
240
err := manager.Claim("redis", "redis/0", time.Minute)
241
c.Assert(err, jc.ErrorIsNil)
242
clock.Advance(almostSeconds(63))
246
func (s *ExpireSuite) TestExtend_ExpiryInFuture_TimePasses(c *gc.C) {
248
leases: map[string]corelease.Info{
249
"redis": corelease.Info{
251
Expiry: offset(time.Second),
254
expectCalls: []call{{
255
method: "ExtendLease",
256
args: []interface{}{"redis", corelease.Request{"redis/0", time.Minute}},
257
callback: func(leases map[string]corelease.Info) {
258
leases["redis"] = corelease.Info{
260
Expiry: offset(63 * time.Second),
266
method: "ExpireLease",
267
args: []interface{}{"redis"},
268
callback: func(leases map[string]corelease.Info) {
269
delete(leases, "redis")
273
fix.RunTest(c, func(manager *lease.Manager, clock *coretesting.Clock) {
274
// Ask for a minute, actually get 63s. Expire on time.
275
err := manager.Claim("redis", "redis/0", time.Minute)
276
c.Assert(err, jc.ErrorIsNil)
277
clock.Advance(63 * time.Second)
281
func (s *ExpireSuite) TestExpire_Multiple(c *gc.C) {
283
leases: map[string]corelease.Info{
284
"redis": corelease.Info{
286
Expiry: offset(time.Second),
288
"store": corelease.Info{
290
Expiry: offset(5 * time.Second),
292
"tokumx": corelease.Info{
294
Expiry: offset(10 * time.Second), // will not expire.
296
"ultron": corelease.Info{
298
Expiry: offset(5 * time.Second),
300
"vvvvvv": corelease.Info{
302
Expiry: offset(time.Second), // would expire, but errors first.
305
expectCalls: []call{{
308
method: "ExpireLease",
309
args: []interface{}{"redis"},
310
callback: func(leases map[string]corelease.Info) {
311
delete(leases, "redis")
314
method: "ExpireLease",
315
args: []interface{}{"store"},
316
err: corelease.ErrInvalid,
317
callback: func(leases map[string]corelease.Info) {
318
delete(leases, "store")
321
method: "ExpireLease",
322
args: []interface{}{"ultron"},
323
err: errors.New("what is this?"),
327
fix.RunTest(c, func(manager *lease.Manager, clock *coretesting.Clock) {
328
clock.Advance(5 * time.Second)
329
err := manager.Wait()
330
c.Check(err, gc.ErrorMatches, "what is this\\?")