github.com/Pankov404/juju@v0.0.0-20150703034450-be266991dceb/state/leadership/manager_expire_test.go (about) 1 // Copyright 2015 Canonical Ltd. 2 // Licensed under the AGPLv3, see LICENCE file for details. 3 4 package leadership_test 5 6 import ( 7 "time" 8 9 "github.com/juju/errors" 10 "github.com/juju/testing" 11 jc "github.com/juju/testing/checkers" 12 gc "gopkg.in/check.v1" 13 14 "github.com/juju/juju/state/leadership" 15 "github.com/juju/juju/state/lease" 16 ) 17 18 type ExpireLeadershipSuite struct { 19 testing.IsolationSuite 20 } 21 22 var _ = gc.Suite(&ExpireLeadershipSuite{}) 23 24 func (s *ExpireLeadershipSuite) TestStartup_ExpiryInPast(c *gc.C) { 25 fix := &Fixture{ 26 leases: map[string]lease.Info{ 27 "redis": lease.Info{Expiry: offset(-time.Second)}, 28 }, 29 expectCalls: []call{{ 30 method: "ExpireLease", 31 args: []interface{}{"redis"}, 32 callback: func(leases map[string]lease.Info) { 33 delete(leases, "redis") 34 }, 35 }}, 36 } 37 fix.RunTest(c, func(_ leadership.ManagerWorker, _ *Clock) {}) 38 } 39 40 func (s *ExpireLeadershipSuite) TestStartup_ExpiryInFuture(c *gc.C) { 41 fix := &Fixture{ 42 leases: map[string]lease.Info{ 43 "redis": lease.Info{Expiry: offset(time.Second)}, 44 }, 45 } 46 fix.RunTest(c, func(_ leadership.ManagerWorker, clock *Clock) { 47 clock.Advance(almostSeconds(1)) 48 }) 49 } 50 51 func (s *ExpireLeadershipSuite) TestStartup_ExpiryInFuture_TimePasses(c *gc.C) { 52 fix := &Fixture{ 53 leases: map[string]lease.Info{ 54 "redis": lease.Info{Expiry: offset(time.Second)}, 55 }, 56 expectCalls: []call{{ 57 method: "ExpireLease", 58 args: []interface{}{"redis"}, 59 callback: func(leases map[string]lease.Info) { 60 delete(leases, "redis") 61 }, 62 }}, 63 } 64 fix.RunTest(c, func(_ leadership.ManagerWorker, clock *Clock) { 65 clock.Advance(time.Second) 66 }) 67 } 68 69 func (s *ExpireLeadershipSuite) TestExpire_ErrInvalid_Expired(c *gc.C) { 70 fix := &Fixture{ 71 leases: map[string]lease.Info{ 72 "redis": lease.Info{Expiry: offset(time.Second)}, 73 }, 74 expectCalls: []call{{ 75 method: "ExpireLease", 76 args: []interface{}{"redis"}, 77 err: lease.ErrInvalid, 78 callback: func(leases map[string]lease.Info) { 79 delete(leases, "redis") 80 }, 81 }}, 82 } 83 fix.RunTest(c, func(_ leadership.ManagerWorker, clock *Clock) { 84 clock.Advance(time.Second) 85 }) 86 } 87 88 func (s *ExpireLeadershipSuite) TestExpire_ErrInvalid_Updated(c *gc.C) { 89 fix := &Fixture{ 90 leases: map[string]lease.Info{ 91 "redis": lease.Info{Expiry: offset(time.Second)}, 92 }, 93 expectCalls: []call{{ 94 method: "ExpireLease", 95 args: []interface{}{"redis"}, 96 err: lease.ErrInvalid, 97 callback: func(leases map[string]lease.Info) { 98 leases["redis"] = lease.Info{Expiry: offset(time.Minute)} 99 }, 100 }}, 101 } 102 fix.RunTest(c, func(_ leadership.ManagerWorker, clock *Clock) { 103 clock.Advance(time.Second) 104 }) 105 } 106 107 func (s *ExpireLeadershipSuite) TestExpire_OtherError(c *gc.C) { 108 fix := &Fixture{ 109 leases: map[string]lease.Info{ 110 "redis": lease.Info{Expiry: offset(time.Second)}, 111 }, 112 expectCalls: []call{{ 113 method: "ExpireLease", 114 args: []interface{}{"redis"}, 115 err: errors.New("snarfblat hobalob"), 116 }}, 117 expectDirty: true, 118 } 119 fix.RunTest(c, func(manager leadership.ManagerWorker, clock *Clock) { 120 clock.Advance(time.Second) 121 err := manager.Wait() 122 c.Check(err, gc.ErrorMatches, "snarfblat hobalob") 123 }) 124 } 125 126 func (s *ExpireLeadershipSuite) TestClaim_ExpiryInFuture(c *gc.C) { 127 fix := &Fixture{ 128 expectCalls: []call{{ 129 method: "ClaimLease", 130 args: []interface{}{"redis", lease.Request{"redis/0", time.Minute}}, 131 callback: func(leases map[string]lease.Info) { 132 leases["redis"] = lease.Info{ 133 Holder: "redis/0", 134 Expiry: offset(63 * time.Second), 135 } 136 }, 137 }}, 138 } 139 fix.RunTest(c, func(manager leadership.ManagerWorker, clock *Clock) { 140 // Ask for a minute, actually get 63s. Don't expire early. 141 err := manager.ClaimLeadership("redis", "redis/0", time.Minute) 142 c.Assert(err, jc.ErrorIsNil) 143 clock.Advance(almostSeconds(63)) 144 }) 145 } 146 147 func (s *ExpireLeadershipSuite) TestClaim_ExpiryInFuture_TimePasses(c *gc.C) { 148 fix := &Fixture{ 149 expectCalls: []call{{ 150 method: "ClaimLease", 151 args: []interface{}{"redis", lease.Request{"redis/0", time.Minute}}, 152 callback: func(leases map[string]lease.Info) { 153 leases["redis"] = lease.Info{ 154 Holder: "redis/0", 155 Expiry: offset(63 * time.Second), 156 } 157 }, 158 }, { 159 method: "ExpireLease", 160 args: []interface{}{"redis"}, 161 callback: func(leases map[string]lease.Info) { 162 delete(leases, "redis") 163 }, 164 }}, 165 } 166 fix.RunTest(c, func(manager leadership.ManagerWorker, clock *Clock) { 167 // Ask for a minute, actually get 63s. Expire on time. 168 err := manager.ClaimLeadership("redis", "redis/0", time.Minute) 169 c.Assert(err, jc.ErrorIsNil) 170 clock.Advance(63 * time.Second) 171 }) 172 } 173 174 func (s *ExpireLeadershipSuite) TestExtend_ExpiryInFuture(c *gc.C) { 175 fix := &Fixture{ 176 leases: map[string]lease.Info{ 177 "redis": lease.Info{ 178 Holder: "redis/0", 179 Expiry: offset(time.Second), 180 }, 181 }, 182 expectCalls: []call{{ 183 method: "ExtendLease", 184 args: []interface{}{"redis", lease.Request{"redis/0", time.Minute}}, 185 callback: func(leases map[string]lease.Info) { 186 leases["redis"] = lease.Info{ 187 Holder: "redis/0", 188 Expiry: offset(63 * time.Second), 189 } 190 }, 191 }}, 192 } 193 fix.RunTest(c, func(manager leadership.ManagerWorker, clock *Clock) { 194 // Ask for a minute, actually get 63s. Don't expire early. 195 err := manager.ClaimLeadership("redis", "redis/0", time.Minute) 196 c.Assert(err, jc.ErrorIsNil) 197 clock.Advance(almostSeconds(63)) 198 }) 199 } 200 201 func (s *ExpireLeadershipSuite) TestExtend_ExpiryInFuture_TimePasses(c *gc.C) { 202 fix := &Fixture{ 203 leases: map[string]lease.Info{ 204 "redis": lease.Info{ 205 Holder: "redis/0", 206 Expiry: offset(time.Second), 207 }, 208 }, 209 expectCalls: []call{{ 210 method: "ExtendLease", 211 args: []interface{}{"redis", lease.Request{"redis/0", time.Minute}}, 212 callback: func(leases map[string]lease.Info) { 213 leases["redis"] = lease.Info{ 214 Holder: "redis/0", 215 Expiry: offset(63 * time.Second), 216 } 217 }, 218 }, { 219 method: "ExpireLease", 220 args: []interface{}{"redis"}, 221 callback: func(leases map[string]lease.Info) { 222 delete(leases, "redis") 223 }, 224 }}, 225 } 226 fix.RunTest(c, func(manager leadership.ManagerWorker, clock *Clock) { 227 // Ask for a minute, actually get 63s. Expire on time. 228 err := manager.ClaimLeadership("redis", "redis/0", time.Minute) 229 c.Assert(err, jc.ErrorIsNil) 230 clock.Advance(63 * time.Second) 231 }) 232 } 233 234 func (s *ExpireLeadershipSuite) TestExpire_Multiple(c *gc.C) { 235 fix := &Fixture{ 236 leases: map[string]lease.Info{ 237 "redis": lease.Info{ 238 Holder: "redis/0", 239 Expiry: offset(time.Second), 240 }, 241 "store": lease.Info{ 242 Holder: "store/3", 243 Expiry: offset(5 * time.Second), 244 }, 245 "tokumx": lease.Info{ 246 Holder: "tokumx/5", 247 Expiry: offset(10 * time.Second), // will not expire. 248 }, 249 "ultron": lease.Info{ 250 Holder: "ultron/7", 251 Expiry: offset(5 * time.Second), 252 }, 253 "vvvvvv": lease.Info{ 254 Holder: "vvvvvv/2", 255 Expiry: offset(time.Second), // would expire, but errors first. 256 }, 257 }, 258 expectCalls: []call{{ 259 method: "ExpireLease", 260 args: []interface{}{"redis"}, 261 callback: func(leases map[string]lease.Info) { 262 delete(leases, "redis") 263 }, 264 }, { 265 method: "ExpireLease", 266 args: []interface{}{"store"}, 267 err: lease.ErrInvalid, 268 callback: func(leases map[string]lease.Info) { 269 delete(leases, "store") 270 }, 271 }, { 272 method: "ExpireLease", 273 args: []interface{}{"ultron"}, 274 err: errors.New("what is this?"), 275 }}, 276 expectDirty: true, 277 } 278 fix.RunTest(c, func(manager leadership.ManagerWorker, clock *Clock) { 279 clock.Advance(5 * time.Second) 280 err := manager.Wait() 281 c.Check(err, gc.ErrorMatches, "what is this\\?") 282 }) 283 }