@daiso-tech/core 0.39.0 → 0.40.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/cache/contracts/cache-adapter.contract.d.ts +9 -9
- package/dist/cache/contracts/database-cache-adapter.contract.d.ts +10 -10
- package/dist/cache/implementations/adapters/no-op-cache-adapter/no-op-cache-adapter.d.ts +9 -9
- package/dist/cache/implementations/adapters/no-op-cache-adapter/no-op-cache-adapter.js.map +1 -1
- package/dist/cache/implementations/derivables/cache/cache.js.map +1 -1
- package/dist/event-bus/contracts/event-bus-adapter.contract.d.ts +3 -3
- package/dist/event-bus/implementations/adapters/no-op-event-bus-adapter/no-op-event-bus-adapter.d.ts +3 -3
- package/dist/event-bus/implementations/derivables/event-bus/event-bus.d.ts +1 -0
- package/dist/event-bus/implementations/derivables/event-bus/event-bus.js +26 -26
- package/dist/event-bus/implementations/derivables/event-bus/event-bus.js.map +1 -1
- package/dist/event-bus/implementations/derivables/event-bus/listener-store.d.ts +11 -4
- package/dist/event-bus/implementations/derivables/event-bus/listener-store.js +17 -12
- package/dist/event-bus/implementations/derivables/event-bus/listener-store.js.map +1 -1
- package/dist/event-bus/implementations/test-utilities/event-bus-adapter.test-suite.js +17 -20
- package/dist/event-bus/implementations/test-utilities/event-bus-adapter.test-suite.js.map +1 -1
- package/dist/event-bus/implementations/test-utilities/event-bus.test-suite.js +159 -752
- package/dist/event-bus/implementations/test-utilities/event-bus.test-suite.js.map +1 -1
- package/dist/lock/contracts/database-lock-adapter.contract.d.ts +52 -14
- package/dist/lock/contracts/lock-adapter.contract.d.ts +29 -8
- package/dist/lock/contracts/lock-adapter.contract.js +10 -1
- package/dist/lock/contracts/lock-adapter.contract.js.map +1 -1
- package/dist/lock/contracts/lock.contract.d.ts +17 -12
- package/dist/lock/contracts/lock.errors.d.ts +10 -0
- package/dist/lock/contracts/lock.errors.js +12 -0
- package/dist/lock/contracts/lock.errors.js.map +1 -1
- package/dist/lock/contracts/lock.events.d.ts +12 -0
- package/dist/lock/contracts/lock.events.js +1 -0
- package/dist/lock/contracts/lock.events.js.map +1 -1
- package/dist/lock/implementations/adapters/kysely-lock-adapter/kysely-lock-adapter.d.ts +24 -6
- package/dist/lock/implementations/adapters/kysely-lock-adapter/kysely-lock-adapter.js +126 -31
- package/dist/lock/implementations/adapters/kysely-lock-adapter/kysely-lock-adapter.js.map +1 -1
- package/dist/lock/implementations/adapters/memory-lock-adapter/memory-lock-adapter.d.ts +20 -7
- package/dist/lock/implementations/adapters/memory-lock-adapter/memory-lock-adapter.js +59 -35
- package/dist/lock/implementations/adapters/memory-lock-adapter/memory-lock-adapter.js.map +1 -1
- package/dist/lock/implementations/adapters/mongodb-lock-adapter/mongodb-lock-adapter.d.ts +9 -9
- package/dist/lock/implementations/adapters/mongodb-lock-adapter/mongodb-lock-adapter.js +150 -78
- package/dist/lock/implementations/adapters/mongodb-lock-adapter/mongodb-lock-adapter.js.map +1 -1
- package/dist/lock/implementations/adapters/no-op-lock-adapter/no-op-lock-adapter.d.ts +5 -5
- package/dist/lock/implementations/adapters/no-op-lock-adapter/no-op-lock-adapter.js +3 -2
- package/dist/lock/implementations/adapters/no-op-lock-adapter/no-op-lock-adapter.js.map +1 -1
- package/dist/lock/implementations/adapters/redis-lock-adapter/redis-lock-adapter.d.ts +5 -5
- package/dist/lock/implementations/adapters/redis-lock-adapter/redis-lock-adapter.js +44 -22
- package/dist/lock/implementations/adapters/redis-lock-adapter/redis-lock-adapter.js.map +1 -1
- package/dist/lock/implementations/derivables/lock-provider/database-lock-adapter.d.ts +3 -3
- package/dist/lock/implementations/derivables/lock-provider/database-lock-adapter.js +42 -10
- package/dist/lock/implementations/derivables/lock-provider/database-lock-adapter.js.map +1 -1
- package/dist/lock/implementations/derivables/lock-provider/is-database-lock-adapter.js +7 -5
- package/dist/lock/implementations/derivables/lock-provider/is-database-lock-adapter.js.map +1 -1
- package/dist/lock/implementations/derivables/lock-provider/lock-provider.js.map +1 -1
- package/dist/lock/implementations/derivables/lock-provider/lock-serde-transformer.d.ts +1 -1
- package/dist/lock/implementations/derivables/lock-provider/lock.d.ts +3 -2
- package/dist/lock/implementations/derivables/lock-provider/lock.js +60 -41
- package/dist/lock/implementations/derivables/lock-provider/lock.js.map +1 -1
- package/dist/lock/implementations/test-utilities/database-lock-adapter.test-suite.js +184 -166
- package/dist/lock/implementations/test-utilities/database-lock-adapter.test-suite.js.map +1 -1
- package/dist/lock/implementations/test-utilities/lock-adapter.test-suite.js +240 -41
- package/dist/lock/implementations/test-utilities/lock-adapter.test-suite.js.map +1 -1
- package/dist/lock/implementations/test-utilities/lock-provider.test-suite.js +2700 -1510
- package/dist/lock/implementations/test-utilities/lock-provider.test-suite.js.map +1 -1
- package/dist/utilities/contracts/deinitizable.contract.d.ts +1 -1
- package/dist/utilities/contracts/initizable.contract.d.ts +1 -1
- package/dist/utilities/contracts/prunable.contract.d.ts +1 -1
- package/package.json +1 -1
|
@@ -1,13 +1,13 @@
|
|
|
1
1
|
/**
|
|
2
2
|
* @module Lock
|
|
3
3
|
*/
|
|
4
|
-
import {} from "vitest";
|
|
5
|
-
import { KeyAlreadyAcquiredLockError, UnownedRefreshLockError, UnownedReleaseLockError, LOCK_EVENTS, } from "../../../lock/contracts/_module-exports.js";
|
|
4
|
+
import { vi, } from "vitest";
|
|
5
|
+
import { KeyAlreadyAcquiredLockError, UnownedRefreshLockError, UnownedReleaseLockError, LOCK_EVENTS, UnrefreshableKeyLockError, } from "../../../lock/contracts/_module-exports.js";
|
|
6
6
|
import { RESULT, resultSuccess, } from "../../../utilities/_module-exports.js";
|
|
7
7
|
import { TimeSpan } from "../../../utilities/_module-exports.js";
|
|
8
|
-
import { LazyPromise } from "../../../async/_module-exports.js";
|
|
9
8
|
import { NoOpSerdeAdapter } from "../../../serde/implementations/adapters/_module-exports.js";
|
|
10
9
|
import { Serde } from "../../../serde/implementations/derivables/_module-exports.js";
|
|
10
|
+
import { LazyPromise } from "../../../async/_module-exports.js";
|
|
11
11
|
/**
|
|
12
12
|
* The `lockProviderTestSuite` function simplifies the process of testing your custom implementation of {@link ILock | `ILock`} with `vitest`.
|
|
13
13
|
*
|
|
@@ -50,1882 +50,3072 @@ export function lockProviderTestSuite(settings) {
|
|
|
50
50
|
beforeEach(async () => {
|
|
51
51
|
lockProvider = await createLockProvider();
|
|
52
52
|
});
|
|
53
|
-
|
|
54
|
-
|
|
53
|
+
async function delay(time) {
|
|
54
|
+
await LazyPromise.delay(time.addMilliseconds(10));
|
|
55
|
+
}
|
|
56
|
+
const RETURN_VALUE = "RETURN_VALUE";
|
|
55
57
|
describe("Api tests:", () => {
|
|
56
58
|
describe("method: run", () => {
|
|
57
|
-
test("Should
|
|
59
|
+
test("Should call acquire method", async () => {
|
|
58
60
|
const key = "a";
|
|
59
61
|
const ttl = null;
|
|
60
62
|
const lock = lockProvider.create(key, {
|
|
61
63
|
ttl,
|
|
62
64
|
});
|
|
63
|
-
const
|
|
64
|
-
|
|
65
|
-
return
|
|
65
|
+
const acquireSpy = vi.spyOn(lock, "acquire");
|
|
66
|
+
await lock.run(() => {
|
|
67
|
+
return Promise.resolve(RETURN_VALUE);
|
|
66
68
|
});
|
|
67
|
-
expect(
|
|
69
|
+
expect(acquireSpy).toHaveBeenCalledTimes(1);
|
|
68
70
|
});
|
|
69
|
-
test("Should
|
|
71
|
+
test("Should call acquire before release method", async () => {
|
|
70
72
|
const key = "a";
|
|
71
73
|
const ttl = null;
|
|
72
74
|
const lock = lockProvider.create(key, {
|
|
73
75
|
ttl,
|
|
74
76
|
});
|
|
75
|
-
|
|
76
|
-
const
|
|
77
|
-
|
|
78
|
-
return
|
|
77
|
+
const acquireSpy = vi.spyOn(lock, "acquire");
|
|
78
|
+
const releaseSpy = vi.spyOn(lock, "release");
|
|
79
|
+
await lock.run(() => {
|
|
80
|
+
return Promise.resolve(RETURN_VALUE);
|
|
79
81
|
});
|
|
80
|
-
expect(
|
|
81
|
-
expect(result.error).toBeInstanceOf(KeyAlreadyAcquiredLockError);
|
|
82
|
+
expect(acquireSpy).toHaveBeenCalledBefore(releaseSpy);
|
|
82
83
|
});
|
|
83
|
-
test("Should
|
|
84
|
+
test("Should call release method", async () => {
|
|
84
85
|
const key = "a";
|
|
85
86
|
const ttl = null;
|
|
86
87
|
const lock = lockProvider.create(key, {
|
|
87
88
|
ttl,
|
|
88
89
|
});
|
|
89
|
-
const
|
|
90
|
-
|
|
91
|
-
return
|
|
92
|
-
})
|
|
93
|
-
expect(
|
|
90
|
+
const releaseSpy = vi.spyOn(lock, "release");
|
|
91
|
+
await lock.run(() => {
|
|
92
|
+
return Promise.resolve(RETURN_VALUE);
|
|
93
|
+
});
|
|
94
|
+
expect(releaseSpy).toHaveBeenCalledTimes(1);
|
|
94
95
|
});
|
|
95
|
-
|
|
96
|
-
describe("method: runOrFail", () => {
|
|
97
|
-
test("Should return string when lock is available", async () => {
|
|
96
|
+
test("Should call release after acquire method", async () => {
|
|
98
97
|
const key = "a";
|
|
99
98
|
const ttl = null;
|
|
100
99
|
const lock = lockProvider.create(key, {
|
|
101
100
|
ttl,
|
|
102
101
|
});
|
|
103
|
-
const
|
|
104
|
-
|
|
105
|
-
|
|
102
|
+
const releaseSpy = vi.spyOn(lock, "release");
|
|
103
|
+
const acquireSpy = vi.spyOn(lock, "acquire");
|
|
104
|
+
await lock.run(() => {
|
|
105
|
+
return Promise.resolve(RETURN_VALUE);
|
|
106
106
|
});
|
|
107
|
-
expect(
|
|
107
|
+
expect(releaseSpy).toHaveBeenCalledAfter(acquireSpy);
|
|
108
108
|
});
|
|
109
|
-
test("Should
|
|
109
|
+
test("Should call release when an error is thrown", async () => {
|
|
110
110
|
const key = "a";
|
|
111
111
|
const ttl = null;
|
|
112
112
|
const lock = lockProvider.create(key, {
|
|
113
113
|
ttl,
|
|
114
114
|
});
|
|
115
|
-
|
|
116
|
-
|
|
117
|
-
await
|
|
118
|
-
|
|
119
|
-
|
|
120
|
-
|
|
115
|
+
const releaseSpy = vi.spyOn(lock, "release");
|
|
116
|
+
try {
|
|
117
|
+
await lock.run(() => {
|
|
118
|
+
return Promise.reject(new Error());
|
|
119
|
+
});
|
|
120
|
+
}
|
|
121
|
+
catch {
|
|
122
|
+
/* EMPTY */
|
|
123
|
+
}
|
|
124
|
+
expect(releaseSpy).toHaveBeenCalledTimes(1);
|
|
121
125
|
});
|
|
122
|
-
test("Should
|
|
126
|
+
test("Should propagate thrown error", async () => {
|
|
123
127
|
const key = "a";
|
|
124
128
|
const ttl = null;
|
|
125
129
|
const lock = lockProvider.create(key, {
|
|
126
130
|
ttl,
|
|
127
131
|
});
|
|
128
|
-
|
|
129
|
-
|
|
130
|
-
|
|
131
|
-
|
|
132
|
-
|
|
132
|
+
class CustomError extends Error {
|
|
133
|
+
}
|
|
134
|
+
const error = lock.run(() => {
|
|
135
|
+
return Promise.reject(new CustomError());
|
|
136
|
+
});
|
|
137
|
+
await expect(error).rejects.toBeInstanceOf(CustomError);
|
|
133
138
|
});
|
|
134
|
-
|
|
135
|
-
describe("method: runBlocking", () => {
|
|
136
|
-
test("Should return string when lock is available", async () => {
|
|
139
|
+
test("Should call handler function when key doesnt exists", async () => {
|
|
137
140
|
const key = "a";
|
|
138
141
|
const ttl = null;
|
|
139
|
-
const
|
|
140
|
-
|
|
142
|
+
const handlerFn = vi.fn(() => {
|
|
143
|
+
return Promise.resolve(RETURN_VALUE);
|
|
141
144
|
});
|
|
142
|
-
|
|
143
|
-
|
|
144
|
-
|
|
145
|
-
}
|
|
146
|
-
|
|
147
|
-
|
|
145
|
+
await lockProvider
|
|
146
|
+
.create(key, {
|
|
147
|
+
ttl,
|
|
148
|
+
})
|
|
149
|
+
.run(handlerFn);
|
|
150
|
+
expect(handlerFn).toHaveBeenCalledTimes(1);
|
|
151
|
+
});
|
|
152
|
+
test("Should call handler function when key is expired", async () => {
|
|
153
|
+
const key = "a";
|
|
154
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
155
|
+
await lockProvider.create(key, { ttl }).acquire();
|
|
156
|
+
await delay(ttl);
|
|
157
|
+
const handlerFn = vi.fn(() => {
|
|
158
|
+
return Promise.resolve(RETURN_VALUE);
|
|
148
159
|
});
|
|
149
|
-
|
|
160
|
+
await lockProvider.create(key, { ttl }).run(handlerFn);
|
|
161
|
+
expect(handlerFn).toHaveBeenCalledTimes(1);
|
|
150
162
|
});
|
|
151
|
-
test("Should
|
|
163
|
+
test("Should not call handler function when key is unexpireable and acquired by same owner", async () => {
|
|
152
164
|
const key = "a";
|
|
153
165
|
const ttl = null;
|
|
166
|
+
const lock = lockProvider.create(key, { ttl });
|
|
167
|
+
await lock.acquire();
|
|
168
|
+
const handlerFn = vi.fn(() => {
|
|
169
|
+
return Promise.resolve(RETURN_VALUE);
|
|
170
|
+
});
|
|
171
|
+
await lock.run(handlerFn);
|
|
172
|
+
expect(handlerFn).toHaveBeenCalledTimes(0);
|
|
173
|
+
});
|
|
174
|
+
test("Should not call handler function when key is unexpired and acquired by same owner", async () => {
|
|
175
|
+
const key = "a";
|
|
176
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
154
177
|
const lock = lockProvider.create(key, {
|
|
155
178
|
ttl,
|
|
156
179
|
});
|
|
157
180
|
await lock.acquire();
|
|
158
|
-
const
|
|
159
|
-
|
|
160
|
-
return "a";
|
|
161
|
-
}, {
|
|
162
|
-
time: TimeSpan.fromMilliseconds(5),
|
|
163
|
-
interval: TimeSpan.fromMilliseconds(5),
|
|
181
|
+
const handlerFn = vi.fn(() => {
|
|
182
|
+
return Promise.resolve(RETURN_VALUE);
|
|
164
183
|
});
|
|
165
|
-
|
|
166
|
-
expect(
|
|
184
|
+
await lock.run(handlerFn);
|
|
185
|
+
expect(handlerFn).toHaveBeenCalledTimes(0);
|
|
167
186
|
});
|
|
168
|
-
test("Should
|
|
187
|
+
test("Should not call handler function when key is unexpireable and acquired by different owner", async () => {
|
|
169
188
|
const key = "a";
|
|
170
189
|
const ttl = null;
|
|
171
|
-
|
|
190
|
+
await lockProvider.create(key, { ttl }).acquire();
|
|
191
|
+
const handlerFn = vi.fn(() => {
|
|
192
|
+
return Promise.resolve(RETURN_VALUE);
|
|
193
|
+
});
|
|
194
|
+
await lockProvider.create(key, { ttl }).run(handlerFn);
|
|
195
|
+
expect(handlerFn).not.toHaveBeenCalled();
|
|
196
|
+
});
|
|
197
|
+
test("Should not call handler function when key is unexpired and acquired by different owner", async () => {
|
|
198
|
+
const key = "a";
|
|
199
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
200
|
+
await lockProvider.create(key, { ttl }).acquire();
|
|
201
|
+
const handlerFn = vi.fn(() => {
|
|
202
|
+
return Promise.resolve(RETURN_VALUE);
|
|
203
|
+
});
|
|
204
|
+
await lockProvider.create(key, { ttl }).run(handlerFn);
|
|
205
|
+
expect(handlerFn).not.toHaveBeenCalled();
|
|
206
|
+
});
|
|
207
|
+
test("Should return ResultSuccess<string> when key doesnt exists", async () => {
|
|
208
|
+
const key = "a";
|
|
209
|
+
const ttl = null;
|
|
210
|
+
const result = await lockProvider
|
|
211
|
+
.create(key, {
|
|
172
212
|
ttl,
|
|
213
|
+
})
|
|
214
|
+
.run(() => {
|
|
215
|
+
return Promise.resolve(RETURN_VALUE);
|
|
173
216
|
});
|
|
174
|
-
|
|
175
|
-
|
|
176
|
-
|
|
177
|
-
|
|
178
|
-
|
|
179
|
-
|
|
217
|
+
expect(result).toEqual(resultSuccess(RETURN_VALUE));
|
|
218
|
+
});
|
|
219
|
+
test("Should return ResultSuccess<string> when key is expired", async () => {
|
|
220
|
+
const key = "a";
|
|
221
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
222
|
+
await lockProvider.create(key, { ttl }).acquire();
|
|
223
|
+
await delay(ttl);
|
|
224
|
+
const result = await lockProvider
|
|
225
|
+
.create(key, { ttl })
|
|
226
|
+
.run(() => {
|
|
227
|
+
return Promise.resolve(RETURN_VALUE);
|
|
180
228
|
});
|
|
181
|
-
expect(result).toEqual(resultSuccess(
|
|
229
|
+
expect(result).toEqual(resultSuccess(RETURN_VALUE));
|
|
182
230
|
});
|
|
183
|
-
test("Should
|
|
231
|
+
test("Should return ResultFailure<KeyAlreadyAcquiredLockError> when key is unexpireable and acquired by same owner", async () => {
|
|
232
|
+
const key = "a";
|
|
233
|
+
const ttl = null;
|
|
234
|
+
const lock = lockProvider.create(key, { ttl });
|
|
235
|
+
await lock.acquire();
|
|
236
|
+
const result = await lock.run(() => {
|
|
237
|
+
return Promise.resolve(RETURN_VALUE);
|
|
238
|
+
});
|
|
239
|
+
expect(result.type).toBe(RESULT.FAILURE);
|
|
240
|
+
expect(result.error).toBeInstanceOf(KeyAlreadyAcquiredLockError);
|
|
241
|
+
});
|
|
242
|
+
test("Should return ResultFailure<KeyAlreadyAcquiredLockError> when key is unexpired and acquired by same owner", async () => {
|
|
184
243
|
const key = "a";
|
|
185
244
|
const ttl = TimeSpan.fromMilliseconds(50);
|
|
186
245
|
const lock = lockProvider.create(key, {
|
|
187
246
|
ttl,
|
|
188
247
|
});
|
|
189
248
|
await lock.acquire();
|
|
190
|
-
|
|
191
|
-
|
|
192
|
-
index++;
|
|
249
|
+
const result = await lock.run(() => {
|
|
250
|
+
return Promise.resolve(RETURN_VALUE);
|
|
193
251
|
});
|
|
194
|
-
|
|
195
|
-
|
|
196
|
-
|
|
197
|
-
|
|
198
|
-
|
|
252
|
+
expect(result.type).toBe(RESULT.FAILURE);
|
|
253
|
+
expect(result.error).toBeInstanceOf(KeyAlreadyAcquiredLockError);
|
|
254
|
+
});
|
|
255
|
+
test("Should return ResultFailure<KeyAlreadyAcquiredLockError> when key is unexpireable and acquired by different owner", async () => {
|
|
256
|
+
const key = "a";
|
|
257
|
+
const ttl = null;
|
|
258
|
+
await lockProvider.create(key, { ttl }).acquire();
|
|
259
|
+
const result = await lockProvider
|
|
260
|
+
.create(key, { ttl })
|
|
261
|
+
.run(() => {
|
|
262
|
+
return Promise.resolve(RETURN_VALUE);
|
|
199
263
|
});
|
|
200
|
-
expect(
|
|
264
|
+
expect(result.type).toBe(RESULT.FAILURE);
|
|
265
|
+
expect(result.error).toBeInstanceOf(KeyAlreadyAcquiredLockError);
|
|
266
|
+
});
|
|
267
|
+
test("Should return ResultFailure<KeyAlreadyAcquiredLockError> when key is unexpired and acquired by different owner", async () => {
|
|
268
|
+
const key = "a";
|
|
269
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
270
|
+
await lockProvider.create(key, { ttl }).acquire();
|
|
271
|
+
const result = await lockProvider
|
|
272
|
+
.create(key, { ttl })
|
|
273
|
+
.run(() => {
|
|
274
|
+
return Promise.resolve(RETURN_VALUE);
|
|
275
|
+
});
|
|
276
|
+
expect(result.type).toBe(RESULT.FAILURE);
|
|
277
|
+
expect(result.error).toBeInstanceOf(KeyAlreadyAcquiredLockError);
|
|
201
278
|
});
|
|
202
279
|
});
|
|
203
|
-
describe("method:
|
|
204
|
-
test("Should
|
|
280
|
+
describe("method: runOrFail", () => {
|
|
281
|
+
test("Should call acquireOrFail method", async () => {
|
|
205
282
|
const key = "a";
|
|
206
283
|
const ttl = null;
|
|
207
284
|
const lock = lockProvider.create(key, {
|
|
208
285
|
ttl,
|
|
209
286
|
});
|
|
210
|
-
const
|
|
211
|
-
|
|
212
|
-
return
|
|
213
|
-
}, {
|
|
214
|
-
time: TimeSpan.fromMilliseconds(5),
|
|
215
|
-
interval: TimeSpan.fromMilliseconds(5),
|
|
287
|
+
const acquireSpy = vi.spyOn(lock, "acquireOrFail");
|
|
288
|
+
await lock.runOrFail(() => {
|
|
289
|
+
return Promise.resolve(RETURN_VALUE);
|
|
216
290
|
});
|
|
217
|
-
expect(
|
|
291
|
+
expect(acquireSpy).toHaveBeenCalledTimes(1);
|
|
218
292
|
});
|
|
219
|
-
test("Should
|
|
293
|
+
test("Should call acquireOrFail before release method", async () => {
|
|
220
294
|
const key = "a";
|
|
221
295
|
const ttl = null;
|
|
222
296
|
const lock = lockProvider.create(key, {
|
|
223
297
|
ttl,
|
|
224
298
|
});
|
|
225
|
-
|
|
226
|
-
const
|
|
227
|
-
|
|
228
|
-
return
|
|
229
|
-
}, {
|
|
230
|
-
time: TimeSpan.fromMilliseconds(5),
|
|
231
|
-
interval: TimeSpan.fromMilliseconds(5),
|
|
299
|
+
const acquireSpy = vi.spyOn(lock, "acquireOrFail");
|
|
300
|
+
const releaseSpy = vi.spyOn(lock, "release");
|
|
301
|
+
await lock.runOrFail(() => {
|
|
302
|
+
return Promise.resolve(RETURN_VALUE);
|
|
232
303
|
});
|
|
233
|
-
|
|
304
|
+
expect(acquireSpy).toHaveBeenCalledBefore(releaseSpy);
|
|
234
305
|
});
|
|
235
|
-
test("Should
|
|
306
|
+
test("Should call release method", async () => {
|
|
236
307
|
const key = "a";
|
|
237
308
|
const ttl = null;
|
|
238
309
|
const lock = lockProvider.create(key, {
|
|
239
310
|
ttl,
|
|
240
311
|
});
|
|
241
|
-
const
|
|
242
|
-
|
|
243
|
-
return
|
|
244
|
-
}), {
|
|
245
|
-
time: TimeSpan.fromMilliseconds(5),
|
|
246
|
-
interval: TimeSpan.fromMilliseconds(5),
|
|
312
|
+
const releaseSpy = vi.spyOn(lock, "release");
|
|
313
|
+
await lock.runOrFail(() => {
|
|
314
|
+
return Promise.resolve(RETURN_VALUE);
|
|
247
315
|
});
|
|
248
|
-
expect(
|
|
316
|
+
expect(releaseSpy).toHaveBeenCalledTimes(1);
|
|
249
317
|
});
|
|
250
|
-
test("Should
|
|
318
|
+
test("Should call release after acquireOrFail method", async () => {
|
|
251
319
|
const key = "a";
|
|
252
|
-
const ttl =
|
|
320
|
+
const ttl = null;
|
|
253
321
|
const lock = lockProvider.create(key, {
|
|
254
322
|
ttl,
|
|
255
323
|
});
|
|
256
|
-
|
|
257
|
-
|
|
258
|
-
await
|
|
259
|
-
|
|
324
|
+
const releaseSpy = vi.spyOn(lock, "release");
|
|
325
|
+
const acquireSpy = vi.spyOn(lock, "acquireOrFail");
|
|
326
|
+
await lock.runOrFail(() => {
|
|
327
|
+
return Promise.resolve(RETURN_VALUE);
|
|
328
|
+
});
|
|
329
|
+
expect(releaseSpy).toHaveBeenCalledAfter(acquireSpy);
|
|
330
|
+
});
|
|
331
|
+
test("Should call release when an error is thrown", async () => {
|
|
332
|
+
const key = "a";
|
|
333
|
+
const ttl = null;
|
|
334
|
+
const lock = lockProvider.create(key, {
|
|
335
|
+
ttl,
|
|
260
336
|
});
|
|
337
|
+
const releaseSpy = vi.spyOn(lock, "release");
|
|
261
338
|
try {
|
|
262
|
-
await lock.
|
|
263
|
-
|
|
264
|
-
}, {
|
|
265
|
-
time: TimeSpan.fromMilliseconds(55),
|
|
266
|
-
interval: TimeSpan.fromMilliseconds(5),
|
|
339
|
+
await lock.runOrFail(() => {
|
|
340
|
+
return Promise.reject(new Error());
|
|
267
341
|
});
|
|
268
342
|
}
|
|
269
343
|
catch {
|
|
270
|
-
/*
|
|
344
|
+
/* EMPTY */
|
|
271
345
|
}
|
|
272
|
-
expect(
|
|
346
|
+
expect(releaseSpy).toHaveBeenCalledTimes(1);
|
|
273
347
|
});
|
|
274
|
-
|
|
275
|
-
describe("method: acquire", () => {
|
|
276
|
-
test("Should return true when lock is available", async () => {
|
|
348
|
+
test("Should propagate thrown error", async () => {
|
|
277
349
|
const key = "a";
|
|
278
350
|
const ttl = null;
|
|
279
351
|
const lock = lockProvider.create(key, {
|
|
280
352
|
ttl,
|
|
281
353
|
});
|
|
282
|
-
|
|
283
|
-
|
|
354
|
+
class CustomError extends Error {
|
|
355
|
+
}
|
|
356
|
+
const error = lock.runOrFail(() => {
|
|
357
|
+
return Promise.reject(new CustomError());
|
|
358
|
+
});
|
|
359
|
+
await expect(error).rejects.toBeInstanceOf(CustomError);
|
|
284
360
|
});
|
|
285
|
-
test("Should
|
|
361
|
+
test("Should call handler function when key doesnt exists", async () => {
|
|
286
362
|
const key = "a";
|
|
287
363
|
const ttl = null;
|
|
288
|
-
const
|
|
364
|
+
const handlerFn = vi.fn(() => {
|
|
365
|
+
return Promise.resolve(RETURN_VALUE);
|
|
366
|
+
});
|
|
367
|
+
await lockProvider
|
|
368
|
+
.create(key, {
|
|
289
369
|
ttl,
|
|
370
|
+
})
|
|
371
|
+
.runOrFail(handlerFn);
|
|
372
|
+
expect(handlerFn).toHaveBeenCalledTimes(1);
|
|
373
|
+
});
|
|
374
|
+
test("Should call handler function when key is expired", async () => {
|
|
375
|
+
const key = "a";
|
|
376
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
377
|
+
await lockProvider.create(key, { ttl }).acquire();
|
|
378
|
+
await delay(ttl);
|
|
379
|
+
const handlerFn = vi.fn(() => {
|
|
380
|
+
return Promise.resolve(RETURN_VALUE);
|
|
290
381
|
});
|
|
291
|
-
await
|
|
292
|
-
|
|
293
|
-
expect(result).toBe(false);
|
|
382
|
+
await lockProvider.create(key, { ttl }).runOrFail(handlerFn);
|
|
383
|
+
expect(handlerFn).toHaveBeenCalledTimes(1);
|
|
294
384
|
});
|
|
295
|
-
test("Should not
|
|
385
|
+
test("Should not call handler function when key is unexpireable and acquired by same owner", async () => {
|
|
296
386
|
const key = "a";
|
|
297
387
|
const ttl = null;
|
|
298
|
-
const
|
|
388
|
+
const lock = lockProvider.create(key, { ttl });
|
|
389
|
+
await lock.acquire();
|
|
390
|
+
const handlerFn = vi.fn(() => {
|
|
391
|
+
return Promise.resolve(RETURN_VALUE);
|
|
392
|
+
});
|
|
393
|
+
try {
|
|
394
|
+
await lock.runOrFail(handlerFn);
|
|
395
|
+
}
|
|
396
|
+
catch {
|
|
397
|
+
/* EMPTY */
|
|
398
|
+
}
|
|
399
|
+
expect(handlerFn).toHaveBeenCalledTimes(0);
|
|
400
|
+
});
|
|
401
|
+
test("Should not call handler function when key is unexpired and acquired by same owner", async () => {
|
|
402
|
+
const key = "a";
|
|
403
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
299
404
|
const lock = lockProvider.create(key, {
|
|
300
405
|
ttl,
|
|
301
|
-
owner,
|
|
302
406
|
});
|
|
303
407
|
await lock.acquire();
|
|
304
|
-
const
|
|
305
|
-
|
|
408
|
+
const handlerFn = vi.fn(() => {
|
|
409
|
+
return Promise.resolve(RETURN_VALUE);
|
|
410
|
+
});
|
|
411
|
+
try {
|
|
412
|
+
await lock.runOrFail(handlerFn);
|
|
413
|
+
}
|
|
414
|
+
catch {
|
|
415
|
+
/* EMPTY */
|
|
416
|
+
}
|
|
417
|
+
expect(handlerFn).toHaveBeenCalledTimes(0);
|
|
306
418
|
});
|
|
307
|
-
test("Should
|
|
419
|
+
test("Should not call handler function when key is unexpireable and acquired by different owner", async () => {
|
|
308
420
|
const key = "a";
|
|
309
421
|
const ttl = null;
|
|
310
|
-
|
|
311
|
-
const
|
|
312
|
-
|
|
313
|
-
owner,
|
|
422
|
+
await lockProvider.create(key, { ttl }).acquire();
|
|
423
|
+
const handlerFn = vi.fn(() => {
|
|
424
|
+
return Promise.resolve(RETURN_VALUE);
|
|
314
425
|
});
|
|
315
|
-
|
|
316
|
-
|
|
317
|
-
|
|
426
|
+
try {
|
|
427
|
+
await lockProvider
|
|
428
|
+
.create(key, { ttl })
|
|
429
|
+
.runOrFail(handlerFn);
|
|
430
|
+
}
|
|
431
|
+
catch {
|
|
432
|
+
/* EMPTY */
|
|
433
|
+
}
|
|
434
|
+
expect(handlerFn).not.toHaveBeenCalled();
|
|
318
435
|
});
|
|
319
|
-
|
|
320
|
-
|
|
321
|
-
|
|
436
|
+
test("Should not call handler function when key is unexpired and acquired by different owner", async () => {
|
|
437
|
+
const key = "a";
|
|
438
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
439
|
+
await lockProvider.create(key, { ttl }).acquire();
|
|
440
|
+
const handlerFn = vi.fn(() => {
|
|
441
|
+
return Promise.resolve(RETURN_VALUE);
|
|
442
|
+
});
|
|
443
|
+
try {
|
|
444
|
+
await lockProvider
|
|
445
|
+
.create(key, { ttl })
|
|
446
|
+
.runOrFail(handlerFn);
|
|
447
|
+
}
|
|
448
|
+
catch {
|
|
449
|
+
/* EMPTY */
|
|
450
|
+
}
|
|
451
|
+
expect(handlerFn).not.toHaveBeenCalled();
|
|
452
|
+
});
|
|
453
|
+
test("Should return value when key doesnt exists", async () => {
|
|
322
454
|
const key = "a";
|
|
323
455
|
const ttl = null;
|
|
324
|
-
const
|
|
456
|
+
const result = await lockProvider
|
|
457
|
+
.create(key, {
|
|
325
458
|
ttl,
|
|
459
|
+
})
|
|
460
|
+
.runOrFail(() => {
|
|
461
|
+
return Promise.resolve(RETURN_VALUE);
|
|
326
462
|
});
|
|
327
|
-
|
|
328
|
-
|
|
463
|
+
expect(result).toBe(RETURN_VALUE);
|
|
464
|
+
});
|
|
465
|
+
test("Should return value when key is expired", async () => {
|
|
466
|
+
const key = "a";
|
|
467
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
468
|
+
await lockProvider.create(key, { ttl }).acquire();
|
|
469
|
+
await delay(ttl);
|
|
470
|
+
const result = await lockProvider
|
|
471
|
+
.create(key, { ttl })
|
|
472
|
+
.runOrFail(() => {
|
|
473
|
+
return Promise.resolve(RETURN_VALUE);
|
|
474
|
+
});
|
|
475
|
+
expect(result).toBe(RETURN_VALUE);
|
|
329
476
|
});
|
|
330
|
-
test("Should throw KeyAlreadyAcquiredLockError when
|
|
477
|
+
test("Should throw KeyAlreadyAcquiredLockError when key is unexpireable and acquired by same owner", async () => {
|
|
331
478
|
const key = "a";
|
|
332
479
|
const ttl = null;
|
|
480
|
+
const lock = lockProvider.create(key, { ttl });
|
|
481
|
+
await lock.acquire();
|
|
482
|
+
const result = lock.runOrFail(() => {
|
|
483
|
+
return Promise.resolve(RETURN_VALUE);
|
|
484
|
+
});
|
|
485
|
+
await expect(result).rejects.toBeInstanceOf(KeyAlreadyAcquiredLockError);
|
|
486
|
+
});
|
|
487
|
+
test("Should throw KeyAlreadyAcquiredLockError when key is unexpired and acquired by same owner", async () => {
|
|
488
|
+
const key = "a";
|
|
489
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
333
490
|
const lock = lockProvider.create(key, {
|
|
334
491
|
ttl,
|
|
335
492
|
});
|
|
336
|
-
await lock.
|
|
337
|
-
const result = lock.
|
|
493
|
+
await lock.acquire();
|
|
494
|
+
const result = lock.runOrFail(() => {
|
|
495
|
+
return Promise.resolve(RETURN_VALUE);
|
|
496
|
+
});
|
|
497
|
+
await expect(result).rejects.toBeInstanceOf(KeyAlreadyAcquiredLockError);
|
|
498
|
+
});
|
|
499
|
+
test("Should throw KeyAlreadyAcquiredLockError when key is unexpireable and acquired by different owner", async () => {
|
|
500
|
+
const key = "a";
|
|
501
|
+
const ttl = null;
|
|
502
|
+
await lockProvider.create(key, { ttl }).acquire();
|
|
503
|
+
const result = lockProvider
|
|
504
|
+
.create(key, { ttl })
|
|
505
|
+
.runOrFail(() => {
|
|
506
|
+
return Promise.resolve(RETURN_VALUE);
|
|
507
|
+
});
|
|
508
|
+
await expect(result).rejects.toBeInstanceOf(KeyAlreadyAcquiredLockError);
|
|
509
|
+
});
|
|
510
|
+
test("Should throw KeyAlreadyAcquiredLockError when key is unexpired and acquired by different owner", async () => {
|
|
511
|
+
const key = "a";
|
|
512
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
513
|
+
await lockProvider.create(key, { ttl }).acquire();
|
|
514
|
+
const result = lockProvider
|
|
515
|
+
.create(key, { ttl })
|
|
516
|
+
.runOrFail(() => {
|
|
517
|
+
return Promise.resolve(RETURN_VALUE);
|
|
518
|
+
});
|
|
338
519
|
await expect(result).rejects.toBeInstanceOf(KeyAlreadyAcquiredLockError);
|
|
339
520
|
});
|
|
340
521
|
});
|
|
341
|
-
describe("method:
|
|
342
|
-
test("Should
|
|
522
|
+
describe("method: runBlocking", () => {
|
|
523
|
+
test("Should call acquireBlocking method", async () => {
|
|
343
524
|
const key = "a";
|
|
344
525
|
const ttl = null;
|
|
345
526
|
const lock = lockProvider.create(key, {
|
|
346
527
|
ttl,
|
|
347
528
|
});
|
|
348
|
-
const
|
|
529
|
+
const acquireSpy = vi.spyOn(lock, "acquireBlocking");
|
|
530
|
+
await lock.runBlocking(() => {
|
|
531
|
+
return Promise.resolve(RETURN_VALUE);
|
|
532
|
+
}, {
|
|
349
533
|
time: TimeSpan.fromMilliseconds(5),
|
|
350
534
|
interval: TimeSpan.fromMilliseconds(5),
|
|
351
535
|
});
|
|
352
|
-
expect(
|
|
536
|
+
expect(acquireSpy).toHaveBeenCalledTimes(1);
|
|
353
537
|
});
|
|
354
|
-
test("Should
|
|
538
|
+
test("Should call acquireBlocking before release method", async () => {
|
|
355
539
|
const key = "a";
|
|
356
540
|
const ttl = null;
|
|
357
541
|
const lock = lockProvider.create(key, {
|
|
358
542
|
ttl,
|
|
359
543
|
});
|
|
360
|
-
|
|
361
|
-
|
|
362
|
-
|
|
363
|
-
|
|
364
|
-
|
|
544
|
+
const acquireSpy = vi.spyOn(lock, "acquireBlocking");
|
|
545
|
+
const releaseSpy = vi.spyOn(lock, "release");
|
|
546
|
+
await lock.runBlocking(() => {
|
|
547
|
+
return Promise.resolve(RETURN_VALUE);
|
|
548
|
+
}, {
|
|
365
549
|
time: TimeSpan.fromMilliseconds(5),
|
|
366
550
|
interval: TimeSpan.fromMilliseconds(5),
|
|
367
551
|
});
|
|
368
|
-
expect(
|
|
552
|
+
expect(acquireSpy).toHaveBeenCalledBefore(releaseSpy);
|
|
369
553
|
});
|
|
370
|
-
test("Should
|
|
554
|
+
test("Should call release method", async () => {
|
|
371
555
|
const key = "a";
|
|
372
556
|
const ttl = null;
|
|
373
|
-
const owner = "b";
|
|
374
557
|
const lock = lockProvider.create(key, {
|
|
375
558
|
ttl,
|
|
376
|
-
owner,
|
|
377
559
|
});
|
|
378
|
-
|
|
560
|
+
const releaseSpy = vi.spyOn(lock, "release");
|
|
561
|
+
await lock.runBlocking(() => {
|
|
562
|
+
return Promise.resolve(RETURN_VALUE);
|
|
563
|
+
}, {
|
|
379
564
|
time: TimeSpan.fromMilliseconds(5),
|
|
380
565
|
interval: TimeSpan.fromMilliseconds(5),
|
|
381
566
|
});
|
|
382
|
-
|
|
383
|
-
expect(result).toBe(false);
|
|
567
|
+
expect(releaseSpy).toHaveBeenCalledTimes(1);
|
|
384
568
|
});
|
|
385
|
-
test("Should
|
|
569
|
+
test("Should call release after acquireBlocking method", async () => {
|
|
386
570
|
const key = "a";
|
|
387
571
|
const ttl = null;
|
|
388
|
-
const owner = "b";
|
|
389
572
|
const lock = lockProvider.create(key, {
|
|
390
573
|
ttl,
|
|
391
|
-
owner,
|
|
392
574
|
});
|
|
393
|
-
|
|
575
|
+
const releaseSpy = vi.spyOn(lock, "release");
|
|
576
|
+
const acquireSpy = vi.spyOn(lock, "acquireBlocking");
|
|
577
|
+
await lock.runBlocking(() => {
|
|
578
|
+
return Promise.resolve(RETURN_VALUE);
|
|
579
|
+
}, {
|
|
394
580
|
time: TimeSpan.fromMilliseconds(5),
|
|
395
581
|
interval: TimeSpan.fromMilliseconds(5),
|
|
396
582
|
});
|
|
397
|
-
|
|
398
|
-
expect(result).toBe(true);
|
|
583
|
+
expect(releaseSpy).toHaveBeenCalledAfter(acquireSpy);
|
|
399
584
|
});
|
|
400
|
-
test("Should
|
|
585
|
+
test("Should call release when an error is thrown", async () => {
|
|
401
586
|
const key = "a";
|
|
402
|
-
const ttl =
|
|
587
|
+
const ttl = null;
|
|
403
588
|
const lock = lockProvider.create(key, {
|
|
404
589
|
ttl,
|
|
405
590
|
});
|
|
406
|
-
|
|
407
|
-
|
|
408
|
-
|
|
409
|
-
|
|
410
|
-
|
|
411
|
-
|
|
412
|
-
|
|
413
|
-
|
|
414
|
-
}
|
|
415
|
-
|
|
591
|
+
const releaseSpy = vi.spyOn(lock, "release");
|
|
592
|
+
try {
|
|
593
|
+
await lock.runBlocking(() => {
|
|
594
|
+
return Promise.reject(new Error());
|
|
595
|
+
}, {
|
|
596
|
+
time: TimeSpan.fromMilliseconds(5),
|
|
597
|
+
interval: TimeSpan.fromMilliseconds(5),
|
|
598
|
+
});
|
|
599
|
+
}
|
|
600
|
+
catch {
|
|
601
|
+
/* EMPTY */
|
|
602
|
+
}
|
|
603
|
+
expect(releaseSpy).toHaveBeenCalledTimes(1);
|
|
416
604
|
});
|
|
417
|
-
|
|
418
|
-
describe("method: acquireBlockingOrFail", () => {
|
|
419
|
-
test("Should not throw KeyAlreadyAcquiredLockError when lock is available", async () => {
|
|
605
|
+
test("Should propagate thrown error", async () => {
|
|
420
606
|
const key = "a";
|
|
421
607
|
const ttl = null;
|
|
422
608
|
const lock = lockProvider.create(key, {
|
|
423
609
|
ttl,
|
|
424
610
|
});
|
|
425
|
-
|
|
611
|
+
class CustomError extends Error {
|
|
612
|
+
}
|
|
613
|
+
const error = lock.runBlocking(() => {
|
|
614
|
+
return Promise.reject(new CustomError());
|
|
615
|
+
}, {
|
|
426
616
|
time: TimeSpan.fromMilliseconds(5),
|
|
427
617
|
interval: TimeSpan.fromMilliseconds(5),
|
|
428
618
|
});
|
|
429
|
-
await expect(
|
|
619
|
+
await expect(error).rejects.toBeInstanceOf(CustomError);
|
|
430
620
|
});
|
|
431
|
-
test("Should
|
|
621
|
+
test("Should call handler function when key doesnt exists", async () => {
|
|
432
622
|
const key = "a";
|
|
433
623
|
const ttl = null;
|
|
434
|
-
const
|
|
435
|
-
|
|
624
|
+
const handlerFn = vi.fn(() => {
|
|
625
|
+
return Promise.resolve(RETURN_VALUE);
|
|
436
626
|
});
|
|
437
|
-
await
|
|
627
|
+
await lockProvider
|
|
628
|
+
.create(key, {
|
|
629
|
+
ttl,
|
|
630
|
+
})
|
|
631
|
+
.runBlocking(handlerFn, {
|
|
438
632
|
time: TimeSpan.fromMilliseconds(5),
|
|
439
633
|
interval: TimeSpan.fromMilliseconds(5),
|
|
440
634
|
});
|
|
441
|
-
|
|
635
|
+
expect(handlerFn).toHaveBeenCalledTimes(1);
|
|
636
|
+
});
|
|
637
|
+
test("Should call handler function when key is expired", async () => {
|
|
638
|
+
const key = "a";
|
|
639
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
640
|
+
await lockProvider.create(key, { ttl }).acquire();
|
|
641
|
+
await delay(ttl);
|
|
642
|
+
const handlerFn = vi.fn(() => {
|
|
643
|
+
return Promise.resolve(RETURN_VALUE);
|
|
644
|
+
});
|
|
645
|
+
await lockProvider.create(key, { ttl }).runBlocking(handlerFn, {
|
|
442
646
|
time: TimeSpan.fromMilliseconds(5),
|
|
443
647
|
interval: TimeSpan.fromMilliseconds(5),
|
|
444
648
|
});
|
|
445
|
-
|
|
649
|
+
expect(handlerFn).toHaveBeenCalledTimes(1);
|
|
446
650
|
});
|
|
447
|
-
test("Should not
|
|
651
|
+
test("Should not call handler function when key is unexpireable and acquired by same owner", async () => {
|
|
448
652
|
const key = "a";
|
|
449
653
|
const ttl = null;
|
|
450
|
-
const
|
|
451
|
-
|
|
452
|
-
|
|
453
|
-
|
|
654
|
+
const lock = lockProvider.create(key, { ttl });
|
|
655
|
+
await lock.acquire();
|
|
656
|
+
const handlerFn = vi.fn(() => {
|
|
657
|
+
return Promise.resolve(RETURN_VALUE);
|
|
454
658
|
});
|
|
455
|
-
await lock.
|
|
659
|
+
await lock.runBlocking(handlerFn, {
|
|
456
660
|
time: TimeSpan.fromMilliseconds(5),
|
|
457
661
|
interval: TimeSpan.fromMilliseconds(5),
|
|
458
662
|
});
|
|
459
|
-
|
|
460
|
-
expect(result).toBe(false);
|
|
663
|
+
expect(handlerFn).toHaveBeenCalledTimes(0);
|
|
461
664
|
});
|
|
462
|
-
test("Should
|
|
665
|
+
test("Should not call handler function when key is unexpired and acquired by same owner", async () => {
|
|
463
666
|
const key = "a";
|
|
464
|
-
const ttl =
|
|
465
|
-
const owner = "b";
|
|
667
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
466
668
|
const lock = lockProvider.create(key, {
|
|
467
669
|
ttl,
|
|
468
|
-
owner,
|
|
469
670
|
});
|
|
470
|
-
await lock.
|
|
471
|
-
|
|
671
|
+
await lock.acquire();
|
|
672
|
+
const handlerFn = vi.fn(() => {
|
|
673
|
+
return Promise.resolve(RETURN_VALUE);
|
|
674
|
+
});
|
|
675
|
+
await lock.runBlocking(handlerFn, {
|
|
676
|
+
time: TimeSpan.fromMilliseconds(5),
|
|
472
677
|
interval: TimeSpan.fromMilliseconds(5),
|
|
473
678
|
});
|
|
474
|
-
|
|
475
|
-
expect(result).toBe(true);
|
|
679
|
+
expect(handlerFn).toHaveBeenCalledTimes(0);
|
|
476
680
|
});
|
|
477
|
-
test("Should
|
|
681
|
+
test("Should not call handler function when key is unexpireable and acquired by different owner", async () => {
|
|
478
682
|
const key = "a";
|
|
479
|
-
const ttl =
|
|
480
|
-
|
|
481
|
-
|
|
683
|
+
const ttl = null;
|
|
684
|
+
await lockProvider.create(key, { ttl }).acquire();
|
|
685
|
+
const handlerFn = vi.fn(() => {
|
|
686
|
+
return Promise.resolve(RETURN_VALUE);
|
|
482
687
|
});
|
|
483
|
-
await
|
|
484
|
-
|
|
485
|
-
|
|
486
|
-
index++;
|
|
688
|
+
await lockProvider.create(key, { ttl }).runBlocking(handlerFn, {
|
|
689
|
+
time: TimeSpan.fromMilliseconds(5),
|
|
690
|
+
interval: TimeSpan.fromMilliseconds(5),
|
|
487
691
|
});
|
|
488
|
-
|
|
489
|
-
await lock.acquireBlockingOrFail({
|
|
490
|
-
time: TimeSpan.fromMilliseconds(55),
|
|
491
|
-
interval: TimeSpan.fromMilliseconds(5),
|
|
492
|
-
});
|
|
493
|
-
}
|
|
494
|
-
catch {
|
|
495
|
-
/* Empty */
|
|
496
|
-
}
|
|
497
|
-
expect(index).toBeGreaterThan(1);
|
|
692
|
+
expect(handlerFn).not.toHaveBeenCalled();
|
|
498
693
|
});
|
|
499
|
-
|
|
500
|
-
describe("method: release", () => {
|
|
501
|
-
test("Should return true when released by same owner", async () => {
|
|
694
|
+
test("Should not call handler function when key is unexpired and acquired by different owner", async () => {
|
|
502
695
|
const key = "a";
|
|
503
|
-
const ttl =
|
|
504
|
-
|
|
505
|
-
const
|
|
506
|
-
|
|
507
|
-
owner,
|
|
696
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
697
|
+
await lockProvider.create(key, { ttl }).acquire();
|
|
698
|
+
const handlerFn = vi.fn(() => {
|
|
699
|
+
return Promise.resolve(RETURN_VALUE);
|
|
508
700
|
});
|
|
509
|
-
await
|
|
510
|
-
|
|
511
|
-
|
|
701
|
+
await lockProvider.create(key, { ttl }).runBlocking(handlerFn, {
|
|
702
|
+
time: TimeSpan.fromMilliseconds(5),
|
|
703
|
+
interval: TimeSpan.fromMilliseconds(5),
|
|
704
|
+
});
|
|
705
|
+
expect(handlerFn).not.toHaveBeenCalled();
|
|
512
706
|
});
|
|
513
|
-
test("Should return
|
|
707
|
+
test("Should return ResultSuccess<string> when key doesnt exists", async () => {
|
|
514
708
|
const key = "a";
|
|
515
709
|
const ttl = null;
|
|
516
|
-
const
|
|
517
|
-
|
|
710
|
+
const result = await lockProvider
|
|
711
|
+
.create(key, {
|
|
518
712
|
ttl,
|
|
519
|
-
|
|
713
|
+
})
|
|
714
|
+
.runBlocking(() => {
|
|
715
|
+
return Promise.resolve(RETURN_VALUE);
|
|
716
|
+
}, {
|
|
717
|
+
time: TimeSpan.fromMilliseconds(5),
|
|
718
|
+
interval: TimeSpan.fromMilliseconds(5),
|
|
520
719
|
});
|
|
521
|
-
|
|
522
|
-
|
|
523
|
-
|
|
524
|
-
|
|
525
|
-
|
|
720
|
+
expect(result).toEqual(resultSuccess(RETURN_VALUE));
|
|
721
|
+
});
|
|
722
|
+
test("Should return ResultSuccess<string> when key is expired", async () => {
|
|
723
|
+
const key = "a";
|
|
724
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
725
|
+
await lockProvider.create(key, { ttl }).acquire();
|
|
726
|
+
await delay(ttl);
|
|
727
|
+
const result = await lockProvider
|
|
728
|
+
.create(key, { ttl })
|
|
729
|
+
.runBlocking(() => {
|
|
730
|
+
return Promise.resolve(RETURN_VALUE);
|
|
731
|
+
}, {
|
|
732
|
+
time: TimeSpan.fromMilliseconds(5),
|
|
733
|
+
interval: TimeSpan.fromMilliseconds(5),
|
|
526
734
|
});
|
|
527
|
-
|
|
528
|
-
expect(result).toBe(false);
|
|
735
|
+
expect(result).toEqual(resultSuccess(RETURN_VALUE));
|
|
529
736
|
});
|
|
530
|
-
test("Should
|
|
737
|
+
test("Should return ResultFailure<KeyAlreadyAcquiredLockError> when key is unexpireable and acquired by same owner", async () => {
|
|
531
738
|
const key = "a";
|
|
532
739
|
const ttl = null;
|
|
533
|
-
const
|
|
534
|
-
const lock = lockProvider.create(key, {
|
|
535
|
-
ttl,
|
|
536
|
-
owner,
|
|
537
|
-
});
|
|
740
|
+
const lock = lockProvider.create(key, { ttl });
|
|
538
741
|
await lock.acquire();
|
|
539
|
-
await lock.
|
|
540
|
-
|
|
541
|
-
|
|
742
|
+
const result = await lock.runBlocking(() => {
|
|
743
|
+
return Promise.resolve(RETURN_VALUE);
|
|
744
|
+
}, {
|
|
745
|
+
time: TimeSpan.fromMilliseconds(5),
|
|
746
|
+
interval: TimeSpan.fromMilliseconds(5),
|
|
747
|
+
});
|
|
748
|
+
expect(result.type).toBe(RESULT.FAILURE);
|
|
749
|
+
expect(result.error).toBeInstanceOf(KeyAlreadyAcquiredLockError);
|
|
542
750
|
});
|
|
543
|
-
test("Should
|
|
751
|
+
test("Should return ResultFailure<KeyAlreadyAcquiredLockError> when key is unexpired and acquired by same owner", async () => {
|
|
544
752
|
const key = "a";
|
|
545
|
-
const ttl =
|
|
546
|
-
const owner = "b";
|
|
753
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
547
754
|
const lock = lockProvider.create(key, {
|
|
548
755
|
ttl,
|
|
549
|
-
owner,
|
|
550
756
|
});
|
|
551
757
|
await lock.acquire();
|
|
552
|
-
await lock.
|
|
553
|
-
|
|
554
|
-
|
|
758
|
+
const result = await lock.runBlocking(() => {
|
|
759
|
+
return Promise.resolve(RETURN_VALUE);
|
|
760
|
+
}, {
|
|
761
|
+
time: TimeSpan.fromMilliseconds(5),
|
|
762
|
+
interval: TimeSpan.fromMilliseconds(5),
|
|
763
|
+
});
|
|
764
|
+
expect(result.type).toBe(RESULT.FAILURE);
|
|
765
|
+
expect(result.error).toBeInstanceOf(KeyAlreadyAcquiredLockError);
|
|
555
766
|
});
|
|
556
|
-
|
|
557
|
-
describe("method: releaseOrFail", () => {
|
|
558
|
-
test("Should not throw UnownedReleaseLockError when released by same owner", async () => {
|
|
767
|
+
test("Should return ResultFailure<KeyAlreadyAcquiredLockError> when key is unexpireable and acquired by different owner", async () => {
|
|
559
768
|
const key = "a";
|
|
560
769
|
const ttl = null;
|
|
561
|
-
|
|
562
|
-
const
|
|
563
|
-
ttl
|
|
564
|
-
|
|
770
|
+
await lockProvider.create(key, { ttl }).acquire();
|
|
771
|
+
const result = await lockProvider
|
|
772
|
+
.create(key, { ttl })
|
|
773
|
+
.runBlocking(() => {
|
|
774
|
+
return Promise.resolve(RETURN_VALUE);
|
|
775
|
+
}, {
|
|
776
|
+
time: TimeSpan.fromMilliseconds(5),
|
|
777
|
+
interval: TimeSpan.fromMilliseconds(5),
|
|
565
778
|
});
|
|
566
|
-
|
|
567
|
-
|
|
568
|
-
await expect(result).resolves.toBeUndefined();
|
|
779
|
+
expect(result.type).toBe(RESULT.FAILURE);
|
|
780
|
+
expect(result.error).toBeInstanceOf(KeyAlreadyAcquiredLockError);
|
|
569
781
|
});
|
|
570
|
-
test("Should
|
|
782
|
+
test("Should return ResultFailure<KeyAlreadyAcquiredLockError> when key is unexpired and acquired by different owner", async () => {
|
|
571
783
|
const key = "a";
|
|
572
|
-
const ttl =
|
|
573
|
-
|
|
784
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
785
|
+
await lockProvider.create(key, { ttl }).acquire();
|
|
786
|
+
const result = await lockProvider
|
|
787
|
+
.create(key, { ttl })
|
|
788
|
+
.runBlocking(() => {
|
|
789
|
+
return Promise.resolve(RETURN_VALUE);
|
|
790
|
+
}, {
|
|
791
|
+
time: TimeSpan.fromMilliseconds(5),
|
|
792
|
+
interval: TimeSpan.fromMilliseconds(5),
|
|
793
|
+
});
|
|
794
|
+
expect(result.type).toBe(RESULT.FAILURE);
|
|
795
|
+
expect(result.error).toBeInstanceOf(KeyAlreadyAcquiredLockError);
|
|
796
|
+
});
|
|
797
|
+
test("Should retry acquire the lock", async () => {
|
|
798
|
+
const key = "a";
|
|
799
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
574
800
|
const lock1 = lockProvider.create(key, {
|
|
575
801
|
ttl,
|
|
576
|
-
owner: owner1,
|
|
577
802
|
});
|
|
578
803
|
await lock1.acquire();
|
|
579
|
-
|
|
804
|
+
let index = 0;
|
|
805
|
+
await lockProvider.addListener(LOCK_EVENTS.UNAVAILABLE, (_event) => {
|
|
806
|
+
index++;
|
|
807
|
+
});
|
|
580
808
|
const lock2 = lockProvider.create(key, {
|
|
581
809
|
ttl,
|
|
582
|
-
owner: owner2,
|
|
583
810
|
});
|
|
584
|
-
|
|
585
|
-
|
|
811
|
+
await lock2.runBlocking(() => {
|
|
812
|
+
return Promise.resolve(RETURN_VALUE);
|
|
813
|
+
}, {
|
|
814
|
+
time: TimeSpan.fromMilliseconds(55),
|
|
815
|
+
interval: TimeSpan.fromMilliseconds(5),
|
|
816
|
+
});
|
|
817
|
+
expect(index).toBeGreaterThan(1);
|
|
586
818
|
});
|
|
587
|
-
|
|
819
|
+
});
|
|
820
|
+
describe("method: runBlockingOrFail", () => {
|
|
821
|
+
test("Should call acquireBlockingOrFail method", async () => {
|
|
588
822
|
const key = "a";
|
|
589
823
|
const ttl = null;
|
|
590
|
-
const owner = "b";
|
|
591
824
|
const lock = lockProvider.create(key, {
|
|
592
825
|
ttl,
|
|
593
|
-
owner,
|
|
594
826
|
});
|
|
595
|
-
|
|
596
|
-
await lock.
|
|
597
|
-
|
|
598
|
-
|
|
827
|
+
const acquireSpy = vi.spyOn(lock, "acquireBlockingOrFail");
|
|
828
|
+
await lock.runBlockingOrFail(() => {
|
|
829
|
+
return Promise.resolve(RETURN_VALUE);
|
|
830
|
+
}, {
|
|
831
|
+
time: TimeSpan.fromMilliseconds(5),
|
|
832
|
+
interval: TimeSpan.fromMilliseconds(5),
|
|
833
|
+
});
|
|
834
|
+
expect(acquireSpy).toHaveBeenCalledTimes(1);
|
|
599
835
|
});
|
|
600
|
-
test("Should
|
|
836
|
+
test("Should call acquireBlockingOrFail before release method", async () => {
|
|
601
837
|
const key = "a";
|
|
602
838
|
const ttl = null;
|
|
603
|
-
const owner = "b";
|
|
604
839
|
const lock = lockProvider.create(key, {
|
|
605
840
|
ttl,
|
|
606
|
-
owner,
|
|
607
841
|
});
|
|
608
|
-
|
|
609
|
-
|
|
610
|
-
|
|
611
|
-
|
|
842
|
+
const acquireSpy = vi.spyOn(lock, "acquireBlockingOrFail");
|
|
843
|
+
const releaseSpy = vi.spyOn(lock, "release");
|
|
844
|
+
await lock.runBlockingOrFail(() => {
|
|
845
|
+
return Promise.resolve(RETURN_VALUE);
|
|
846
|
+
}, {
|
|
847
|
+
time: TimeSpan.fromMilliseconds(5),
|
|
848
|
+
interval: TimeSpan.fromMilliseconds(5),
|
|
849
|
+
});
|
|
850
|
+
expect(acquireSpy).toHaveBeenCalledBefore(releaseSpy);
|
|
612
851
|
});
|
|
613
|
-
|
|
614
|
-
describe("method: forceRelease", () => {
|
|
615
|
-
test("Should release lock no regardless of the owner", async () => {
|
|
852
|
+
test("Should call release method", async () => {
|
|
616
853
|
const key = "a";
|
|
617
854
|
const ttl = null;
|
|
618
|
-
const
|
|
619
|
-
const lock1 = lockProvider.create(key, {
|
|
855
|
+
const lock = lockProvider.create(key, {
|
|
620
856
|
ttl,
|
|
621
|
-
owner: owner1,
|
|
622
857
|
});
|
|
623
|
-
|
|
624
|
-
|
|
625
|
-
|
|
626
|
-
|
|
627
|
-
|
|
858
|
+
const releaseSpy = vi.spyOn(lock, "release");
|
|
859
|
+
await lock.runBlockingOrFail(() => {
|
|
860
|
+
return Promise.resolve(RETURN_VALUE);
|
|
861
|
+
}, {
|
|
862
|
+
time: TimeSpan.fromMilliseconds(5),
|
|
863
|
+
interval: TimeSpan.fromMilliseconds(5),
|
|
628
864
|
});
|
|
629
|
-
|
|
630
|
-
const result = await lock1.acquire();
|
|
631
|
-
expect(result).toBe(true);
|
|
865
|
+
expect(releaseSpy).toHaveBeenCalledTimes(1);
|
|
632
866
|
});
|
|
633
|
-
test("Should
|
|
867
|
+
test("Should call release after acquireBlockingOrFail method", async () => {
|
|
634
868
|
const key = "a";
|
|
635
869
|
const ttl = null;
|
|
636
|
-
const owner = "b";
|
|
637
870
|
const lock = lockProvider.create(key, {
|
|
638
871
|
ttl,
|
|
639
|
-
owner,
|
|
640
872
|
});
|
|
641
|
-
|
|
642
|
-
|
|
643
|
-
|
|
644
|
-
|
|
873
|
+
const releaseSpy = vi.spyOn(lock, "release");
|
|
874
|
+
const acquireSpy = vi.spyOn(lock, "acquireBlockingOrFail");
|
|
875
|
+
await lock.runBlockingOrFail(() => {
|
|
876
|
+
return Promise.resolve(RETURN_VALUE);
|
|
877
|
+
}, {
|
|
878
|
+
time: TimeSpan.fromMilliseconds(5),
|
|
879
|
+
interval: TimeSpan.fromMilliseconds(5),
|
|
880
|
+
});
|
|
881
|
+
expect(releaseSpy).toHaveBeenCalledAfter(acquireSpy);
|
|
645
882
|
});
|
|
646
|
-
test("Should
|
|
883
|
+
test("Should call release when an error is thrown", async () => {
|
|
647
884
|
const key = "a";
|
|
648
885
|
const ttl = null;
|
|
649
|
-
const owner = "b";
|
|
650
886
|
const lock = lockProvider.create(key, {
|
|
651
887
|
ttl,
|
|
652
|
-
owner,
|
|
653
888
|
});
|
|
654
|
-
|
|
655
|
-
|
|
656
|
-
|
|
657
|
-
|
|
889
|
+
const releaseSpy = vi.spyOn(lock, "release");
|
|
890
|
+
try {
|
|
891
|
+
await lock.runBlockingOrFail(() => {
|
|
892
|
+
return Promise.reject(new Error());
|
|
893
|
+
}, {
|
|
894
|
+
time: TimeSpan.fromMilliseconds(5),
|
|
895
|
+
interval: TimeSpan.fromMilliseconds(5),
|
|
896
|
+
});
|
|
897
|
+
}
|
|
898
|
+
catch {
|
|
899
|
+
/* EMPTY */
|
|
900
|
+
}
|
|
901
|
+
expect(releaseSpy).toHaveBeenCalledTimes(1);
|
|
658
902
|
});
|
|
659
|
-
|
|
660
|
-
describe("method: isExpired", () => {
|
|
661
|
-
test("Should return false when lock has no expiration", async () => {
|
|
903
|
+
test("Should propagate thrown error", async () => {
|
|
662
904
|
const key = "a";
|
|
663
905
|
const ttl = null;
|
|
664
|
-
const owner = "b";
|
|
665
906
|
const lock = lockProvider.create(key, {
|
|
666
907
|
ttl,
|
|
667
|
-
owner,
|
|
668
908
|
});
|
|
669
|
-
|
|
670
|
-
|
|
671
|
-
|
|
909
|
+
class CustomError extends Error {
|
|
910
|
+
}
|
|
911
|
+
const error = lock.runBlockingOrFail(() => {
|
|
912
|
+
return Promise.reject(new CustomError());
|
|
913
|
+
}, {
|
|
914
|
+
time: TimeSpan.fromMilliseconds(5),
|
|
915
|
+
interval: TimeSpan.fromMilliseconds(5),
|
|
916
|
+
});
|
|
917
|
+
await expect(error).rejects.toBeInstanceOf(CustomError);
|
|
672
918
|
});
|
|
673
|
-
test("Should
|
|
919
|
+
test("Should call handler function when key doesnt exists", async () => {
|
|
674
920
|
const key = "a";
|
|
675
|
-
const
|
|
676
|
-
const
|
|
677
|
-
|
|
921
|
+
const ttl = null;
|
|
922
|
+
const handlerFn = vi.fn(() => {
|
|
923
|
+
return Promise.resolve(RETURN_VALUE);
|
|
924
|
+
});
|
|
925
|
+
await lockProvider
|
|
926
|
+
.create(key, {
|
|
678
927
|
ttl,
|
|
679
|
-
|
|
928
|
+
})
|
|
929
|
+
.runBlockingOrFail(handlerFn, {
|
|
930
|
+
time: TimeSpan.fromMilliseconds(5),
|
|
931
|
+
interval: TimeSpan.fromMilliseconds(5),
|
|
680
932
|
});
|
|
681
|
-
|
|
682
|
-
const result = await lock.isExpired();
|
|
683
|
-
expect(result).toBe(false);
|
|
933
|
+
expect(handlerFn).toHaveBeenCalledTimes(1);
|
|
684
934
|
});
|
|
685
|
-
test("Should
|
|
935
|
+
test("Should call handler function when key is expired", async () => {
|
|
686
936
|
const key = "a";
|
|
687
|
-
const
|
|
688
|
-
|
|
689
|
-
|
|
690
|
-
|
|
691
|
-
|
|
937
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
938
|
+
await lockProvider.create(key, { ttl }).acquire();
|
|
939
|
+
await delay(ttl);
|
|
940
|
+
const handlerFn = vi.fn(() => {
|
|
941
|
+
return Promise.resolve(RETURN_VALUE);
|
|
942
|
+
});
|
|
943
|
+
await lockProvider
|
|
944
|
+
.create(key, { ttl })
|
|
945
|
+
.runBlockingOrFail(handlerFn, {
|
|
946
|
+
time: TimeSpan.fromMilliseconds(5),
|
|
947
|
+
interval: TimeSpan.fromMilliseconds(5),
|
|
692
948
|
});
|
|
693
|
-
|
|
694
|
-
await LazyPromise.delay(ttl.addMilliseconds(25));
|
|
695
|
-
const result = await lock.isExpired();
|
|
696
|
-
expect(result).toBe(true);
|
|
949
|
+
expect(handlerFn).toHaveBeenCalledTimes(1);
|
|
697
950
|
});
|
|
698
|
-
|
|
699
|
-
describe("method: isLocked", () => {
|
|
700
|
-
test("Should return true when lock has no expiration", async () => {
|
|
951
|
+
test("Should not call handler function when key is unexpireable and acquired by same owner", async () => {
|
|
701
952
|
const key = "a";
|
|
702
953
|
const ttl = null;
|
|
703
|
-
const
|
|
704
|
-
const lock = lockProvider.create(key, {
|
|
705
|
-
ttl,
|
|
706
|
-
owner,
|
|
707
|
-
});
|
|
954
|
+
const lock = lockProvider.create(key, { ttl });
|
|
708
955
|
await lock.acquire();
|
|
709
|
-
const
|
|
710
|
-
|
|
711
|
-
});
|
|
712
|
-
test("Should return true when lock has not expired", async () => {
|
|
713
|
-
const key = "a";
|
|
714
|
-
const owner = "b";
|
|
715
|
-
const ttl = TTL;
|
|
716
|
-
const lock = lockProvider.create(key, {
|
|
717
|
-
ttl,
|
|
718
|
-
owner,
|
|
956
|
+
const handlerFn = vi.fn(() => {
|
|
957
|
+
return Promise.resolve(RETURN_VALUE);
|
|
719
958
|
});
|
|
720
|
-
|
|
721
|
-
|
|
722
|
-
|
|
959
|
+
try {
|
|
960
|
+
await lock.runBlockingOrFail(handlerFn, {
|
|
961
|
+
time: TimeSpan.fromMilliseconds(5),
|
|
962
|
+
interval: TimeSpan.fromMilliseconds(5),
|
|
963
|
+
});
|
|
964
|
+
}
|
|
965
|
+
catch {
|
|
966
|
+
/* EMPTY */
|
|
967
|
+
}
|
|
968
|
+
expect(handlerFn).toHaveBeenCalledTimes(0);
|
|
723
969
|
});
|
|
724
|
-
test("Should
|
|
970
|
+
test("Should not call handler function when key is unexpired and acquired by same owner", async () => {
|
|
725
971
|
const key = "a";
|
|
726
|
-
const
|
|
727
|
-
const ttl = TTL;
|
|
972
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
728
973
|
const lock = lockProvider.create(key, {
|
|
729
974
|
ttl,
|
|
730
|
-
owner,
|
|
731
975
|
});
|
|
732
976
|
await lock.acquire();
|
|
733
|
-
|
|
734
|
-
|
|
735
|
-
|
|
977
|
+
const handlerFn = vi.fn(() => {
|
|
978
|
+
return Promise.resolve(RETURN_VALUE);
|
|
979
|
+
});
|
|
980
|
+
try {
|
|
981
|
+
await lock.runBlockingOrFail(handlerFn, {
|
|
982
|
+
time: TimeSpan.fromMilliseconds(5),
|
|
983
|
+
interval: TimeSpan.fromMilliseconds(5),
|
|
984
|
+
});
|
|
985
|
+
}
|
|
986
|
+
catch {
|
|
987
|
+
/* EMPTY */
|
|
988
|
+
}
|
|
989
|
+
expect(handlerFn).toHaveBeenCalledTimes(0);
|
|
736
990
|
});
|
|
737
|
-
|
|
738
|
-
describe("method: refresh", () => {
|
|
739
|
-
test("Should return true when refreshed by same owner", async () => {
|
|
991
|
+
test("Should not call handler function when key is unexpireable and acquired by different owner", async () => {
|
|
740
992
|
const key = "a";
|
|
741
|
-
const ttl =
|
|
742
|
-
|
|
743
|
-
const
|
|
744
|
-
|
|
745
|
-
owner,
|
|
993
|
+
const ttl = null;
|
|
994
|
+
await lockProvider.create(key, { ttl }).acquire();
|
|
995
|
+
const handlerFn = vi.fn(() => {
|
|
996
|
+
return Promise.resolve(RETURN_VALUE);
|
|
746
997
|
});
|
|
747
|
-
|
|
748
|
-
|
|
749
|
-
|
|
750
|
-
|
|
998
|
+
try {
|
|
999
|
+
await lockProvider
|
|
1000
|
+
.create(key, { ttl })
|
|
1001
|
+
.runBlockingOrFail(handlerFn, {
|
|
1002
|
+
time: TimeSpan.fromMilliseconds(5),
|
|
1003
|
+
interval: TimeSpan.fromMilliseconds(5),
|
|
1004
|
+
});
|
|
1005
|
+
}
|
|
1006
|
+
catch {
|
|
1007
|
+
/* EMPTY */
|
|
1008
|
+
}
|
|
1009
|
+
expect(handlerFn).not.toHaveBeenCalled();
|
|
751
1010
|
});
|
|
752
|
-
test("Should
|
|
1011
|
+
test("Should not call handler function when key is unexpired and acquired by different owner", async () => {
|
|
753
1012
|
const key = "a";
|
|
754
|
-
const ttl =
|
|
755
|
-
|
|
756
|
-
const
|
|
757
|
-
|
|
758
|
-
owner: owner1,
|
|
1013
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
1014
|
+
await lockProvider.create(key, { ttl }).acquire();
|
|
1015
|
+
const handlerFn = vi.fn(() => {
|
|
1016
|
+
return Promise.resolve(RETURN_VALUE);
|
|
759
1017
|
});
|
|
760
|
-
|
|
761
|
-
|
|
762
|
-
|
|
1018
|
+
try {
|
|
1019
|
+
await lockProvider
|
|
1020
|
+
.create(key, { ttl })
|
|
1021
|
+
.runBlockingOrFail(handlerFn, {
|
|
1022
|
+
time: TimeSpan.fromMilliseconds(5),
|
|
1023
|
+
interval: TimeSpan.fromMilliseconds(5),
|
|
1024
|
+
});
|
|
1025
|
+
}
|
|
1026
|
+
catch {
|
|
1027
|
+
/* EMPTY */
|
|
1028
|
+
}
|
|
1029
|
+
expect(handlerFn).not.toHaveBeenCalled();
|
|
1030
|
+
});
|
|
1031
|
+
test("Should return value when key doesnt exists", async () => {
|
|
1032
|
+
const key = "a";
|
|
1033
|
+
const ttl = null;
|
|
1034
|
+
const result = await lockProvider
|
|
1035
|
+
.create(key, {
|
|
763
1036
|
ttl,
|
|
764
|
-
|
|
1037
|
+
})
|
|
1038
|
+
.runBlockingOrFail(() => {
|
|
1039
|
+
return Promise.resolve(RETURN_VALUE);
|
|
1040
|
+
}, {
|
|
1041
|
+
time: TimeSpan.fromMilliseconds(5),
|
|
1042
|
+
interval: TimeSpan.fromMilliseconds(5),
|
|
765
1043
|
});
|
|
766
|
-
|
|
767
|
-
expect(result).toBe(false);
|
|
1044
|
+
expect(result).toBe(RETURN_VALUE);
|
|
768
1045
|
});
|
|
769
|
-
test("Should
|
|
1046
|
+
test("Should return value when key is expired", async () => {
|
|
770
1047
|
const key = "a";
|
|
771
|
-
const ttl =
|
|
772
|
-
|
|
773
|
-
|
|
774
|
-
|
|
775
|
-
|
|
1048
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
1049
|
+
await lockProvider.create(key, { ttl }).acquire();
|
|
1050
|
+
await delay(ttl);
|
|
1051
|
+
const result = await lockProvider
|
|
1052
|
+
.create(key, { ttl })
|
|
1053
|
+
.runBlockingOrFail(() => {
|
|
1054
|
+
return Promise.resolve(RETURN_VALUE);
|
|
1055
|
+
}, {
|
|
1056
|
+
time: TimeSpan.fromMilliseconds(5),
|
|
1057
|
+
interval: TimeSpan.fromMilliseconds(5),
|
|
776
1058
|
});
|
|
1059
|
+
expect(result).toBe(RETURN_VALUE);
|
|
1060
|
+
});
|
|
1061
|
+
test("Should throw KeyAlreadyAcquiredLockError when key is unexpireable and acquired by same owner", async () => {
|
|
1062
|
+
const key = "a";
|
|
1063
|
+
const ttl = null;
|
|
1064
|
+
const lock = lockProvider.create(key, { ttl });
|
|
777
1065
|
await lock.acquire();
|
|
778
|
-
|
|
779
|
-
|
|
780
|
-
|
|
781
|
-
|
|
1066
|
+
const result = lock.runBlockingOrFail(() => {
|
|
1067
|
+
return Promise.resolve(RETURN_VALUE);
|
|
1068
|
+
}, {
|
|
1069
|
+
time: TimeSpan.fromMilliseconds(5),
|
|
1070
|
+
interval: TimeSpan.fromMilliseconds(5),
|
|
1071
|
+
});
|
|
1072
|
+
await expect(result).rejects.toBeInstanceOf(KeyAlreadyAcquiredLockError);
|
|
782
1073
|
});
|
|
783
|
-
|
|
784
|
-
describe("method: refreshOrFail", () => {
|
|
785
|
-
test("Should not throw UnownedRefreshLockError when refreshed by same owner", async () => {
|
|
1074
|
+
test("Should throw KeyAlreadyAcquiredLockError when key is unexpired and acquired by same owner", async () => {
|
|
786
1075
|
const key = "a";
|
|
787
|
-
const ttl =
|
|
788
|
-
const owner = "b";
|
|
1076
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
789
1077
|
const lock = lockProvider.create(key, {
|
|
790
1078
|
ttl,
|
|
791
|
-
owner,
|
|
792
1079
|
});
|
|
793
1080
|
await lock.acquire();
|
|
794
|
-
|
|
795
|
-
|
|
796
|
-
|
|
1081
|
+
const result = lock.runBlockingOrFail(() => {
|
|
1082
|
+
return Promise.resolve(RETURN_VALUE);
|
|
1083
|
+
}, {
|
|
1084
|
+
time: TimeSpan.fromMilliseconds(5),
|
|
1085
|
+
interval: TimeSpan.fromMilliseconds(5),
|
|
1086
|
+
});
|
|
1087
|
+
await expect(result).rejects.toBeInstanceOf(KeyAlreadyAcquiredLockError);
|
|
1088
|
+
});
|
|
1089
|
+
test("Should throw KeyAlreadyAcquiredLockError when key is unexpireable and acquired by different owner", async () => {
|
|
1090
|
+
const key = "a";
|
|
1091
|
+
const ttl = null;
|
|
1092
|
+
await lockProvider.create(key, { ttl }).acquire();
|
|
1093
|
+
const result = lockProvider
|
|
1094
|
+
.create(key, { ttl })
|
|
1095
|
+
.runBlockingOrFail(() => {
|
|
1096
|
+
return Promise.resolve(RETURN_VALUE);
|
|
1097
|
+
}, {
|
|
1098
|
+
time: TimeSpan.fromMilliseconds(5),
|
|
1099
|
+
interval: TimeSpan.fromMilliseconds(5),
|
|
1100
|
+
});
|
|
1101
|
+
await expect(result).rejects.toBeInstanceOf(KeyAlreadyAcquiredLockError);
|
|
1102
|
+
});
|
|
1103
|
+
test("Should throw KeyAlreadyAcquiredLockError when key is unexpired and acquired by different owner", async () => {
|
|
1104
|
+
const key = "a";
|
|
1105
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
1106
|
+
await lockProvider.create(key, { ttl }).acquire();
|
|
1107
|
+
const result = lockProvider
|
|
1108
|
+
.create(key, { ttl })
|
|
1109
|
+
.runBlockingOrFail(() => {
|
|
1110
|
+
return Promise.resolve(RETURN_VALUE);
|
|
1111
|
+
}, {
|
|
1112
|
+
time: TimeSpan.fromMilliseconds(5),
|
|
1113
|
+
interval: TimeSpan.fromMilliseconds(5),
|
|
1114
|
+
});
|
|
1115
|
+
await expect(result).rejects.toBeInstanceOf(KeyAlreadyAcquiredLockError);
|
|
797
1116
|
});
|
|
798
|
-
test("Should
|
|
1117
|
+
test("Should retry acquire the lock", async () => {
|
|
799
1118
|
const key = "a";
|
|
800
|
-
const ttl =
|
|
801
|
-
const owner1 = "b";
|
|
1119
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
802
1120
|
const lock1 = lockProvider.create(key, {
|
|
803
1121
|
ttl,
|
|
804
|
-
owner: owner1,
|
|
805
1122
|
});
|
|
806
1123
|
await lock1.acquire();
|
|
807
|
-
|
|
1124
|
+
let index = 0;
|
|
1125
|
+
await lockProvider.addListener(LOCK_EVENTS.UNAVAILABLE, (_event) => {
|
|
1126
|
+
index++;
|
|
1127
|
+
});
|
|
808
1128
|
const lock2 = lockProvider.create(key, {
|
|
809
1129
|
ttl,
|
|
810
|
-
owner: owner2,
|
|
811
1130
|
});
|
|
812
|
-
|
|
813
|
-
|
|
1131
|
+
try {
|
|
1132
|
+
await lock2.runBlockingOrFail(() => {
|
|
1133
|
+
return Promise.resolve(RETURN_VALUE);
|
|
1134
|
+
}, {
|
|
1135
|
+
time: TimeSpan.fromMilliseconds(55),
|
|
1136
|
+
interval: TimeSpan.fromMilliseconds(5),
|
|
1137
|
+
});
|
|
1138
|
+
}
|
|
1139
|
+
catch {
|
|
1140
|
+
/* EMPTY */
|
|
1141
|
+
}
|
|
1142
|
+
expect(index).toBeGreaterThan(1);
|
|
1143
|
+
});
|
|
1144
|
+
});
|
|
1145
|
+
describe("method: acquire", () => {
|
|
1146
|
+
test("Should return true when key doesnt exists", async () => {
|
|
1147
|
+
const key = "a";
|
|
1148
|
+
const ttl = null;
|
|
1149
|
+
const result = await lockProvider
|
|
1150
|
+
.create(key, {
|
|
1151
|
+
ttl,
|
|
1152
|
+
})
|
|
1153
|
+
.acquire();
|
|
1154
|
+
expect(result).toBe(true);
|
|
814
1155
|
});
|
|
815
|
-
test("Should
|
|
1156
|
+
test("Should return true when key is expired", async () => {
|
|
816
1157
|
const key = "a";
|
|
817
|
-
const ttl =
|
|
818
|
-
|
|
1158
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
1159
|
+
await lockProvider.create(key, { ttl }).acquire();
|
|
1160
|
+
await delay(ttl);
|
|
1161
|
+
const result = await lockProvider
|
|
1162
|
+
.create(key, { ttl })
|
|
1163
|
+
.acquire();
|
|
1164
|
+
expect(result).toBe(true);
|
|
1165
|
+
});
|
|
1166
|
+
test("Should return false when key is unexpireable and acquired by same owner", async () => {
|
|
1167
|
+
const key = "a";
|
|
1168
|
+
const ttl = null;
|
|
1169
|
+
const lock = lockProvider.create(key, { ttl });
|
|
1170
|
+
await lock.acquire();
|
|
1171
|
+
const result = await lock.acquire();
|
|
1172
|
+
expect(result).toBe(false);
|
|
1173
|
+
});
|
|
1174
|
+
test("Should return false when key is unexpired and acquired by same owner", async () => {
|
|
1175
|
+
const key = "a";
|
|
1176
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
819
1177
|
const lock = lockProvider.create(key, {
|
|
820
1178
|
ttl,
|
|
821
|
-
owner,
|
|
822
1179
|
});
|
|
823
|
-
await lock.
|
|
824
|
-
await
|
|
825
|
-
|
|
826
|
-
|
|
827
|
-
|
|
1180
|
+
await lock.acquire();
|
|
1181
|
+
const result = await lock.acquire();
|
|
1182
|
+
expect(result).toBe(false);
|
|
1183
|
+
});
|
|
1184
|
+
test("Should return false when key is unexpireable and acquired by different owner", async () => {
|
|
1185
|
+
const key = "a";
|
|
1186
|
+
const ttl = null;
|
|
1187
|
+
await lockProvider.create(key, { ttl }).acquire();
|
|
1188
|
+
const result = await lockProvider
|
|
1189
|
+
.create(key, { ttl })
|
|
1190
|
+
.acquire();
|
|
1191
|
+
expect(result).toBe(false);
|
|
1192
|
+
});
|
|
1193
|
+
test("Should return false when key is unexpired and acquired by different owner", async () => {
|
|
1194
|
+
const key = "a";
|
|
1195
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
1196
|
+
await lockProvider.create(key, { ttl }).acquire();
|
|
1197
|
+
const result = await lockProvider
|
|
1198
|
+
.create(key, { ttl })
|
|
1199
|
+
.acquire();
|
|
1200
|
+
expect(result).toBe(false);
|
|
828
1201
|
});
|
|
829
1202
|
});
|
|
830
|
-
describe("method:
|
|
831
|
-
test("Should
|
|
1203
|
+
describe("method: acquireOrFail", () => {
|
|
1204
|
+
test("Should not throw error when key doesnt exists", async () => {
|
|
832
1205
|
const key = "a";
|
|
833
1206
|
const ttl = null;
|
|
834
|
-
const
|
|
1207
|
+
const result = lockProvider
|
|
1208
|
+
.create(key, {
|
|
1209
|
+
ttl,
|
|
1210
|
+
})
|
|
1211
|
+
.acquireOrFail();
|
|
1212
|
+
await expect(result).resolves.toBeUndefined();
|
|
1213
|
+
});
|
|
1214
|
+
test("Should not throw error when key is expired", async () => {
|
|
1215
|
+
const key = "a";
|
|
1216
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
1217
|
+
await lockProvider.create(key, { ttl }).acquire();
|
|
1218
|
+
await delay(ttl);
|
|
1219
|
+
const result = lockProvider
|
|
1220
|
+
.create(key, { ttl })
|
|
1221
|
+
.acquireOrFail();
|
|
1222
|
+
await expect(result).resolves.toBeUndefined();
|
|
1223
|
+
});
|
|
1224
|
+
test("Should throw KeyAlreadyAcquiredLockError when key is unexpireable and acquired by same owner", async () => {
|
|
1225
|
+
const key = "a";
|
|
1226
|
+
const ttl = null;
|
|
1227
|
+
const lock = lockProvider.create(key, { ttl });
|
|
1228
|
+
await lock.acquire();
|
|
1229
|
+
const result = lock.acquireOrFail();
|
|
1230
|
+
await expect(result).rejects.toBeInstanceOf(KeyAlreadyAcquiredLockError);
|
|
1231
|
+
});
|
|
1232
|
+
test("Should throw KeyAlreadyAcquiredLockError when key is unexpired and acquired by same owner", async () => {
|
|
1233
|
+
const key = "a";
|
|
1234
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
835
1235
|
const lock = lockProvider.create(key, {
|
|
836
1236
|
ttl,
|
|
837
|
-
owner,
|
|
838
1237
|
});
|
|
839
|
-
|
|
840
|
-
|
|
1238
|
+
await lock.acquire();
|
|
1239
|
+
const result = lock.acquireOrFail();
|
|
1240
|
+
await expect(result).rejects.toBeInstanceOf(KeyAlreadyAcquiredLockError);
|
|
841
1241
|
});
|
|
842
|
-
test("Should
|
|
1242
|
+
test("Should throw KeyAlreadyAcquiredLockError when key is unexpireable and acquired by different owner", async () => {
|
|
843
1243
|
const key = "a";
|
|
844
1244
|
const ttl = null;
|
|
845
|
-
|
|
846
|
-
const
|
|
1245
|
+
await lockProvider.create(key, { ttl }).acquire();
|
|
1246
|
+
const result = lockProvider
|
|
1247
|
+
.create(key, { ttl })
|
|
1248
|
+
.acquireOrFail();
|
|
1249
|
+
await expect(result).rejects.toBeInstanceOf(KeyAlreadyAcquiredLockError);
|
|
1250
|
+
});
|
|
1251
|
+
test("Should throw KeyAlreadyAcquiredLockError when key is unexpired and acquired by different owner", async () => {
|
|
1252
|
+
const key = "a";
|
|
1253
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
1254
|
+
await lockProvider.create(key, { ttl }).acquire();
|
|
1255
|
+
const result = lockProvider
|
|
1256
|
+
.create(key, { ttl })
|
|
1257
|
+
.acquireOrFail();
|
|
1258
|
+
await expect(result).rejects.toBeInstanceOf(KeyAlreadyAcquiredLockError);
|
|
1259
|
+
});
|
|
1260
|
+
});
|
|
1261
|
+
describe("method: acquireBlocking", () => {
|
|
1262
|
+
test("Should return true when key doesnt exists", async () => {
|
|
1263
|
+
const key = "a";
|
|
1264
|
+
const ttl = null;
|
|
1265
|
+
const result = await lockProvider
|
|
1266
|
+
.create(key, {
|
|
847
1267
|
ttl,
|
|
848
|
-
|
|
1268
|
+
})
|
|
1269
|
+
.acquireBlocking({
|
|
1270
|
+
time: TimeSpan.fromMilliseconds(5),
|
|
1271
|
+
interval: TimeSpan.fromMilliseconds(5),
|
|
1272
|
+
});
|
|
1273
|
+
expect(result).toBe(true);
|
|
1274
|
+
});
|
|
1275
|
+
test("Should return true when key is expired", async () => {
|
|
1276
|
+
const key = "a";
|
|
1277
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
1278
|
+
await lockProvider.create(key, { ttl }).acquire();
|
|
1279
|
+
await delay(ttl);
|
|
1280
|
+
const result = await lockProvider
|
|
1281
|
+
.create(key, { ttl })
|
|
1282
|
+
.acquireBlocking({
|
|
1283
|
+
time: TimeSpan.fromMilliseconds(5),
|
|
1284
|
+
interval: TimeSpan.fromMilliseconds(5),
|
|
849
1285
|
});
|
|
1286
|
+
expect(result).toBe(true);
|
|
1287
|
+
});
|
|
1288
|
+
test("Should return false when key is unexpireable and acquired by same owner", async () => {
|
|
1289
|
+
const key = "a";
|
|
1290
|
+
const ttl = null;
|
|
1291
|
+
const lock = lockProvider.create(key, { ttl });
|
|
850
1292
|
await lock.acquire();
|
|
851
|
-
const result = await lock.
|
|
852
|
-
|
|
1293
|
+
const result = await lock.acquireBlocking({
|
|
1294
|
+
time: TimeSpan.fromMilliseconds(5),
|
|
1295
|
+
interval: TimeSpan.fromMilliseconds(5),
|
|
1296
|
+
});
|
|
1297
|
+
expect(result).toBe(false);
|
|
853
1298
|
});
|
|
854
|
-
test("Should return
|
|
1299
|
+
test("Should return false when key is unexpired and acquired by same owner", async () => {
|
|
855
1300
|
const key = "a";
|
|
856
|
-
const ttl =
|
|
857
|
-
const owner = "b";
|
|
1301
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
858
1302
|
const lock = lockProvider.create(key, {
|
|
859
1303
|
ttl,
|
|
860
|
-
owner,
|
|
861
1304
|
});
|
|
862
1305
|
await lock.acquire();
|
|
863
|
-
const result = await lock.
|
|
864
|
-
|
|
1306
|
+
const result = await lock.acquireBlocking({
|
|
1307
|
+
time: TimeSpan.fromMilliseconds(5),
|
|
1308
|
+
interval: TimeSpan.fromMilliseconds(5),
|
|
1309
|
+
});
|
|
1310
|
+
expect(result).toBe(false);
|
|
865
1311
|
});
|
|
866
|
-
|
|
867
|
-
describe("method: getOwner", () => {
|
|
868
|
-
test("Should return the owner", async () => {
|
|
1312
|
+
test("Should return false when key is unexpireable and acquired by different owner", async () => {
|
|
869
1313
|
const key = "a";
|
|
870
|
-
const
|
|
871
|
-
|
|
872
|
-
|
|
1314
|
+
const ttl = null;
|
|
1315
|
+
await lockProvider.create(key, { ttl }).acquire();
|
|
1316
|
+
const result = await lockProvider
|
|
1317
|
+
.create(key, { ttl })
|
|
1318
|
+
.acquireBlocking({
|
|
1319
|
+
time: TimeSpan.fromMilliseconds(5),
|
|
1320
|
+
interval: TimeSpan.fromMilliseconds(5),
|
|
873
1321
|
});
|
|
874
|
-
|
|
875
|
-
expect(result).toBe(owner);
|
|
1322
|
+
expect(result).toBe(false);
|
|
876
1323
|
});
|
|
877
|
-
test("Should return
|
|
1324
|
+
test("Should return false when key is unexpired and acquired by different owner", async () => {
|
|
878
1325
|
const key = "a";
|
|
879
|
-
const
|
|
880
|
-
|
|
881
|
-
|
|
882
|
-
|
|
1326
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
1327
|
+
await lockProvider.create(key, { ttl }).acquire();
|
|
1328
|
+
const result = await lockProvider
|
|
1329
|
+
.create(key, { ttl })
|
|
1330
|
+
.acquireBlocking({
|
|
1331
|
+
time: TimeSpan.fromMilliseconds(5),
|
|
1332
|
+
interval: TimeSpan.fromMilliseconds(5),
|
|
1333
|
+
});
|
|
1334
|
+
expect(result).toBe(false);
|
|
1335
|
+
});
|
|
1336
|
+
test("Should retry acquire the lock", async () => {
|
|
1337
|
+
const key = "a";
|
|
1338
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
1339
|
+
const lock1 = lockProvider.create(key, {
|
|
1340
|
+
ttl,
|
|
1341
|
+
});
|
|
1342
|
+
await lock1.acquire();
|
|
1343
|
+
let index = 0;
|
|
1344
|
+
await lockProvider.addListener(LOCK_EVENTS.UNAVAILABLE, (_event) => {
|
|
1345
|
+
index++;
|
|
1346
|
+
});
|
|
1347
|
+
const lock2 = lockProvider.create(key, {
|
|
1348
|
+
ttl,
|
|
1349
|
+
});
|
|
1350
|
+
await lock2.acquireBlocking({
|
|
1351
|
+
time: TimeSpan.fromMilliseconds(55),
|
|
1352
|
+
interval: TimeSpan.fromMilliseconds(5),
|
|
1353
|
+
});
|
|
1354
|
+
expect(index).toBeGreaterThan(1);
|
|
883
1355
|
});
|
|
884
1356
|
});
|
|
885
|
-
|
|
886
|
-
|
|
887
|
-
|
|
888
|
-
|
|
889
|
-
|
|
890
|
-
|
|
891
|
-
|
|
892
|
-
|
|
893
|
-
|
|
894
|
-
|
|
895
|
-
|
|
896
|
-
|
|
897
|
-
|
|
898
|
-
|
|
899
|
-
|
|
900
|
-
|
|
901
|
-
|
|
902
|
-
|
|
903
|
-
|
|
904
|
-
|
|
905
|
-
|
|
906
|
-
|
|
907
|
-
|
|
908
|
-
|
|
909
|
-
|
|
910
|
-
|
|
911
|
-
|
|
912
|
-
|
|
913
|
-
|
|
914
|
-
|
|
915
|
-
|
|
916
|
-
|
|
917
|
-
|
|
918
|
-
|
|
919
|
-
|
|
920
|
-
|
|
921
|
-
|
|
922
|
-
|
|
923
|
-
|
|
924
|
-
|
|
925
|
-
|
|
926
|
-
|
|
927
|
-
|
|
928
|
-
|
|
929
|
-
|
|
930
|
-
|
|
931
|
-
|
|
932
|
-
|
|
933
|
-
|
|
934
|
-
|
|
935
|
-
|
|
936
|
-
|
|
937
|
-
|
|
938
|
-
|
|
939
|
-
|
|
940
|
-
|
|
941
|
-
})
|
|
942
|
-
|
|
943
|
-
|
|
944
|
-
|
|
945
|
-
|
|
946
|
-
|
|
947
|
-
});
|
|
948
|
-
|
|
949
|
-
|
|
950
|
-
|
|
951
|
-
|
|
952
|
-
|
|
953
|
-
|
|
954
|
-
|
|
955
|
-
|
|
956
|
-
|
|
957
|
-
|
|
958
|
-
|
|
959
|
-
|
|
960
|
-
|
|
961
|
-
|
|
962
|
-
|
|
963
|
-
|
|
964
|
-
|
|
965
|
-
|
|
966
|
-
|
|
967
|
-
|
|
968
|
-
|
|
969
|
-
|
|
970
|
-
|
|
971
|
-
|
|
972
|
-
|
|
973
|
-
|
|
974
|
-
|
|
975
|
-
|
|
976
|
-
|
|
977
|
-
|
|
978
|
-
});
|
|
979
|
-
|
|
980
|
-
|
|
981
|
-
|
|
982
|
-
|
|
983
|
-
|
|
984
|
-
|
|
985
|
-
|
|
986
|
-
|
|
987
|
-
|
|
988
|
-
|
|
989
|
-
|
|
990
|
-
|
|
991
|
-
|
|
992
|
-
|
|
993
|
-
|
|
994
|
-
|
|
995
|
-
|
|
996
|
-
|
|
997
|
-
|
|
998
|
-
|
|
999
|
-
|
|
1000
|
-
|
|
1001
|
-
|
|
1002
|
-
|
|
1003
|
-
|
|
1004
|
-
|
|
1005
|
-
|
|
1006
|
-
|
|
1007
|
-
|
|
1008
|
-
|
|
1357
|
+
describe("method: acquireBlockingOrFail", () => {
|
|
1358
|
+
test("Should not throw error when key doesnt exists", async () => {
|
|
1359
|
+
const key = "a";
|
|
1360
|
+
const ttl = null;
|
|
1361
|
+
const result = lockProvider
|
|
1362
|
+
.create(key, {
|
|
1363
|
+
ttl,
|
|
1364
|
+
})
|
|
1365
|
+
.acquireBlockingOrFail({
|
|
1366
|
+
time: TimeSpan.fromMilliseconds(5),
|
|
1367
|
+
interval: TimeSpan.fromMilliseconds(5),
|
|
1368
|
+
});
|
|
1369
|
+
await expect(result).resolves.toBeUndefined();
|
|
1370
|
+
});
|
|
1371
|
+
test("Should not throw error when key is expired", async () => {
|
|
1372
|
+
const key = "a";
|
|
1373
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
1374
|
+
await lockProvider.create(key, { ttl }).acquire();
|
|
1375
|
+
await delay(ttl);
|
|
1376
|
+
const result = lockProvider
|
|
1377
|
+
.create(key, { ttl })
|
|
1378
|
+
.acquireBlockingOrFail({
|
|
1379
|
+
time: TimeSpan.fromMilliseconds(5),
|
|
1380
|
+
interval: TimeSpan.fromMilliseconds(5),
|
|
1381
|
+
});
|
|
1382
|
+
await expect(result).resolves.toBeUndefined();
|
|
1383
|
+
});
|
|
1384
|
+
test("Should throw KeyAlreadyAcquiredLockError when key is unexpireable and acquired by same owner", async () => {
|
|
1385
|
+
const key = "a";
|
|
1386
|
+
const ttl = null;
|
|
1387
|
+
const lock = lockProvider.create(key, { ttl });
|
|
1388
|
+
await lock.acquire();
|
|
1389
|
+
const result = lock.acquireBlockingOrFail({
|
|
1390
|
+
time: TimeSpan.fromMilliseconds(5),
|
|
1391
|
+
interval: TimeSpan.fromMilliseconds(5),
|
|
1392
|
+
});
|
|
1393
|
+
await expect(result).rejects.toBeInstanceOf(KeyAlreadyAcquiredLockError);
|
|
1394
|
+
});
|
|
1395
|
+
test("Should throw KeyAlreadyAcquiredLockError when key is unexpired and acquired by same owner", async () => {
|
|
1396
|
+
const key = "a";
|
|
1397
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
1398
|
+
const lock = lockProvider.create(key, {
|
|
1399
|
+
ttl,
|
|
1400
|
+
});
|
|
1401
|
+
await lock.acquire();
|
|
1402
|
+
const result = lock.acquireBlockingOrFail({
|
|
1403
|
+
time: TimeSpan.fromMilliseconds(5),
|
|
1404
|
+
interval: TimeSpan.fromMilliseconds(5),
|
|
1405
|
+
});
|
|
1406
|
+
await expect(result).rejects.toBeInstanceOf(KeyAlreadyAcquiredLockError);
|
|
1407
|
+
});
|
|
1408
|
+
test("Should throw KeyAlreadyAcquiredLockError when key is unexpireable and acquired by different owner", async () => {
|
|
1409
|
+
const key = "a";
|
|
1410
|
+
const ttl = null;
|
|
1411
|
+
await lockProvider.create(key, { ttl }).acquire();
|
|
1412
|
+
const result = lockProvider
|
|
1413
|
+
.create(key, { ttl })
|
|
1414
|
+
.acquireBlockingOrFail({
|
|
1415
|
+
time: TimeSpan.fromMilliseconds(5),
|
|
1416
|
+
interval: TimeSpan.fromMilliseconds(5),
|
|
1417
|
+
});
|
|
1418
|
+
await expect(result).rejects.toBeInstanceOf(KeyAlreadyAcquiredLockError);
|
|
1419
|
+
});
|
|
1420
|
+
test("Should throw KeyAlreadyAcquiredLockError when key is unexpired and acquired by different owner", async () => {
|
|
1421
|
+
const key = "a";
|
|
1422
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
1423
|
+
await lockProvider.create(key, { ttl }).acquire();
|
|
1424
|
+
const result = lockProvider
|
|
1425
|
+
.create(key, { ttl })
|
|
1426
|
+
.acquireBlockingOrFail({
|
|
1427
|
+
time: TimeSpan.fromMilliseconds(5),
|
|
1428
|
+
interval: TimeSpan.fromMilliseconds(5),
|
|
1429
|
+
});
|
|
1430
|
+
await expect(result).rejects.toBeInstanceOf(KeyAlreadyAcquiredLockError);
|
|
1431
|
+
});
|
|
1432
|
+
test("Should retry acquire the lock", async () => {
|
|
1433
|
+
const key = "a";
|
|
1434
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
1435
|
+
const lock1 = lockProvider.create(key, {
|
|
1436
|
+
ttl,
|
|
1437
|
+
});
|
|
1438
|
+
await lock1.acquire();
|
|
1439
|
+
let index = 0;
|
|
1440
|
+
await lockProvider.addListener(LOCK_EVENTS.UNAVAILABLE, (_event) => {
|
|
1441
|
+
index++;
|
|
1442
|
+
});
|
|
1443
|
+
const lock2 = lockProvider.create(key, {
|
|
1444
|
+
ttl,
|
|
1445
|
+
});
|
|
1446
|
+
try {
|
|
1447
|
+
await lock2.acquireBlockingOrFail({
|
|
1448
|
+
time: TimeSpan.fromMilliseconds(55),
|
|
1449
|
+
interval: TimeSpan.fromMilliseconds(5),
|
|
1450
|
+
});
|
|
1451
|
+
}
|
|
1452
|
+
catch {
|
|
1453
|
+
/* EMPTY */
|
|
1454
|
+
}
|
|
1455
|
+
expect(index).toBeGreaterThan(1);
|
|
1456
|
+
});
|
|
1457
|
+
});
|
|
1458
|
+
describe("method: release", () => {
|
|
1459
|
+
test("Should return false when key doesnt exists", async () => {
|
|
1460
|
+
const key = "a";
|
|
1461
|
+
const result = await lockProvider.create(key).release();
|
|
1462
|
+
expect(result).toBe(false);
|
|
1463
|
+
});
|
|
1464
|
+
test("Should return false when key is unexpireable and released by different owner", async () => {
|
|
1465
|
+
const key = "a";
|
|
1466
|
+
const ttl = null;
|
|
1467
|
+
await lockProvider.create(key, { ttl }).acquire();
|
|
1468
|
+
const result = await lockProvider
|
|
1469
|
+
.create(key, { ttl })
|
|
1470
|
+
.release();
|
|
1471
|
+
expect(result).toBe(false);
|
|
1472
|
+
});
|
|
1473
|
+
test("Should return false when key is unexpired and released by different owner", async () => {
|
|
1474
|
+
const key = "a";
|
|
1475
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
1476
|
+
await lockProvider.create(key, { ttl }).acquire();
|
|
1477
|
+
const result = await lockProvider
|
|
1478
|
+
.create(key, { ttl })
|
|
1479
|
+
.release();
|
|
1480
|
+
expect(result).toBe(false);
|
|
1481
|
+
});
|
|
1482
|
+
test("Should return false when key is expired and released by different owner", async () => {
|
|
1483
|
+
const key = "a";
|
|
1484
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
1485
|
+
await lockProvider.create(key, { ttl }).acquire();
|
|
1486
|
+
const result = await lockProvider
|
|
1487
|
+
.create(key, { ttl })
|
|
1488
|
+
.release();
|
|
1489
|
+
await delay(ttl);
|
|
1490
|
+
expect(result).toBe(false);
|
|
1491
|
+
});
|
|
1492
|
+
test("Should return false when key is expired and released by same owner", async () => {
|
|
1493
|
+
const key = "a";
|
|
1494
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
1495
|
+
const lock = lockProvider.create(key, { ttl });
|
|
1496
|
+
await lock.acquire();
|
|
1497
|
+
await delay(ttl);
|
|
1498
|
+
const result = await lock.release();
|
|
1499
|
+
expect(result).toBe(false);
|
|
1500
|
+
});
|
|
1501
|
+
test("Should return true when key is unexpireable and released by same owner", async () => {
|
|
1502
|
+
const key = "a";
|
|
1503
|
+
const ttl = null;
|
|
1504
|
+
const lock = lockProvider.create(key, { ttl });
|
|
1505
|
+
await lock.acquire();
|
|
1506
|
+
const result = await lock.release();
|
|
1507
|
+
expect(result).toBe(true);
|
|
1508
|
+
});
|
|
1509
|
+
test("Should return true when key is unexpired and released by same owner", async () => {
|
|
1510
|
+
const key = "a";
|
|
1511
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
1512
|
+
const lock = lockProvider.create(key, { ttl });
|
|
1513
|
+
await lock.acquire();
|
|
1514
|
+
const result = await lock.release();
|
|
1515
|
+
expect(result).toBe(true);
|
|
1516
|
+
});
|
|
1517
|
+
test("Should not be reacquirable when key is unexpireable and released by different owner", async () => {
|
|
1518
|
+
const key = "a";
|
|
1519
|
+
const ttl = null;
|
|
1520
|
+
const lock1 = lockProvider.create(key, { ttl });
|
|
1521
|
+
await lock1.acquire();
|
|
1522
|
+
const lock2 = lockProvider.create(key, { ttl });
|
|
1523
|
+
await lock2.release();
|
|
1524
|
+
const result = await lock2.acquire();
|
|
1525
|
+
expect(result).toBe(false);
|
|
1526
|
+
});
|
|
1527
|
+
test("Should not be reacquirable when key is unexpired and released by different owner", async () => {
|
|
1528
|
+
const key = "a";
|
|
1529
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
1530
|
+
const lock1 = lockProvider.create(key, { ttl });
|
|
1531
|
+
await lock1.acquire();
|
|
1532
|
+
const lock2 = lockProvider.create(key, { ttl });
|
|
1533
|
+
await lock2.release();
|
|
1534
|
+
const result = await lock2.acquire();
|
|
1535
|
+
expect(result).toBe(false);
|
|
1536
|
+
});
|
|
1537
|
+
test("Should be reacquirable when key is unexpireable and released by same owner", async () => {
|
|
1538
|
+
const key = "a";
|
|
1539
|
+
const ttl = null;
|
|
1540
|
+
const lock1 = lockProvider.create(key, { ttl });
|
|
1541
|
+
await lock1.acquire();
|
|
1542
|
+
await lock1.release();
|
|
1543
|
+
const lock2 = lockProvider.create(key, { ttl });
|
|
1544
|
+
const result = await lock2.acquire();
|
|
1545
|
+
expect(result).toBe(true);
|
|
1546
|
+
});
|
|
1547
|
+
test("Should be reacquirable when key is unexpired and released by same owner", async () => {
|
|
1548
|
+
const key = "a";
|
|
1549
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
1550
|
+
const lock1 = lockProvider.create(key, { ttl });
|
|
1551
|
+
await lock1.acquire();
|
|
1552
|
+
await lock1.release();
|
|
1553
|
+
const lock2 = lockProvider.create(key, { ttl });
|
|
1554
|
+
const result = await lock2.acquire();
|
|
1555
|
+
expect(result).toBe(true);
|
|
1556
|
+
});
|
|
1557
|
+
});
|
|
1558
|
+
describe("method: releaseOrFail", () => {
|
|
1559
|
+
test("Should throw UnownedReleaseLockError when key doesnt exists", async () => {
|
|
1560
|
+
const key = "a";
|
|
1561
|
+
const result = lockProvider.create(key).releaseOrFail();
|
|
1562
|
+
await expect(result).rejects.toBeInstanceOf(UnownedReleaseLockError);
|
|
1563
|
+
});
|
|
1564
|
+
test("Should throw UnownedReleaseLockError when key is unexpireable and released by different owner", async () => {
|
|
1565
|
+
const key = "a";
|
|
1566
|
+
const ttl = null;
|
|
1567
|
+
await lockProvider.create(key, { ttl }).acquire();
|
|
1568
|
+
const result = lockProvider
|
|
1569
|
+
.create(key, { ttl })
|
|
1570
|
+
.releaseOrFail();
|
|
1571
|
+
await expect(result).rejects.toBeInstanceOf(UnownedReleaseLockError);
|
|
1572
|
+
});
|
|
1573
|
+
test("Should throw UnownedReleaseLockError when key is unexpired and released by different owner", async () => {
|
|
1574
|
+
const key = "a";
|
|
1575
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
1576
|
+
await lockProvider.create(key, { ttl }).acquire();
|
|
1577
|
+
const result = lockProvider
|
|
1578
|
+
.create(key, { ttl })
|
|
1579
|
+
.releaseOrFail();
|
|
1580
|
+
await expect(result).rejects.toBeInstanceOf(UnownedReleaseLockError);
|
|
1581
|
+
});
|
|
1582
|
+
test("Should throw UnownedReleaseLockError when key is expired and released by different owner", async () => {
|
|
1583
|
+
const key = "a";
|
|
1584
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
1585
|
+
await lockProvider.create(key, { ttl }).acquire();
|
|
1586
|
+
const result = lockProvider
|
|
1587
|
+
.create(key, { ttl })
|
|
1588
|
+
.releaseOrFail();
|
|
1589
|
+
await delay(ttl);
|
|
1590
|
+
await expect(result).rejects.toBeInstanceOf(UnownedReleaseLockError);
|
|
1591
|
+
});
|
|
1592
|
+
test("Should throw UnownedReleaseLockError when key is expired and released by same owner", async () => {
|
|
1593
|
+
const key = "a";
|
|
1594
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
1595
|
+
const lock = lockProvider.create(key, { ttl });
|
|
1596
|
+
await lock.acquire();
|
|
1597
|
+
await delay(ttl);
|
|
1598
|
+
const result = lock.releaseOrFail();
|
|
1599
|
+
await expect(result).rejects.toBeInstanceOf(UnownedReleaseLockError);
|
|
1600
|
+
});
|
|
1601
|
+
test("Should not throw error when key is unexpireable and released by same owner", async () => {
|
|
1602
|
+
const key = "a";
|
|
1603
|
+
const ttl = null;
|
|
1604
|
+
const lock = lockProvider.create(key, { ttl });
|
|
1605
|
+
await lock.acquire();
|
|
1606
|
+
const result = lock.releaseOrFail();
|
|
1607
|
+
await expect(result).resolves.toBeUndefined();
|
|
1608
|
+
});
|
|
1609
|
+
test("Should not throw error when key is unexpired and released by same owner", async () => {
|
|
1610
|
+
const key = "a";
|
|
1611
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
1612
|
+
const lock = lockProvider.create(key, { ttl });
|
|
1613
|
+
await lock.acquire();
|
|
1614
|
+
const result = lock.releaseOrFail();
|
|
1615
|
+
await expect(result).resolves.toBeUndefined();
|
|
1616
|
+
});
|
|
1617
|
+
test("Should not be reacquirable when key is unexpireable and released by different owner", async () => {
|
|
1618
|
+
const key = "a";
|
|
1619
|
+
const ttl = null;
|
|
1620
|
+
const lock1 = lockProvider.create(key, { ttl });
|
|
1621
|
+
await lock1.acquire();
|
|
1622
|
+
const lock2 = lockProvider.create(key, { ttl });
|
|
1623
|
+
try {
|
|
1624
|
+
await lock2.releaseOrFail();
|
|
1625
|
+
}
|
|
1626
|
+
catch {
|
|
1627
|
+
/* EMPTY */
|
|
1628
|
+
}
|
|
1629
|
+
const result = await lock2.acquire();
|
|
1630
|
+
expect(result).toBe(false);
|
|
1631
|
+
});
|
|
1632
|
+
test("Should not be reacquirable when key is unexpired and released by different owner", async () => {
|
|
1633
|
+
const key = "a";
|
|
1634
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
1635
|
+
const lock1 = lockProvider.create(key, { ttl });
|
|
1636
|
+
await lock1.acquire();
|
|
1637
|
+
const lock2 = lockProvider.create(key, { ttl });
|
|
1638
|
+
try {
|
|
1639
|
+
await lock2.releaseOrFail();
|
|
1640
|
+
}
|
|
1641
|
+
catch {
|
|
1642
|
+
/* EMPTY */
|
|
1643
|
+
}
|
|
1644
|
+
const result = await lock2.acquire();
|
|
1645
|
+
expect(result).toBe(false);
|
|
1646
|
+
});
|
|
1647
|
+
test("Should be reacquirable when key is unexpireable and released by same owner", async () => {
|
|
1648
|
+
const key = "a";
|
|
1649
|
+
const ttl = null;
|
|
1650
|
+
const lock1 = lockProvider.create(key, { ttl });
|
|
1651
|
+
await lock1.acquire();
|
|
1652
|
+
await lock1.releaseOrFail();
|
|
1653
|
+
const lock2 = lockProvider.create(key, { ttl });
|
|
1654
|
+
const result = await lock2.acquire();
|
|
1655
|
+
expect(result).toBe(true);
|
|
1656
|
+
});
|
|
1657
|
+
test("Should be reacquirable when key is unexpired and released by same owner", async () => {
|
|
1658
|
+
const key = "a";
|
|
1659
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
1660
|
+
const lock1 = lockProvider.create(key, { ttl });
|
|
1661
|
+
await lock1.acquire();
|
|
1662
|
+
await lock1.releaseOrFail();
|
|
1663
|
+
const lock2 = lockProvider.create(key, { ttl });
|
|
1664
|
+
const result = await lock2.acquire();
|
|
1665
|
+
expect(result).toBe(true);
|
|
1666
|
+
});
|
|
1667
|
+
});
|
|
1668
|
+
describe("method: forceRelease", () => {
|
|
1669
|
+
test("Should return false when key doesnt exists", async () => {
|
|
1670
|
+
const key = "a";
|
|
1671
|
+
const result = await lockProvider.create(key).forceRelease();
|
|
1672
|
+
expect(result).toBe(false);
|
|
1673
|
+
});
|
|
1674
|
+
test("Should return false when key is expired", async () => {
|
|
1675
|
+
const key = "a";
|
|
1676
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
1677
|
+
const lock = lockProvider.create(key, {
|
|
1678
|
+
ttl,
|
|
1679
|
+
});
|
|
1680
|
+
await lock.acquire();
|
|
1681
|
+
await delay(ttl);
|
|
1682
|
+
const result = await lock.forceRelease();
|
|
1683
|
+
expect(result).toBe(false);
|
|
1684
|
+
});
|
|
1685
|
+
test("Should return true when key is uenxpired", async () => {
|
|
1686
|
+
const key = "a";
|
|
1687
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
1688
|
+
const lock = lockProvider.create(key, { ttl });
|
|
1689
|
+
await lock.acquire();
|
|
1690
|
+
const result = await lock.forceRelease();
|
|
1691
|
+
expect(result).toBe(true);
|
|
1692
|
+
});
|
|
1693
|
+
test("Should return true when key is unexpireable", async () => {
|
|
1694
|
+
const key = "a";
|
|
1695
|
+
const ttl = null;
|
|
1696
|
+
const lock = lockProvider.create(key, { ttl });
|
|
1697
|
+
await lock.acquire();
|
|
1698
|
+
const result = await lock.forceRelease();
|
|
1699
|
+
expect(result).toBe(true);
|
|
1700
|
+
});
|
|
1701
|
+
test("Should be reacquirable when key is uenxpired", async () => {
|
|
1702
|
+
const key = "a";
|
|
1703
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
1704
|
+
const lock = lockProvider.create(key, { ttl });
|
|
1705
|
+
await lock.acquire();
|
|
1706
|
+
await lock.forceRelease();
|
|
1707
|
+
const result = await lock.acquire();
|
|
1708
|
+
expect(result).toBe(true);
|
|
1709
|
+
});
|
|
1710
|
+
test("Should be reacquirable when key is unexpireable", async () => {
|
|
1711
|
+
const key = "a";
|
|
1712
|
+
const ttl = null;
|
|
1713
|
+
const lock = lockProvider.create(key, { ttl });
|
|
1714
|
+
await lock.acquire();
|
|
1715
|
+
await lock.forceRelease();
|
|
1716
|
+
const result = await lock.acquire();
|
|
1717
|
+
expect(result).toBe(true);
|
|
1718
|
+
});
|
|
1719
|
+
});
|
|
1720
|
+
describe("method: isExpired", () => {
|
|
1721
|
+
test("Should return false when lock has no expiration", async () => {
|
|
1722
|
+
const key = "a";
|
|
1723
|
+
const ttl = null;
|
|
1724
|
+
const owner = "b";
|
|
1725
|
+
const lock = lockProvider.create(key, {
|
|
1726
|
+
ttl,
|
|
1727
|
+
owner,
|
|
1728
|
+
});
|
|
1729
|
+
await lock.acquire();
|
|
1730
|
+
const result = await lock.isExpired();
|
|
1731
|
+
expect(result).toBe(false);
|
|
1732
|
+
});
|
|
1733
|
+
test("Should return false when lock has not expired", async () => {
|
|
1734
|
+
const key = "a";
|
|
1735
|
+
const owner = "b";
|
|
1736
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
1737
|
+
const lock = lockProvider.create(key, {
|
|
1738
|
+
ttl,
|
|
1739
|
+
owner,
|
|
1740
|
+
});
|
|
1741
|
+
await lock.acquire();
|
|
1742
|
+
const result = await lock.isExpired();
|
|
1743
|
+
expect(result).toBe(false);
|
|
1744
|
+
});
|
|
1745
|
+
test("Should return true when lock has expired", async () => {
|
|
1746
|
+
const key = "a";
|
|
1747
|
+
const owner = "b";
|
|
1748
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
1749
|
+
const lock = lockProvider.create(key, {
|
|
1750
|
+
ttl,
|
|
1751
|
+
owner,
|
|
1752
|
+
});
|
|
1753
|
+
await lock.acquire();
|
|
1754
|
+
await delay(ttl);
|
|
1755
|
+
const result = await lock.isExpired();
|
|
1756
|
+
expect(result).toBe(true);
|
|
1757
|
+
});
|
|
1758
|
+
});
|
|
1759
|
+
describe("method: isLocked", () => {
|
|
1760
|
+
test("Should return true when lock has no expiration", async () => {
|
|
1761
|
+
const key = "a";
|
|
1762
|
+
const ttl = null;
|
|
1763
|
+
const owner = "b";
|
|
1764
|
+
const lock = lockProvider.create(key, {
|
|
1765
|
+
ttl,
|
|
1766
|
+
owner,
|
|
1767
|
+
});
|
|
1768
|
+
await lock.acquire();
|
|
1769
|
+
const result = await lock.isLocked();
|
|
1770
|
+
expect(result).toBe(true);
|
|
1771
|
+
});
|
|
1772
|
+
test("Should return true when lock has not expired", async () => {
|
|
1773
|
+
const key = "a";
|
|
1774
|
+
const owner = "b";
|
|
1775
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
1776
|
+
const lock = lockProvider.create(key, {
|
|
1777
|
+
ttl,
|
|
1778
|
+
owner,
|
|
1779
|
+
});
|
|
1780
|
+
await lock.acquire();
|
|
1781
|
+
const result = await lock.isLocked();
|
|
1782
|
+
expect(result).toBe(true);
|
|
1783
|
+
});
|
|
1784
|
+
test("Should return false when lock has expired", async () => {
|
|
1785
|
+
const key = "a";
|
|
1786
|
+
const owner = "b";
|
|
1787
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
1788
|
+
const lock = lockProvider.create(key, {
|
|
1789
|
+
ttl,
|
|
1790
|
+
owner,
|
|
1791
|
+
});
|
|
1792
|
+
await lock.acquire();
|
|
1793
|
+
await delay(ttl);
|
|
1794
|
+
const result = await lock.isLocked();
|
|
1795
|
+
expect(result).toBe(false);
|
|
1796
|
+
});
|
|
1797
|
+
});
|
|
1798
|
+
describe("method: refresh", () => {
|
|
1799
|
+
test("Should return false when key doesnt exists", async () => {
|
|
1800
|
+
const key = "a";
|
|
1801
|
+
const newTtl = TimeSpan.fromMinutes(1);
|
|
1802
|
+
const result = await lockProvider.create(key).refresh(newTtl);
|
|
1803
|
+
expect(result).toBe(false);
|
|
1804
|
+
});
|
|
1805
|
+
test("Should return false when key is unexpireable and refreshed by different owner", async () => {
|
|
1806
|
+
const key = "a";
|
|
1807
|
+
const ttl = null;
|
|
1808
|
+
const lock1 = lockProvider.create(key, { ttl });
|
|
1809
|
+
await lock1.acquire();
|
|
1810
|
+
const newTtl = TimeSpan.fromMinutes(1);
|
|
1811
|
+
const lock2 = lockProvider.create(key, { ttl });
|
|
1812
|
+
const result = await lock2.refresh(newTtl);
|
|
1813
|
+
expect(result).toBe(false);
|
|
1814
|
+
});
|
|
1815
|
+
test("Should return false when key is unexpired and refreshed by different owner", async () => {
|
|
1816
|
+
const key = "a";
|
|
1817
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
1818
|
+
const lock1 = lockProvider.create(key, { ttl });
|
|
1819
|
+
await lock1.acquire();
|
|
1820
|
+
const newTtl = TimeSpan.fromMinutes(1);
|
|
1821
|
+
const lock2 = lockProvider.create(key, { ttl });
|
|
1822
|
+
const result = await lock2.refresh(newTtl);
|
|
1823
|
+
expect(result).toBe(false);
|
|
1824
|
+
});
|
|
1825
|
+
test("Should return false when key is expired and refreshed by different owner", async () => {
|
|
1826
|
+
const key = "a";
|
|
1827
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
1828
|
+
const lock1 = lockProvider.create(key, { ttl });
|
|
1829
|
+
await lock1.acquire();
|
|
1830
|
+
await delay(ttl);
|
|
1831
|
+
const newTtl = TimeSpan.fromMinutes(1);
|
|
1832
|
+
const lock2 = lockProvider.create(key, { ttl });
|
|
1833
|
+
const result = await lock2.refresh(newTtl);
|
|
1834
|
+
expect(result).toBe(false);
|
|
1835
|
+
});
|
|
1836
|
+
test("Should return false when key is expired and refreshed by same owner", async () => {
|
|
1837
|
+
const key = "a";
|
|
1838
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
1839
|
+
const lock = lockProvider.create(key, {
|
|
1840
|
+
ttl,
|
|
1841
|
+
});
|
|
1842
|
+
await lock.acquire();
|
|
1843
|
+
await delay(ttl);
|
|
1844
|
+
const newTtl = TimeSpan.fromMinutes(1);
|
|
1845
|
+
const result = await lock.refresh(newTtl);
|
|
1846
|
+
expect(result).toBe(false);
|
|
1847
|
+
});
|
|
1848
|
+
test("Should return false when key is unexpireable and refreshed by same owner", async () => {
|
|
1849
|
+
const key = "a";
|
|
1850
|
+
const ttl = null;
|
|
1851
|
+
const lock = lockProvider.create(key, { ttl });
|
|
1852
|
+
await lock.acquire();
|
|
1853
|
+
const newTtl = TimeSpan.fromMinutes(1);
|
|
1854
|
+
const result = await lock.refresh(newTtl);
|
|
1855
|
+
expect(result).toBe(false);
|
|
1856
|
+
});
|
|
1857
|
+
test("Should return true when key is unexpired and refreshed by same owner", async () => {
|
|
1858
|
+
const key = "a";
|
|
1859
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
1860
|
+
const lock = lockProvider.create(key, { ttl });
|
|
1861
|
+
await lock.acquire();
|
|
1862
|
+
const newTtl = TimeSpan.fromMinutes(1);
|
|
1863
|
+
const result = await lock.refresh(newTtl);
|
|
1864
|
+
expect(result).toBe(true);
|
|
1865
|
+
});
|
|
1866
|
+
test("Should not update expiration when key is unexpireable and refreshed by same owner", async () => {
|
|
1867
|
+
const key = "a";
|
|
1868
|
+
const ttl = null;
|
|
1869
|
+
const lock1 = lockProvider.create(key, { ttl });
|
|
1870
|
+
await lock1.acquire();
|
|
1871
|
+
const newTtl = TimeSpan.fromMilliseconds(50);
|
|
1872
|
+
await lock1.refresh(newTtl);
|
|
1873
|
+
await delay(newTtl);
|
|
1874
|
+
const lock2 = lockProvider.create(key, { ttl });
|
|
1875
|
+
const result = await lock2.acquire();
|
|
1876
|
+
expect(result).toBe(false);
|
|
1877
|
+
});
|
|
1878
|
+
test("Should update expiration when key is unexpired and refreshed by same owner", async () => {
|
|
1879
|
+
const key = "a";
|
|
1880
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
1881
|
+
const lock1 = lockProvider.create(key, { ttl });
|
|
1882
|
+
await lock1.acquire();
|
|
1883
|
+
const newTtl = TimeSpan.fromMilliseconds(100);
|
|
1884
|
+
await lock1.refresh(newTtl);
|
|
1885
|
+
await delay(newTtl.divide(2));
|
|
1886
|
+
const lock2 = lockProvider.create(key, { ttl });
|
|
1887
|
+
const result1 = await lock2.acquire();
|
|
1888
|
+
expect(result1).toBe(false);
|
|
1889
|
+
await delay(newTtl.divide(2));
|
|
1890
|
+
const result2 = await lock2.acquire();
|
|
1891
|
+
expect(result2).toBe(true);
|
|
1892
|
+
});
|
|
1893
|
+
});
|
|
1894
|
+
describe("method: refreshOrFail", () => {
|
|
1895
|
+
test("Should throw UnownedRefreshLockError when key doesnt exists", async () => {
|
|
1896
|
+
const key = "a";
|
|
1897
|
+
const newTtl = TimeSpan.fromMinutes(1);
|
|
1898
|
+
const result = lockProvider.create(key).refreshOrFail(newTtl);
|
|
1899
|
+
await expect(result).rejects.toBeInstanceOf(UnownedRefreshLockError);
|
|
1900
|
+
});
|
|
1901
|
+
test("Should throw UnownedRefreshLockError when key is unexpireable and refreshed by different owner", async () => {
|
|
1902
|
+
const key = "a";
|
|
1903
|
+
const ttl = null;
|
|
1904
|
+
const lock1 = lockProvider.create(key, { ttl });
|
|
1905
|
+
await lock1.acquire();
|
|
1906
|
+
const newTtl = TimeSpan.fromMinutes(1);
|
|
1907
|
+
const lock2 = lockProvider.create(key, { ttl });
|
|
1908
|
+
const result = lock2.refreshOrFail(newTtl);
|
|
1909
|
+
await expect(result).rejects.toBeInstanceOf(UnownedRefreshLockError);
|
|
1910
|
+
});
|
|
1911
|
+
test("Should throw UnownedRefreshLockError when key is unexpired and refreshed by different owner", async () => {
|
|
1912
|
+
const key = "a";
|
|
1913
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
1914
|
+
const lock1 = lockProvider.create(key, { ttl });
|
|
1915
|
+
await lock1.acquire();
|
|
1916
|
+
const newTtl = TimeSpan.fromMinutes(1);
|
|
1917
|
+
const lock2 = lockProvider.create(key, { ttl });
|
|
1918
|
+
const result = lock2.refreshOrFail(newTtl);
|
|
1919
|
+
await expect(result).rejects.toBeInstanceOf(UnownedRefreshLockError);
|
|
1920
|
+
});
|
|
1921
|
+
test("Should throw UnownedRefreshLockError when key is expired and refreshed by different owner", async () => {
|
|
1922
|
+
const key = "a";
|
|
1923
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
1924
|
+
const lock1 = lockProvider.create(key, { ttl });
|
|
1925
|
+
await lock1.acquire();
|
|
1926
|
+
await delay(ttl);
|
|
1927
|
+
const newTtl = TimeSpan.fromMinutes(1);
|
|
1928
|
+
const lock2 = lockProvider.create(key, { ttl });
|
|
1929
|
+
const result = lock2.refreshOrFail(newTtl);
|
|
1930
|
+
await expect(result).rejects.toBeInstanceOf(UnownedRefreshLockError);
|
|
1931
|
+
});
|
|
1932
|
+
test("Should throw UnownedRefreshLockError when key is expired and refreshed by same owner", async () => {
|
|
1933
|
+
const key = "a";
|
|
1934
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
1935
|
+
const lock = lockProvider.create(key, {
|
|
1936
|
+
ttl,
|
|
1937
|
+
});
|
|
1938
|
+
await lock.acquire();
|
|
1939
|
+
await delay(ttl);
|
|
1940
|
+
const newTtl = TimeSpan.fromMinutes(1);
|
|
1941
|
+
const result = lock.refreshOrFail(newTtl);
|
|
1942
|
+
await expect(result).rejects.toBeInstanceOf(UnownedRefreshLockError);
|
|
1943
|
+
});
|
|
1944
|
+
test("Should throw UnrefreshableKeyLockError when key is unexpireable and refreshed by same owner", async () => {
|
|
1945
|
+
const key = "a";
|
|
1946
|
+
const ttl = null;
|
|
1947
|
+
const lock = lockProvider.create(key, { ttl });
|
|
1948
|
+
await lock.acquire();
|
|
1949
|
+
const newTtl = TimeSpan.fromMinutes(1);
|
|
1950
|
+
const result = lock.refreshOrFail(newTtl);
|
|
1951
|
+
await expect(result).rejects.toBeInstanceOf(UnrefreshableKeyLockError);
|
|
1952
|
+
});
|
|
1953
|
+
test("Should not throw error when key is unexpired and refreshed by same owner", async () => {
|
|
1954
|
+
const key = "a";
|
|
1955
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
1956
|
+
const lock = lockProvider.create(key, { ttl });
|
|
1957
|
+
await lock.acquire();
|
|
1958
|
+
const newTtl = TimeSpan.fromMinutes(1);
|
|
1959
|
+
const result = lock.refreshOrFail(newTtl);
|
|
1960
|
+
await expect(result).resolves.toBeUndefined();
|
|
1961
|
+
});
|
|
1962
|
+
test("Should not update expiration when key is unexpireable and refreshed by same owner", async () => {
|
|
1963
|
+
const key = "a";
|
|
1964
|
+
const ttl = null;
|
|
1965
|
+
const lock1 = lockProvider.create(key, { ttl });
|
|
1966
|
+
await lock1.acquire();
|
|
1967
|
+
const newTtl = TimeSpan.fromMilliseconds(50);
|
|
1968
|
+
try {
|
|
1969
|
+
await lock1.refreshOrFail(newTtl);
|
|
1970
|
+
}
|
|
1971
|
+
catch {
|
|
1972
|
+
/* EMPTY */
|
|
1973
|
+
}
|
|
1974
|
+
await delay(newTtl);
|
|
1975
|
+
const lock2 = lockProvider.create(key, { ttl });
|
|
1976
|
+
const result = await lock2.acquire();
|
|
1977
|
+
expect(result).toBe(false);
|
|
1978
|
+
});
|
|
1979
|
+
test("Should update expiration when key is unexpired and refreshed by same owner", async () => {
|
|
1980
|
+
const key = "a";
|
|
1981
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
1982
|
+
const lock1 = lockProvider.create(key, { ttl });
|
|
1983
|
+
await lock1.acquire();
|
|
1984
|
+
const newTtl = TimeSpan.fromMilliseconds(100);
|
|
1985
|
+
await lock1.refreshOrFail(newTtl);
|
|
1986
|
+
await delay(newTtl.divide(2));
|
|
1987
|
+
const lock2 = lockProvider.create(key, { ttl });
|
|
1988
|
+
const result1 = await lock2.acquire();
|
|
1989
|
+
expect(result1).toBe(false);
|
|
1990
|
+
await delay(newTtl.divide(2));
|
|
1991
|
+
const result2 = await lock2.acquire();
|
|
1992
|
+
expect(result2).toBe(true);
|
|
1993
|
+
});
|
|
1994
|
+
});
|
|
1995
|
+
describe("method: getRemainingTime", () => {
|
|
1996
|
+
test("Should return null when lock is not acquired", async () => {
|
|
1997
|
+
const key = "a";
|
|
1998
|
+
const ttl = null;
|
|
1999
|
+
const owner = "b";
|
|
2000
|
+
const lock = lockProvider.create(key, {
|
|
2001
|
+
ttl,
|
|
2002
|
+
owner,
|
|
2003
|
+
});
|
|
2004
|
+
const result = await lock.getRemainingTime();
|
|
2005
|
+
expect(result).toBeNull();
|
|
2006
|
+
});
|
|
2007
|
+
test("Should return null when lock is acquired and has expiration", async () => {
|
|
2008
|
+
const key = "a";
|
|
2009
|
+
const ttl = null;
|
|
2010
|
+
const owner = "b";
|
|
2011
|
+
const lock = lockProvider.create(key, {
|
|
2012
|
+
ttl,
|
|
2013
|
+
owner,
|
|
2014
|
+
});
|
|
2015
|
+
await lock.acquire();
|
|
2016
|
+
const result = await lock.getRemainingTime();
|
|
2017
|
+
expect(result).toBeNull();
|
|
2018
|
+
});
|
|
2019
|
+
test("Should return remaining time when lock is not acquired", async () => {
|
|
2020
|
+
const key = "a";
|
|
2021
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
2022
|
+
const owner = "b";
|
|
2023
|
+
const lock = lockProvider.create(key, {
|
|
2024
|
+
ttl,
|
|
2025
|
+
owner,
|
|
2026
|
+
});
|
|
2027
|
+
await lock.acquire();
|
|
2028
|
+
const result = await lock.getRemainingTime();
|
|
2029
|
+
expect(result?.toMilliseconds()).toBe(ttl.toMilliseconds());
|
|
2030
|
+
});
|
|
2031
|
+
});
|
|
2032
|
+
describe("method: getOwner", () => {
|
|
2033
|
+
test("Should return the owner", async () => {
|
|
2034
|
+
const key = "a";
|
|
2035
|
+
const owner = "b";
|
|
2036
|
+
const lock = lockProvider.create(key, {
|
|
2037
|
+
owner,
|
|
2038
|
+
});
|
|
2039
|
+
const result = await lock.getOwner();
|
|
2040
|
+
expect(result).toBe(owner);
|
|
2041
|
+
});
|
|
2042
|
+
test("Should return the auto generated owner", async () => {
|
|
2043
|
+
const key = "a";
|
|
2044
|
+
const lock = lockProvider.create(key);
|
|
2045
|
+
const result = await lock.getOwner();
|
|
2046
|
+
expect(result).toBeDefined();
|
|
2047
|
+
expect(typeof result).toBe("string");
|
|
2048
|
+
});
|
|
2049
|
+
});
|
|
2050
|
+
});
|
|
2051
|
+
describe("Event tests:", () => {
|
|
2052
|
+
describe("method: acquire", () => {
|
|
2053
|
+
test("Should dispatch AcquiredLockEvent when key doesnt exists", async () => {
|
|
2054
|
+
const key = "a";
|
|
2055
|
+
const owner = "b";
|
|
2056
|
+
const ttl = null;
|
|
2057
|
+
const handlerFn = vi.fn((_event) => { });
|
|
2058
|
+
await lockProvider.addListener(LOCK_EVENTS.ACQUIRED, handlerFn);
|
|
2059
|
+
await lockProvider
|
|
2060
|
+
.create(key, {
|
|
2061
|
+
ttl,
|
|
2062
|
+
owner,
|
|
2063
|
+
})
|
|
2064
|
+
.acquire();
|
|
2065
|
+
await delay(TimeSpan.fromMilliseconds(10));
|
|
2066
|
+
expect(handlerFn).toHaveBeenCalledTimes(1);
|
|
2067
|
+
expect(handlerFn).toHaveBeenCalledWith({
|
|
2068
|
+
key,
|
|
2069
|
+
owner,
|
|
2070
|
+
ttl,
|
|
2071
|
+
});
|
|
2072
|
+
});
|
|
2073
|
+
test("Should dispatch AcquiredLockEvent when key is expired", async () => {
|
|
2074
|
+
const key = "a";
|
|
2075
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
2076
|
+
await lockProvider.create(key, { ttl }).acquire();
|
|
2077
|
+
await delay(ttl);
|
|
2078
|
+
const handlerFn = vi.fn((_event) => { });
|
|
2079
|
+
await lockProvider.addListener(LOCK_EVENTS.ACQUIRED, handlerFn);
|
|
2080
|
+
const owner = "b";
|
|
2081
|
+
const ttl2 = null;
|
|
2082
|
+
await lockProvider.create(key, { ttl: ttl2, owner }).acquire();
|
|
2083
|
+
await delay(TimeSpan.fromMilliseconds(10));
|
|
2084
|
+
expect(handlerFn).toHaveBeenCalledTimes(1);
|
|
2085
|
+
expect(handlerFn).toHaveBeenCalledWith({
|
|
2086
|
+
key,
|
|
2087
|
+
owner,
|
|
2088
|
+
ttl: ttl2,
|
|
2089
|
+
});
|
|
2090
|
+
});
|
|
2091
|
+
test("Should dispatch UnavailableLockEvent when key is unexpireable and acquired by same owner", async () => {
|
|
2092
|
+
const key = "a";
|
|
2093
|
+
const owner = "b";
|
|
2094
|
+
const ttl = null;
|
|
2095
|
+
const lock = lockProvider.create(key, { ttl, owner });
|
|
2096
|
+
await lock.acquire();
|
|
2097
|
+
const handlerFn = vi.fn((_event) => { });
|
|
2098
|
+
await lockProvider.addListener(LOCK_EVENTS.UNAVAILABLE, handlerFn);
|
|
2099
|
+
await lock.acquire();
|
|
2100
|
+
await delay(TimeSpan.fromMilliseconds(10));
|
|
2101
|
+
expect(handlerFn).toHaveBeenCalledTimes(1);
|
|
2102
|
+
expect(handlerFn).toHaveBeenCalledWith({
|
|
2103
|
+
key,
|
|
2104
|
+
owner,
|
|
2105
|
+
});
|
|
2106
|
+
});
|
|
2107
|
+
test("Should dispatch UnavailableLockEvent when key is unexpired and acquired by same owner", async () => {
|
|
2108
|
+
const key = "a";
|
|
2109
|
+
const owner = "b";
|
|
2110
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
2111
|
+
const lock = lockProvider.create(key, {
|
|
2112
|
+
ttl,
|
|
2113
|
+
owner,
|
|
2114
|
+
});
|
|
2115
|
+
await lock.acquire();
|
|
2116
|
+
const handlerFn = vi.fn((_event) => { });
|
|
2117
|
+
await lockProvider.addListener(LOCK_EVENTS.UNAVAILABLE, handlerFn);
|
|
2118
|
+
await lock.acquire();
|
|
2119
|
+
await delay(TimeSpan.fromMilliseconds(10));
|
|
2120
|
+
expect(handlerFn).toHaveBeenCalledTimes(1);
|
|
2121
|
+
expect(handlerFn).toHaveBeenCalledWith({
|
|
2122
|
+
key,
|
|
2123
|
+
owner,
|
|
2124
|
+
});
|
|
2125
|
+
});
|
|
2126
|
+
test("Should dispatch UnavailableLockEvent when key is unexpireable and acquired by different owner", async () => {
|
|
2127
|
+
const key = "a";
|
|
2128
|
+
const ttl = null;
|
|
2129
|
+
await lockProvider.create(key, { ttl }).acquire();
|
|
2130
|
+
const handlerFn = vi.fn((_event) => { });
|
|
2131
|
+
await lockProvider.addListener(LOCK_EVENTS.UNAVAILABLE, handlerFn);
|
|
2132
|
+
const owner = "b";
|
|
2133
|
+
await lockProvider.create(key, { ttl, owner }).acquire();
|
|
2134
|
+
await delay(TimeSpan.fromMilliseconds(10));
|
|
2135
|
+
expect(handlerFn).toHaveBeenCalledTimes(1);
|
|
2136
|
+
expect(handlerFn).toHaveBeenCalledWith({
|
|
2137
|
+
key,
|
|
2138
|
+
owner,
|
|
2139
|
+
});
|
|
2140
|
+
});
|
|
2141
|
+
test("Should dispatch UnavailableLockEvent when key is unexpired and acquired by different owner", async () => {
|
|
2142
|
+
const key = "a";
|
|
2143
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
2144
|
+
await lockProvider.create(key, { ttl }).acquire();
|
|
2145
|
+
const handlerFn = vi.fn((_event) => { });
|
|
2146
|
+
await lockProvider.addListener(LOCK_EVENTS.UNAVAILABLE, handlerFn);
|
|
2147
|
+
const owner = "b";
|
|
2148
|
+
await lockProvider.create(key, { ttl, owner }).acquire();
|
|
2149
|
+
await delay(TimeSpan.fromMilliseconds(10));
|
|
2150
|
+
expect(handlerFn).toHaveBeenCalledTimes(1);
|
|
2151
|
+
expect(handlerFn).toHaveBeenCalledWith({
|
|
2152
|
+
key,
|
|
2153
|
+
owner,
|
|
2154
|
+
});
|
|
2155
|
+
});
|
|
2156
|
+
});
|
|
2157
|
+
describe("method: acquireOrFail", () => {
|
|
2158
|
+
test("Should dispatch AcquiredLockEvent when key doesnt exists", async () => {
|
|
2159
|
+
const key = "a";
|
|
2160
|
+
const owner = "b";
|
|
2161
|
+
const ttl = null;
|
|
2162
|
+
const handlerFn = vi.fn((_event) => { });
|
|
2163
|
+
await lockProvider.addListener(LOCK_EVENTS.ACQUIRED, handlerFn);
|
|
2164
|
+
await lockProvider
|
|
2165
|
+
.create(key, {
|
|
2166
|
+
ttl,
|
|
2167
|
+
owner,
|
|
2168
|
+
})
|
|
2169
|
+
.acquireOrFail();
|
|
2170
|
+
await delay(TimeSpan.fromMilliseconds(10));
|
|
2171
|
+
expect(handlerFn).toHaveBeenCalledTimes(1);
|
|
2172
|
+
expect(handlerFn).toHaveBeenCalledWith({
|
|
2173
|
+
key,
|
|
2174
|
+
owner,
|
|
2175
|
+
ttl,
|
|
2176
|
+
});
|
|
2177
|
+
});
|
|
2178
|
+
test("Should dispatch AcquiredLockEvent when key is expired", async () => {
|
|
2179
|
+
const key = "a";
|
|
2180
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
2181
|
+
await lockProvider.create(key, { ttl }).acquire();
|
|
2182
|
+
await delay(ttl);
|
|
2183
|
+
const handlerFn = vi.fn((_event) => { });
|
|
2184
|
+
await lockProvider.addListener(LOCK_EVENTS.ACQUIRED, handlerFn);
|
|
2185
|
+
const owner = "b";
|
|
2186
|
+
const ttl2 = null;
|
|
2187
|
+
await lockProvider
|
|
2188
|
+
.create(key, { ttl: ttl2, owner })
|
|
2189
|
+
.acquireOrFail();
|
|
2190
|
+
await delay(TimeSpan.fromMilliseconds(10));
|
|
2191
|
+
expect(handlerFn).toHaveBeenCalledTimes(1);
|
|
2192
|
+
expect(handlerFn).toHaveBeenCalledWith({
|
|
2193
|
+
key,
|
|
2194
|
+
owner,
|
|
2195
|
+
ttl: ttl2,
|
|
2196
|
+
});
|
|
2197
|
+
});
|
|
2198
|
+
test("Should dispatch UnavailableLockEvent when key is unexpireable and acquired by same owner", async () => {
|
|
2199
|
+
const key = "a";
|
|
2200
|
+
const owner = "b";
|
|
2201
|
+
const ttl = null;
|
|
2202
|
+
const lock = lockProvider.create(key, { ttl, owner });
|
|
2203
|
+
await lock.acquire();
|
|
2204
|
+
const handlerFn = vi.fn((_event) => { });
|
|
2205
|
+
await lockProvider.addListener(LOCK_EVENTS.UNAVAILABLE, handlerFn);
|
|
2206
|
+
try {
|
|
2207
|
+
await lock.acquireOrFail();
|
|
2208
|
+
}
|
|
2209
|
+
catch {
|
|
2210
|
+
/* EMPTY */
|
|
2211
|
+
}
|
|
2212
|
+
await delay(TimeSpan.fromMilliseconds(10));
|
|
2213
|
+
expect(handlerFn).toHaveBeenCalledTimes(1);
|
|
2214
|
+
expect(handlerFn).toHaveBeenCalledWith({
|
|
2215
|
+
key,
|
|
2216
|
+
owner,
|
|
2217
|
+
});
|
|
2218
|
+
});
|
|
2219
|
+
test("Should dispatch UnavailableLockEvent when key is unexpired and acquired by same owner", async () => {
|
|
2220
|
+
const key = "a";
|
|
2221
|
+
const owner = "b";
|
|
2222
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
2223
|
+
const lock = lockProvider.create(key, {
|
|
2224
|
+
ttl,
|
|
2225
|
+
owner,
|
|
2226
|
+
});
|
|
2227
|
+
await lock.acquire();
|
|
2228
|
+
const handlerFn = vi.fn((_event) => { });
|
|
2229
|
+
await lockProvider.addListener(LOCK_EVENTS.UNAVAILABLE, handlerFn);
|
|
2230
|
+
try {
|
|
2231
|
+
await lock.acquireOrFail();
|
|
2232
|
+
}
|
|
2233
|
+
catch {
|
|
2234
|
+
/* EMPTY */
|
|
2235
|
+
}
|
|
2236
|
+
await delay(TimeSpan.fromMilliseconds(10));
|
|
2237
|
+
expect(handlerFn).toHaveBeenCalledTimes(1);
|
|
2238
|
+
expect(handlerFn).toHaveBeenCalledWith({
|
|
2239
|
+
key,
|
|
2240
|
+
owner,
|
|
2241
|
+
});
|
|
2242
|
+
});
|
|
2243
|
+
test("Should dispatch UnavailableLockEvent when key is unexpireable and acquired by different owner", async () => {
|
|
2244
|
+
const key = "a";
|
|
2245
|
+
const ttl = null;
|
|
2246
|
+
await lockProvider.create(key, { ttl }).acquire();
|
|
2247
|
+
const handlerFn = vi.fn((_event) => { });
|
|
2248
|
+
await lockProvider.addListener(LOCK_EVENTS.UNAVAILABLE, handlerFn);
|
|
2249
|
+
const owner = "b";
|
|
2250
|
+
try {
|
|
2251
|
+
await lockProvider
|
|
2252
|
+
.create(key, { ttl, owner })
|
|
2253
|
+
.acquireOrFail();
|
|
2254
|
+
}
|
|
2255
|
+
catch {
|
|
2256
|
+
/* EMPTY */
|
|
2257
|
+
}
|
|
2258
|
+
await delay(TimeSpan.fromMilliseconds(10));
|
|
2259
|
+
expect(handlerFn).toHaveBeenCalledTimes(1);
|
|
2260
|
+
expect(handlerFn).toHaveBeenCalledWith({
|
|
2261
|
+
key,
|
|
2262
|
+
owner,
|
|
2263
|
+
});
|
|
2264
|
+
});
|
|
2265
|
+
test("Should dispatch UnavailableLockEvent when key is unexpired and acquired by different owner", async () => {
|
|
2266
|
+
const key = "a";
|
|
2267
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
2268
|
+
await lockProvider.create(key, { ttl }).acquire();
|
|
2269
|
+
const handlerFn = vi.fn((_event) => { });
|
|
2270
|
+
await lockProvider.addListener(LOCK_EVENTS.UNAVAILABLE, handlerFn);
|
|
2271
|
+
const owner = "b";
|
|
2272
|
+
try {
|
|
2273
|
+
await lockProvider
|
|
2274
|
+
.create(key, { ttl, owner })
|
|
2275
|
+
.acquireOrFail();
|
|
2276
|
+
}
|
|
2277
|
+
catch {
|
|
2278
|
+
/* EMPTY */
|
|
2279
|
+
}
|
|
2280
|
+
await delay(TimeSpan.fromMilliseconds(10));
|
|
2281
|
+
expect(handlerFn).toHaveBeenCalledTimes(1);
|
|
2282
|
+
expect(handlerFn).toHaveBeenCalledWith({
|
|
2283
|
+
key,
|
|
2284
|
+
owner,
|
|
2285
|
+
});
|
|
2286
|
+
});
|
|
2287
|
+
});
|
|
2288
|
+
describe("method: acquireBlocking", () => {
|
|
2289
|
+
test("Should dispatch AcquiredLockEvent when key doesnt exists", async () => {
|
|
2290
|
+
const key = "a";
|
|
2291
|
+
const owner = "b";
|
|
2292
|
+
const ttl = null;
|
|
2293
|
+
const handlerFn = vi.fn((_event) => { });
|
|
2294
|
+
await lockProvider.addListener(LOCK_EVENTS.ACQUIRED, handlerFn);
|
|
2295
|
+
await lockProvider
|
|
2296
|
+
.create(key, {
|
|
2297
|
+
ttl,
|
|
2298
|
+
owner,
|
|
2299
|
+
})
|
|
2300
|
+
.acquireBlocking();
|
|
2301
|
+
await delay(TimeSpan.fromMilliseconds(10));
|
|
2302
|
+
expect(handlerFn).toHaveBeenCalledTimes(1);
|
|
2303
|
+
expect(handlerFn).toHaveBeenCalledWith({
|
|
2304
|
+
key,
|
|
2305
|
+
owner,
|
|
2306
|
+
ttl,
|
|
2307
|
+
});
|
|
2308
|
+
});
|
|
2309
|
+
test("Should dispatch AcquiredLockEvent when key is expired", async () => {
|
|
2310
|
+
const key = "a";
|
|
2311
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
2312
|
+
await lockProvider.create(key, { ttl }).acquire();
|
|
2313
|
+
await delay(ttl);
|
|
2314
|
+
const handlerFn = vi.fn((_event) => { });
|
|
2315
|
+
await lockProvider.addListener(LOCK_EVENTS.ACQUIRED, handlerFn);
|
|
2316
|
+
const owner = "b";
|
|
2317
|
+
const ttl2 = null;
|
|
2318
|
+
await lockProvider
|
|
2319
|
+
.create(key, { ttl: ttl2, owner })
|
|
2320
|
+
.acquireBlocking({
|
|
2321
|
+
time: TimeSpan.fromMilliseconds(5),
|
|
2322
|
+
interval: TimeSpan.fromMilliseconds(5),
|
|
2323
|
+
});
|
|
2324
|
+
await delay(TimeSpan.fromMilliseconds(10));
|
|
2325
|
+
expect(handlerFn).toHaveBeenCalledTimes(1);
|
|
2326
|
+
expect(handlerFn).toHaveBeenCalledWith({
|
|
2327
|
+
key,
|
|
2328
|
+
owner,
|
|
2329
|
+
ttl: ttl2,
|
|
2330
|
+
});
|
|
2331
|
+
});
|
|
2332
|
+
test("Should dispatch UnavailableLockEvent when key is unexpireable and acquired by same owner", async () => {
|
|
2333
|
+
const key = "a";
|
|
2334
|
+
const owner = "b";
|
|
2335
|
+
const ttl = null;
|
|
2336
|
+
const lock = lockProvider.create(key, { ttl, owner });
|
|
2337
|
+
await lock.acquire();
|
|
2338
|
+
const handlerFn = vi.fn((_event) => { });
|
|
2339
|
+
await lockProvider.addListener(LOCK_EVENTS.UNAVAILABLE, handlerFn);
|
|
2340
|
+
await lock.acquireBlocking({
|
|
2341
|
+
time: TimeSpan.fromMilliseconds(5),
|
|
2342
|
+
interval: TimeSpan.fromMilliseconds(5),
|
|
2343
|
+
});
|
|
2344
|
+
await delay(TimeSpan.fromMilliseconds(10));
|
|
2345
|
+
expect(handlerFn).toHaveBeenCalledTimes(1);
|
|
2346
|
+
expect(handlerFn).toHaveBeenCalledWith({
|
|
2347
|
+
key,
|
|
2348
|
+
owner,
|
|
2349
|
+
});
|
|
2350
|
+
});
|
|
2351
|
+
test("Should dispatch UnavailableLockEvent when key is unexpired and acquired by same owner", async () => {
|
|
2352
|
+
const key = "a";
|
|
2353
|
+
const owner = "b";
|
|
2354
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
2355
|
+
const lock = lockProvider.create(key, {
|
|
2356
|
+
ttl,
|
|
2357
|
+
owner,
|
|
2358
|
+
});
|
|
2359
|
+
await lock.acquire();
|
|
2360
|
+
const handlerFn = vi.fn((_event) => { });
|
|
2361
|
+
await lockProvider.addListener(LOCK_EVENTS.UNAVAILABLE, handlerFn);
|
|
2362
|
+
await lock.acquireBlocking({
|
|
2363
|
+
time: TimeSpan.fromMilliseconds(5),
|
|
2364
|
+
interval: TimeSpan.fromMilliseconds(5),
|
|
2365
|
+
});
|
|
2366
|
+
await delay(TimeSpan.fromMilliseconds(10));
|
|
2367
|
+
expect(handlerFn).toHaveBeenCalledTimes(1);
|
|
2368
|
+
expect(handlerFn).toHaveBeenCalledWith({
|
|
2369
|
+
key,
|
|
2370
|
+
owner,
|
|
2371
|
+
});
|
|
2372
|
+
});
|
|
2373
|
+
test("Should dispatch UnavailableLockEvent when key is unexpireable and acquired by different owner", async () => {
|
|
2374
|
+
const key = "a";
|
|
2375
|
+
const ttl = null;
|
|
2376
|
+
await lockProvider.create(key, { ttl }).acquire();
|
|
2377
|
+
const handlerFn = vi.fn((_event) => { });
|
|
2378
|
+
await lockProvider.addListener(LOCK_EVENTS.UNAVAILABLE, handlerFn);
|
|
2379
|
+
const owner = "b";
|
|
2380
|
+
await lockProvider.create(key, { ttl, owner }).acquireBlocking({
|
|
2381
|
+
time: TimeSpan.fromMilliseconds(5),
|
|
2382
|
+
interval: TimeSpan.fromMilliseconds(5),
|
|
2383
|
+
});
|
|
2384
|
+
await delay(TimeSpan.fromMilliseconds(10));
|
|
2385
|
+
expect(handlerFn).toHaveBeenCalledTimes(1);
|
|
2386
|
+
expect(handlerFn).toHaveBeenCalledWith({
|
|
2387
|
+
key,
|
|
2388
|
+
owner,
|
|
2389
|
+
});
|
|
2390
|
+
});
|
|
2391
|
+
test("Should dispatch UnavailableLockEvent when key is unexpired and acquired by different owner", async () => {
|
|
2392
|
+
const key = "a";
|
|
2393
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
2394
|
+
await lockProvider.create(key, { ttl }).acquire();
|
|
2395
|
+
const handlerFn = vi.fn((_event) => { });
|
|
2396
|
+
await lockProvider.addListener(LOCK_EVENTS.UNAVAILABLE, handlerFn);
|
|
2397
|
+
const owner = "b";
|
|
2398
|
+
await lockProvider.create(key, { ttl, owner }).acquireBlocking({
|
|
2399
|
+
time: TimeSpan.fromMilliseconds(5),
|
|
2400
|
+
interval: TimeSpan.fromMilliseconds(5),
|
|
2401
|
+
});
|
|
2402
|
+
await delay(TimeSpan.fromMilliseconds(10));
|
|
2403
|
+
expect(handlerFn).toHaveBeenCalledTimes(1);
|
|
2404
|
+
expect(handlerFn).toHaveBeenCalledWith({
|
|
2405
|
+
key,
|
|
2406
|
+
owner,
|
|
2407
|
+
});
|
|
2408
|
+
});
|
|
2409
|
+
});
|
|
2410
|
+
describe("method: acquireBlockingOrFail", () => {
|
|
2411
|
+
test("Should dispatch AcquiredLockEvent when key doesnt exists", async () => {
|
|
2412
|
+
const key = "a";
|
|
2413
|
+
const owner = "b";
|
|
2414
|
+
const ttl = null;
|
|
2415
|
+
const handlerFn = vi.fn((_event) => { });
|
|
2416
|
+
await lockProvider.addListener(LOCK_EVENTS.ACQUIRED, handlerFn);
|
|
2417
|
+
await lockProvider
|
|
2418
|
+
.create(key, {
|
|
2419
|
+
ttl,
|
|
2420
|
+
owner,
|
|
2421
|
+
})
|
|
2422
|
+
.acquireBlockingOrFail({
|
|
2423
|
+
time: TimeSpan.fromMilliseconds(5),
|
|
2424
|
+
interval: TimeSpan.fromMilliseconds(5),
|
|
2425
|
+
});
|
|
2426
|
+
await delay(TimeSpan.fromMilliseconds(10));
|
|
2427
|
+
expect(handlerFn).toHaveBeenCalledTimes(1);
|
|
2428
|
+
expect(handlerFn).toHaveBeenCalledWith({
|
|
2429
|
+
key,
|
|
2430
|
+
owner,
|
|
2431
|
+
ttl,
|
|
2432
|
+
});
|
|
2433
|
+
});
|
|
2434
|
+
test("Should dispatch AcquiredLockEvent when key is expired", async () => {
|
|
2435
|
+
const key = "a";
|
|
2436
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
2437
|
+
await lockProvider.create(key, { ttl }).acquire();
|
|
2438
|
+
await delay(ttl);
|
|
2439
|
+
const handlerFn = vi.fn((_event) => { });
|
|
2440
|
+
await lockProvider.addListener(LOCK_EVENTS.ACQUIRED, handlerFn);
|
|
2441
|
+
const owner = "b";
|
|
2442
|
+
const ttl2 = null;
|
|
2443
|
+
await lockProvider
|
|
2444
|
+
.create(key, { ttl: ttl2, owner })
|
|
2445
|
+
.acquireBlockingOrFail({
|
|
2446
|
+
time: TimeSpan.fromMilliseconds(5),
|
|
2447
|
+
interval: TimeSpan.fromMilliseconds(5),
|
|
2448
|
+
});
|
|
2449
|
+
await delay(TimeSpan.fromMilliseconds(10));
|
|
2450
|
+
expect(handlerFn).toHaveBeenCalledTimes(1);
|
|
2451
|
+
expect(handlerFn).toHaveBeenCalledWith({
|
|
2452
|
+
key,
|
|
2453
|
+
owner,
|
|
2454
|
+
ttl: ttl2,
|
|
2455
|
+
});
|
|
2456
|
+
});
|
|
2457
|
+
test("Should dispatch UnavailableLockEvent when key is unexpireable and acquired by same owner", async () => {
|
|
2458
|
+
const key = "a";
|
|
2459
|
+
const owner = "b";
|
|
2460
|
+
const ttl = null;
|
|
2461
|
+
const lock = lockProvider.create(key, { ttl, owner });
|
|
2462
|
+
await lock.acquire();
|
|
2463
|
+
const handlerFn = vi.fn((_event) => { });
|
|
2464
|
+
await lockProvider.addListener(LOCK_EVENTS.UNAVAILABLE, handlerFn);
|
|
2465
|
+
try {
|
|
2466
|
+
await lock.acquireBlockingOrFail({
|
|
2467
|
+
time: TimeSpan.fromMilliseconds(5),
|
|
1009
2468
|
interval: TimeSpan.fromMilliseconds(5),
|
|
1010
2469
|
});
|
|
1011
|
-
|
|
1012
|
-
|
|
1013
|
-
|
|
1014
|
-
|
|
1015
|
-
|
|
1016
|
-
|
|
1017
|
-
|
|
1018
|
-
|
|
1019
|
-
|
|
1020
|
-
|
|
1021
|
-
|
|
1022
|
-
|
|
1023
|
-
|
|
1024
|
-
|
|
1025
|
-
|
|
1026
|
-
|
|
1027
|
-
|
|
1028
|
-
|
|
1029
|
-
|
|
1030
|
-
|
|
1031
|
-
|
|
1032
|
-
|
|
1033
|
-
|
|
1034
|
-
|
|
1035
|
-
expect(event_?.ttl?.toMilliseconds()).toBe(TTL.toMilliseconds());
|
|
1036
|
-
await unsubscribe();
|
|
1037
|
-
});
|
|
1038
|
-
test("Should dispatch ReleasedLockEvent when lock is not acquired", async () => {
|
|
1039
|
-
const key = "a";
|
|
1040
|
-
const owner = "b";
|
|
1041
|
-
const lock = lockProvider.create(key, {
|
|
1042
|
-
owner,
|
|
1043
|
-
ttl: TTL,
|
|
1044
|
-
});
|
|
1045
|
-
let event_ = null;
|
|
1046
|
-
const unsubscribe = await lockProvider.subscribe(LOCK_EVENTS.RELEASED, (event) => {
|
|
1047
|
-
event_ = event;
|
|
1048
|
-
});
|
|
1049
|
-
await lock.runOrFail(async () => {
|
|
1050
|
-
await LazyPromise.delay(DELAY_TIME);
|
|
1051
|
-
});
|
|
1052
|
-
await LazyPromise.delay(DELAY_TIME);
|
|
1053
|
-
expect(event_?.key).toBe(key);
|
|
1054
|
-
expect(event_?.owner).toBe(owner);
|
|
1055
|
-
await unsubscribe();
|
|
1056
|
-
});
|
|
1057
|
-
test("Should dispatch UnavailableLockEvent when lock is acquired", async () => {
|
|
1058
|
-
const key = "a";
|
|
1059
|
-
const owner = "b";
|
|
1060
|
-
const lock = lockProvider.create(key, {
|
|
1061
|
-
owner,
|
|
1062
|
-
});
|
|
1063
|
-
let event_ = null;
|
|
1064
|
-
await lock.acquire();
|
|
1065
|
-
const unsubscribe = await lockProvider.subscribe(LOCK_EVENTS.UNAVAILABLE, (event) => {
|
|
1066
|
-
event_ = event;
|
|
1067
|
-
});
|
|
1068
|
-
try {
|
|
1069
|
-
await lock.runOrFail(async () => {
|
|
1070
|
-
await LazyPromise.delay(DELAY_TIME);
|
|
1071
|
-
});
|
|
1072
|
-
await LazyPromise.delay(DELAY_TIME);
|
|
1073
|
-
}
|
|
1074
|
-
catch {
|
|
1075
|
-
/* Empty */
|
|
1076
|
-
}
|
|
1077
|
-
expect(event_?.key).toBe("a");
|
|
1078
|
-
expect(event_?.owner).toBe(owner);
|
|
1079
|
-
await unsubscribe();
|
|
1080
|
-
});
|
|
1081
|
-
});
|
|
1082
|
-
describe("method: acquire", () => {
|
|
1083
|
-
test("Should dispatch AcquiredLockEvent when lock is not acquired", async () => {
|
|
1084
|
-
const key = "a";
|
|
1085
|
-
const owner = "b";
|
|
1086
|
-
const lock = lockProvider.create(key, {
|
|
1087
|
-
owner,
|
|
1088
|
-
ttl: TTL,
|
|
1089
|
-
});
|
|
1090
|
-
let event_ = null;
|
|
1091
|
-
const unsubscribe = await lockProvider.subscribe(LOCK_EVENTS.ACQUIRED, (event) => {
|
|
1092
|
-
event_ = event;
|
|
1093
|
-
});
|
|
1094
|
-
await lock.acquire();
|
|
1095
|
-
await LazyPromise.delay(DELAY_TIME);
|
|
1096
|
-
expect(event_?.key).toBe("a");
|
|
1097
|
-
expect(event_?.owner).toBe(owner);
|
|
1098
|
-
expect(event_?.ttl?.toMilliseconds()).toBe(TTL.toMilliseconds());
|
|
1099
|
-
await unsubscribe();
|
|
1100
|
-
});
|
|
1101
|
-
test("Should dispatch UnavailableLockEvent when lock is acquired", async () => {
|
|
1102
|
-
const key = "a";
|
|
1103
|
-
const owner = "b";
|
|
1104
|
-
const lock = lockProvider.create(key, {
|
|
1105
|
-
owner,
|
|
1106
|
-
});
|
|
1107
|
-
let event_ = null;
|
|
1108
|
-
await lock.acquire();
|
|
1109
|
-
const unsubscribe = await lockProvider.subscribe(LOCK_EVENTS.UNAVAILABLE, (event) => {
|
|
1110
|
-
event_ = event;
|
|
1111
|
-
});
|
|
1112
|
-
await lock.acquire();
|
|
1113
|
-
await LazyPromise.delay(DELAY_TIME);
|
|
1114
|
-
expect(event_?.key).toBe("a");
|
|
1115
|
-
expect(event_?.owner).toBe(owner);
|
|
1116
|
-
await unsubscribe();
|
|
1117
|
-
});
|
|
1118
|
-
});
|
|
1119
|
-
describe("method: acquireBlocking", () => {
|
|
1120
|
-
test("Should dispatch AcquiredLockEvent when lock is not acquired", async () => {
|
|
1121
|
-
const key = "a";
|
|
1122
|
-
const owner = "b";
|
|
1123
|
-
const lock = lockProvider.create(key, {
|
|
1124
|
-
owner,
|
|
1125
|
-
ttl: TTL,
|
|
1126
|
-
});
|
|
1127
|
-
let event_ = null;
|
|
1128
|
-
const unsubscribe = await lockProvider.subscribe(LOCK_EVENTS.ACQUIRED, (event) => {
|
|
1129
|
-
event_ = event;
|
|
1130
|
-
});
|
|
1131
|
-
await lock.acquireBlocking({
|
|
2470
|
+
}
|
|
2471
|
+
catch {
|
|
2472
|
+
/* EMPTY */
|
|
2473
|
+
}
|
|
2474
|
+
await delay(TimeSpan.fromMilliseconds(10));
|
|
2475
|
+
expect(handlerFn).toHaveBeenCalledTimes(1);
|
|
2476
|
+
expect(handlerFn).toHaveBeenCalledWith({
|
|
2477
|
+
key,
|
|
2478
|
+
owner,
|
|
2479
|
+
});
|
|
2480
|
+
});
|
|
2481
|
+
test("Should dispatch UnavailableLockEvent when key is unexpired and acquired by same owner", async () => {
|
|
2482
|
+
const key = "a";
|
|
2483
|
+
const owner = "b";
|
|
2484
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
2485
|
+
const lock = lockProvider.create(key, {
|
|
2486
|
+
ttl,
|
|
2487
|
+
owner,
|
|
2488
|
+
});
|
|
2489
|
+
await lock.acquire();
|
|
2490
|
+
const handlerFn = vi.fn((_event) => { });
|
|
2491
|
+
await lockProvider.addListener(LOCK_EVENTS.UNAVAILABLE, handlerFn);
|
|
2492
|
+
try {
|
|
2493
|
+
await lock.acquireBlockingOrFail({
|
|
1132
2494
|
time: TimeSpan.fromMilliseconds(5),
|
|
1133
2495
|
interval: TimeSpan.fromMilliseconds(5),
|
|
1134
2496
|
});
|
|
1135
|
-
|
|
1136
|
-
|
|
1137
|
-
|
|
1138
|
-
|
|
1139
|
-
|
|
1140
|
-
|
|
1141
|
-
|
|
1142
|
-
|
|
1143
|
-
|
|
1144
|
-
|
|
1145
|
-
|
|
1146
|
-
|
|
1147
|
-
|
|
1148
|
-
|
|
2497
|
+
}
|
|
2498
|
+
catch {
|
|
2499
|
+
/* EMPTY */
|
|
2500
|
+
}
|
|
2501
|
+
await delay(TimeSpan.fromMilliseconds(10));
|
|
2502
|
+
expect(handlerFn).toHaveBeenCalledTimes(1);
|
|
2503
|
+
expect(handlerFn).toHaveBeenCalledWith({
|
|
2504
|
+
key,
|
|
2505
|
+
owner,
|
|
2506
|
+
});
|
|
2507
|
+
});
|
|
2508
|
+
test("Should dispatch UnavailableLockEvent when key is unexpireable and acquired by different owner", async () => {
|
|
2509
|
+
const key = "a";
|
|
2510
|
+
const ttl = null;
|
|
2511
|
+
await lockProvider.create(key, { ttl }).acquire();
|
|
2512
|
+
const handlerFn = vi.fn((_event) => { });
|
|
2513
|
+
await lockProvider.addListener(LOCK_EVENTS.UNAVAILABLE, handlerFn);
|
|
2514
|
+
const owner = "b";
|
|
2515
|
+
try {
|
|
2516
|
+
await lockProvider
|
|
2517
|
+
.create(key, { ttl, owner })
|
|
2518
|
+
.acquireBlockingOrFail({
|
|
1149
2519
|
time: TimeSpan.fromMilliseconds(5),
|
|
1150
2520
|
interval: TimeSpan.fromMilliseconds(5),
|
|
1151
2521
|
});
|
|
1152
|
-
|
|
1153
|
-
|
|
1154
|
-
|
|
1155
|
-
|
|
2522
|
+
}
|
|
2523
|
+
catch {
|
|
2524
|
+
/* EMPTY */
|
|
2525
|
+
}
|
|
2526
|
+
await delay(TimeSpan.fromMilliseconds(10));
|
|
2527
|
+
expect(handlerFn).toHaveBeenCalledTimes(1);
|
|
2528
|
+
expect(handlerFn).toHaveBeenCalledWith({
|
|
2529
|
+
key,
|
|
2530
|
+
owner,
|
|
2531
|
+
});
|
|
2532
|
+
});
|
|
2533
|
+
test("Should dispatch UnavailableLockEvent when key is unexpired and acquired by different owner", async () => {
|
|
2534
|
+
const key = "a";
|
|
2535
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
2536
|
+
await lockProvider.create(key, { ttl }).acquire();
|
|
2537
|
+
const handlerFn = vi.fn((_event) => { });
|
|
2538
|
+
await lockProvider.addListener(LOCK_EVENTS.UNAVAILABLE, handlerFn);
|
|
2539
|
+
const owner = "b";
|
|
2540
|
+
try {
|
|
2541
|
+
await lockProvider
|
|
2542
|
+
.create(key, { ttl, owner })
|
|
2543
|
+
.acquireBlockingOrFail({
|
|
1156
2544
|
time: TimeSpan.fromMilliseconds(5),
|
|
1157
2545
|
interval: TimeSpan.fromMilliseconds(5),
|
|
1158
2546
|
});
|
|
1159
|
-
|
|
1160
|
-
|
|
1161
|
-
|
|
1162
|
-
|
|
1163
|
-
|
|
1164
|
-
|
|
1165
|
-
|
|
1166
|
-
|
|
1167
|
-
|
|
1168
|
-
|
|
1169
|
-
|
|
1170
|
-
|
|
1171
|
-
|
|
1172
|
-
|
|
1173
|
-
|
|
1174
|
-
|
|
1175
|
-
|
|
1176
|
-
|
|
1177
|
-
|
|
1178
|
-
|
|
1179
|
-
|
|
1180
|
-
|
|
1181
|
-
|
|
1182
|
-
|
|
1183
|
-
});
|
|
1184
|
-
|
|
1185
|
-
|
|
1186
|
-
|
|
1187
|
-
|
|
1188
|
-
|
|
1189
|
-
|
|
1190
|
-
|
|
1191
|
-
|
|
1192
|
-
|
|
1193
|
-
|
|
1194
|
-
|
|
1195
|
-
|
|
1196
|
-
|
|
1197
|
-
|
|
1198
|
-
|
|
1199
|
-
|
|
1200
|
-
|
|
1201
|
-
|
|
1202
|
-
|
|
1203
|
-
|
|
1204
|
-
|
|
1205
|
-
|
|
1206
|
-
|
|
1207
|
-
|
|
1208
|
-
|
|
1209
|
-
|
|
1210
|
-
|
|
1211
|
-
|
|
1212
|
-
|
|
1213
|
-
|
|
1214
|
-
|
|
1215
|
-
|
|
1216
|
-
|
|
1217
|
-
|
|
1218
|
-
|
|
1219
|
-
|
|
1220
|
-
|
|
1221
|
-
|
|
1222
|
-
|
|
1223
|
-
|
|
1224
|
-
|
|
1225
|
-
|
|
1226
|
-
|
|
1227
|
-
|
|
1228
|
-
|
|
1229
|
-
|
|
1230
|
-
|
|
1231
|
-
|
|
1232
|
-
|
|
1233
|
-
|
|
1234
|
-
|
|
1235
|
-
|
|
1236
|
-
|
|
1237
|
-
|
|
1238
|
-
|
|
1239
|
-
|
|
1240
|
-
|
|
1241
|
-
|
|
1242
|
-
|
|
1243
|
-
|
|
1244
|
-
|
|
1245
|
-
});
|
|
1246
|
-
});
|
|
1247
|
-
|
|
1248
|
-
|
|
1249
|
-
|
|
1250
|
-
|
|
1251
|
-
|
|
1252
|
-
|
|
1253
|
-
|
|
1254
|
-
|
|
1255
|
-
|
|
1256
|
-
|
|
1257
|
-
|
|
1258
|
-
|
|
2547
|
+
}
|
|
2548
|
+
catch {
|
|
2549
|
+
/* EMPTY */
|
|
2550
|
+
}
|
|
2551
|
+
await delay(TimeSpan.fromMilliseconds(10));
|
|
2552
|
+
expect(handlerFn).toHaveBeenCalledTimes(1);
|
|
2553
|
+
expect(handlerFn).toHaveBeenCalledWith({
|
|
2554
|
+
key,
|
|
2555
|
+
owner,
|
|
2556
|
+
});
|
|
2557
|
+
});
|
|
2558
|
+
});
|
|
2559
|
+
describe("method: release", () => {
|
|
2560
|
+
test("Should dispatch UnownedReleaseTryLockEvent when key doesnt exists", async () => {
|
|
2561
|
+
const key = "a";
|
|
2562
|
+
const owner = "b";
|
|
2563
|
+
const handlerFn = vi.fn((_event) => { });
|
|
2564
|
+
await lockProvider.addListener(LOCK_EVENTS.UNOWNED_RELEASE_TRY, handlerFn);
|
|
2565
|
+
await lockProvider.create(key, { owner }).release();
|
|
2566
|
+
await delay(TimeSpan.fromMilliseconds(10));
|
|
2567
|
+
expect(handlerFn).toHaveBeenCalledTimes(1);
|
|
2568
|
+
expect(handlerFn).toHaveBeenCalledWith({
|
|
2569
|
+
key,
|
|
2570
|
+
owner,
|
|
2571
|
+
});
|
|
2572
|
+
});
|
|
2573
|
+
test("Should dispatch UnownedReleaseTryLockEvent when key is unexpireable and released by different owner", async () => {
|
|
2574
|
+
const key = "a";
|
|
2575
|
+
const ttl = null;
|
|
2576
|
+
await lockProvider.create(key, { ttl }).acquire();
|
|
2577
|
+
const handlerFn = vi.fn((_event) => { });
|
|
2578
|
+
await lockProvider.addListener(LOCK_EVENTS.UNOWNED_RELEASE_TRY, handlerFn);
|
|
2579
|
+
const owner = "b";
|
|
2580
|
+
await lockProvider.create(key, { ttl, owner }).release();
|
|
2581
|
+
await delay(TimeSpan.fromMilliseconds(10));
|
|
2582
|
+
expect(handlerFn).toHaveBeenCalledTimes(1);
|
|
2583
|
+
expect(handlerFn).toHaveBeenCalledWith({
|
|
2584
|
+
key,
|
|
2585
|
+
owner,
|
|
2586
|
+
});
|
|
2587
|
+
});
|
|
2588
|
+
test("Should dispatch UnownedReleaseTryLockEvent when key is unexpired and released by different owner", async () => {
|
|
2589
|
+
const key = "a";
|
|
2590
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
2591
|
+
await lockProvider.create(key, { ttl }).acquire();
|
|
2592
|
+
const handlerFn = vi.fn((_event) => { });
|
|
2593
|
+
await lockProvider.addListener(LOCK_EVENTS.UNOWNED_RELEASE_TRY, handlerFn);
|
|
2594
|
+
const owner = "b";
|
|
2595
|
+
await lockProvider.create(key, { ttl, owner }).release();
|
|
2596
|
+
await delay(TimeSpan.fromMilliseconds(10));
|
|
2597
|
+
expect(handlerFn).toHaveBeenCalledTimes(1);
|
|
2598
|
+
expect(handlerFn).toHaveBeenCalledWith({
|
|
2599
|
+
key,
|
|
2600
|
+
owner,
|
|
2601
|
+
});
|
|
2602
|
+
});
|
|
2603
|
+
test("Should dispatch UnownedReleaseTryLockEvent when key is expired and released by different owner", async () => {
|
|
2604
|
+
const key = "a";
|
|
2605
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
2606
|
+
await lockProvider.create(key, { ttl }).acquire();
|
|
2607
|
+
const handlerFn = vi.fn((_event) => { });
|
|
2608
|
+
await lockProvider.addListener(LOCK_EVENTS.UNOWNED_RELEASE_TRY, handlerFn);
|
|
2609
|
+
const owner = "b";
|
|
2610
|
+
await lockProvider.create(key, { ttl, owner }).release();
|
|
2611
|
+
await delay(ttl);
|
|
2612
|
+
expect(handlerFn).toHaveBeenCalledTimes(1);
|
|
2613
|
+
expect(handlerFn).toHaveBeenCalledWith({
|
|
2614
|
+
key,
|
|
2615
|
+
owner,
|
|
2616
|
+
});
|
|
2617
|
+
});
|
|
2618
|
+
test("Should dispatch UnownedReleaseTryLockEvent when key is expired and released by same owner", async () => {
|
|
2619
|
+
const key = "a";
|
|
2620
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
2621
|
+
const owner = "b";
|
|
2622
|
+
const lock = lockProvider.create(key, { ttl, owner });
|
|
2623
|
+
await lock.acquire();
|
|
2624
|
+
await delay(ttl);
|
|
2625
|
+
const handlerFn = vi.fn((_event) => { });
|
|
2626
|
+
await lockProvider.addListener(LOCK_EVENTS.UNOWNED_RELEASE_TRY, handlerFn);
|
|
2627
|
+
await lock.release();
|
|
2628
|
+
await delay(TimeSpan.fromMilliseconds(10));
|
|
2629
|
+
expect(handlerFn).toHaveBeenCalledTimes(1);
|
|
2630
|
+
expect(handlerFn).toHaveBeenCalledWith({
|
|
2631
|
+
key,
|
|
2632
|
+
owner,
|
|
2633
|
+
});
|
|
2634
|
+
});
|
|
2635
|
+
test("Should dispatch ReleasedLockEvent when key is unexpireable and released by same owner", async () => {
|
|
2636
|
+
const key = "a";
|
|
2637
|
+
const ttl = null;
|
|
2638
|
+
const owner = "b";
|
|
2639
|
+
const lock = lockProvider.create(key, { ttl, owner });
|
|
2640
|
+
await lock.acquire();
|
|
2641
|
+
const handlerFn = vi.fn((_event) => { });
|
|
2642
|
+
await lockProvider.addListener(LOCK_EVENTS.RELEASED, handlerFn);
|
|
2643
|
+
await lock.release();
|
|
2644
|
+
await delay(TimeSpan.fromMilliseconds(10));
|
|
2645
|
+
expect(handlerFn).toHaveBeenCalledTimes(1);
|
|
2646
|
+
expect(handlerFn).toHaveBeenCalledWith({
|
|
2647
|
+
key,
|
|
2648
|
+
owner,
|
|
2649
|
+
});
|
|
2650
|
+
});
|
|
2651
|
+
test("Should dispatch ReleasedLockEvent when key is unexpired and released by same owner", async () => {
|
|
2652
|
+
const key = "a";
|
|
2653
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
2654
|
+
const owner = "b";
|
|
2655
|
+
const lock = lockProvider.create(key, { ttl, owner });
|
|
2656
|
+
await lock.acquire();
|
|
2657
|
+
const handlerFn = vi.fn((_event) => { });
|
|
2658
|
+
await lockProvider.addListener(LOCK_EVENTS.RELEASED, handlerFn);
|
|
2659
|
+
await lock.release();
|
|
2660
|
+
await delay(TimeSpan.fromMilliseconds(10));
|
|
2661
|
+
expect(handlerFn).toHaveBeenCalledTimes(1);
|
|
2662
|
+
expect(handlerFn).toHaveBeenCalledWith({
|
|
2663
|
+
key,
|
|
2664
|
+
owner,
|
|
2665
|
+
});
|
|
2666
|
+
});
|
|
2667
|
+
});
|
|
2668
|
+
describe("method: releaseOrFail", () => {
|
|
2669
|
+
test("Should dispatch UnownedReleaseTryLockEvent when key doesnt exists", async () => {
|
|
2670
|
+
const key = "a";
|
|
2671
|
+
const owner = "b";
|
|
2672
|
+
const handlerFn = vi.fn((_event) => { });
|
|
2673
|
+
await lockProvider.addListener(LOCK_EVENTS.UNOWNED_RELEASE_TRY, handlerFn);
|
|
2674
|
+
try {
|
|
2675
|
+
await lockProvider.create(key, { owner }).releaseOrFail();
|
|
2676
|
+
}
|
|
2677
|
+
catch {
|
|
2678
|
+
/* EMPTY */
|
|
2679
|
+
}
|
|
2680
|
+
await delay(TimeSpan.fromMilliseconds(10));
|
|
2681
|
+
expect(handlerFn).toHaveBeenCalledTimes(1);
|
|
2682
|
+
expect(handlerFn).toHaveBeenCalledWith({
|
|
2683
|
+
key,
|
|
2684
|
+
owner,
|
|
2685
|
+
});
|
|
2686
|
+
});
|
|
2687
|
+
test("Should dispatch UnownedReleaseTryLockEvent when key is unexpireable and released by different owner", async () => {
|
|
2688
|
+
const key = "a";
|
|
2689
|
+
const ttl = null;
|
|
2690
|
+
await lockProvider.create(key, { ttl }).acquire();
|
|
2691
|
+
const handlerFn = vi.fn((_event) => { });
|
|
2692
|
+
await lockProvider.addListener(LOCK_EVENTS.UNOWNED_RELEASE_TRY, handlerFn);
|
|
2693
|
+
const owner = "b";
|
|
2694
|
+
try {
|
|
2695
|
+
await lockProvider
|
|
2696
|
+
.create(key, { ttl, owner })
|
|
2697
|
+
.releaseOrFail();
|
|
2698
|
+
}
|
|
2699
|
+
catch {
|
|
2700
|
+
/* EMPTY */
|
|
2701
|
+
}
|
|
2702
|
+
await delay(TimeSpan.fromMilliseconds(10));
|
|
2703
|
+
expect(handlerFn).toHaveBeenCalledTimes(1);
|
|
2704
|
+
expect(handlerFn).toHaveBeenCalledWith({
|
|
2705
|
+
key,
|
|
2706
|
+
owner,
|
|
2707
|
+
});
|
|
2708
|
+
});
|
|
2709
|
+
test("Should dispatch UnownedReleaseTryLockEvent when key is unexpired and released by different owner", async () => {
|
|
2710
|
+
const key = "a";
|
|
2711
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
2712
|
+
await lockProvider.create(key, { ttl }).acquire();
|
|
2713
|
+
const handlerFn = vi.fn((_event) => { });
|
|
2714
|
+
await lockProvider.addListener(LOCK_EVENTS.UNOWNED_RELEASE_TRY, handlerFn);
|
|
2715
|
+
const owner = "b";
|
|
2716
|
+
try {
|
|
2717
|
+
await lockProvider
|
|
2718
|
+
.create(key, { ttl, owner })
|
|
2719
|
+
.releaseOrFail();
|
|
2720
|
+
}
|
|
2721
|
+
catch {
|
|
2722
|
+
/* EMPTY */
|
|
2723
|
+
}
|
|
2724
|
+
await delay(TimeSpan.fromMilliseconds(10));
|
|
2725
|
+
expect(handlerFn).toHaveBeenCalledTimes(1);
|
|
2726
|
+
expect(handlerFn).toHaveBeenCalledWith({
|
|
2727
|
+
key,
|
|
2728
|
+
owner,
|
|
2729
|
+
});
|
|
2730
|
+
});
|
|
2731
|
+
test("Should dispatch UnownedReleaseTryLockEvent when key is expired and released by different owner", async () => {
|
|
2732
|
+
const key = "a";
|
|
2733
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
2734
|
+
await lockProvider.create(key, { ttl }).acquire();
|
|
2735
|
+
const handlerFn = vi.fn((_event) => { });
|
|
2736
|
+
await lockProvider.addListener(LOCK_EVENTS.UNOWNED_RELEASE_TRY, handlerFn);
|
|
2737
|
+
const owner = "b";
|
|
2738
|
+
try {
|
|
2739
|
+
await lockProvider
|
|
2740
|
+
.create(key, { ttl, owner })
|
|
2741
|
+
.releaseOrFail();
|
|
2742
|
+
}
|
|
2743
|
+
catch {
|
|
2744
|
+
/* EMPTY */
|
|
2745
|
+
}
|
|
2746
|
+
await delay(ttl);
|
|
2747
|
+
expect(handlerFn).toHaveBeenCalledTimes(1);
|
|
2748
|
+
expect(handlerFn).toHaveBeenCalledWith({
|
|
2749
|
+
key,
|
|
2750
|
+
owner,
|
|
2751
|
+
});
|
|
2752
|
+
});
|
|
2753
|
+
test("Should dispatch UnownedReleaseTryLockEvent when key is expired and released by same owner", async () => {
|
|
2754
|
+
const key = "a";
|
|
2755
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
2756
|
+
const owner = "b";
|
|
2757
|
+
const lock = lockProvider.create(key, { ttl, owner });
|
|
2758
|
+
await lock.acquire();
|
|
2759
|
+
await delay(ttl);
|
|
2760
|
+
const handlerFn = vi.fn((_event) => { });
|
|
2761
|
+
await lockProvider.addListener(LOCK_EVENTS.UNOWNED_RELEASE_TRY, handlerFn);
|
|
2762
|
+
try {
|
|
2763
|
+
await lock.releaseOrFail();
|
|
2764
|
+
}
|
|
2765
|
+
catch {
|
|
2766
|
+
/* EMPTY */
|
|
2767
|
+
}
|
|
2768
|
+
await delay(TimeSpan.fromMilliseconds(10));
|
|
2769
|
+
expect(handlerFn).toHaveBeenCalledTimes(1);
|
|
2770
|
+
expect(handlerFn).toHaveBeenCalledWith({
|
|
2771
|
+
key,
|
|
2772
|
+
owner,
|
|
2773
|
+
});
|
|
2774
|
+
});
|
|
2775
|
+
test("Should dispatch ReleasedLockEvent when key is unexpireable and released by same owner", async () => {
|
|
2776
|
+
const key = "a";
|
|
2777
|
+
const ttl = null;
|
|
2778
|
+
const owner = "b";
|
|
2779
|
+
const lock = lockProvider.create(key, { ttl, owner });
|
|
2780
|
+
await lock.acquire();
|
|
2781
|
+
const handlerFn = vi.fn((_event) => { });
|
|
2782
|
+
await lockProvider.addListener(LOCK_EVENTS.RELEASED, handlerFn);
|
|
2783
|
+
try {
|
|
1259
2784
|
await lock.releaseOrFail();
|
|
1260
|
-
|
|
1261
|
-
|
|
1262
|
-
|
|
1263
|
-
|
|
1264
|
-
|
|
1265
|
-
|
|
1266
|
-
|
|
1267
|
-
|
|
1268
|
-
|
|
1269
|
-
|
|
1270
|
-
|
|
1271
|
-
|
|
1272
|
-
|
|
1273
|
-
|
|
1274
|
-
|
|
1275
|
-
|
|
1276
|
-
|
|
1277
|
-
|
|
1278
|
-
|
|
1279
|
-
|
|
1280
|
-
|
|
1281
|
-
|
|
1282
|
-
|
|
1283
|
-
|
|
1284
|
-
|
|
1285
|
-
/* Empty */
|
|
1286
|
-
}
|
|
1287
|
-
expect(event_?.key).toBe(key);
|
|
1288
|
-
expect(event_?.owner).toBe(owner2);
|
|
1289
|
-
await unsubscribe();
|
|
1290
|
-
});
|
|
1291
|
-
});
|
|
1292
|
-
describe("method: forceRelease", () => {
|
|
1293
|
-
test("Should dispatch ForceReleasedLockEvent when lock forcefully released", async () => {
|
|
1294
|
-
const key = "a";
|
|
1295
|
-
const owner1 = "b";
|
|
1296
|
-
const lock1 = lockProvider.create(key, {
|
|
1297
|
-
owner: owner1,
|
|
1298
|
-
});
|
|
1299
|
-
await lock1.acquire();
|
|
1300
|
-
const owner2 = "c";
|
|
1301
|
-
const lock2 = lockProvider.create(key, {
|
|
1302
|
-
owner: owner2,
|
|
1303
|
-
});
|
|
1304
|
-
let event_ = null;
|
|
1305
|
-
const unsubscribe = await lockProvider.subscribe(LOCK_EVENTS.FORCE_RELEASED, (event) => {
|
|
1306
|
-
event_ = event;
|
|
1307
|
-
});
|
|
1308
|
-
await lock2.forceRelease();
|
|
1309
|
-
await LazyPromise.delay(DELAY_TIME);
|
|
1310
|
-
expect(event_?.key).toBe(key);
|
|
1311
|
-
await unsubscribe();
|
|
1312
|
-
});
|
|
1313
|
-
});
|
|
1314
|
-
describe("method: refresh", () => {
|
|
1315
|
-
test("Should dispatch RefreshedLockEvent when refreshed by same owner", async () => {
|
|
1316
|
-
const key = "a";
|
|
1317
|
-
const owner = "b";
|
|
1318
|
-
const lock = lockProvider.create(key, {
|
|
1319
|
-
owner,
|
|
1320
|
-
ttl: TTL,
|
|
1321
|
-
});
|
|
1322
|
-
await lock.acquire();
|
|
1323
|
-
let event_ = null;
|
|
1324
|
-
const unsubscribe = await lockProvider.subscribe(LOCK_EVENTS.REFRESHED, (event) => {
|
|
1325
|
-
event_ = event;
|
|
1326
|
-
});
|
|
1327
|
-
await LazyPromise.delay(TTL.divide(2));
|
|
1328
|
-
const newTTL = TTL.multiply(2);
|
|
1329
|
-
await lock.refresh(newTTL);
|
|
1330
|
-
await LazyPromise.delay(DELAY_TIME);
|
|
1331
|
-
expect(event_?.key).toBe(key);
|
|
1332
|
-
expect(event_?.owner).toBe(owner);
|
|
1333
|
-
expect(event_?.ttl.toMilliseconds()).toBe(newTTL.toMilliseconds());
|
|
1334
|
-
await unsubscribe();
|
|
1335
|
-
});
|
|
1336
|
-
test("Should dispatch UnownedRefreshTryLockEvent when refreshed by different owner", async () => {
|
|
1337
|
-
const key = "a";
|
|
1338
|
-
const owner1 = "b";
|
|
1339
|
-
const lock1 = lockProvider.create(key, {
|
|
1340
|
-
owner: owner1,
|
|
1341
|
-
ttl: TTL,
|
|
1342
|
-
});
|
|
1343
|
-
await lock1.acquire();
|
|
1344
|
-
const owner2 = "c";
|
|
1345
|
-
const lock2 = lockProvider.create(key, {
|
|
1346
|
-
owner: owner2,
|
|
1347
|
-
});
|
|
1348
|
-
let event_ = null;
|
|
1349
|
-
const unsubscribe = await lockProvider.subscribe(LOCK_EVENTS.UNOWNED_REFRESH_TRY, (event) => {
|
|
1350
|
-
event_ = event;
|
|
1351
|
-
});
|
|
1352
|
-
await LazyPromise.delay(TTL.divide(2));
|
|
1353
|
-
const newTTL = TTL.multiply(2);
|
|
1354
|
-
await lock2.refresh(newTTL);
|
|
1355
|
-
await LazyPromise.delay(DELAY_TIME);
|
|
1356
|
-
expect(event_?.key).toBe(key);
|
|
1357
|
-
expect(event_?.owner).toBe(owner2);
|
|
1358
|
-
await unsubscribe();
|
|
1359
|
-
});
|
|
1360
|
-
});
|
|
1361
|
-
describe("method: refreshOrFail", () => {
|
|
1362
|
-
test("Should dispatch RefreshedLockEvent when refreshed by same owner", async () => {
|
|
1363
|
-
const key = "a";
|
|
1364
|
-
const owner = "b";
|
|
1365
|
-
const lock = lockProvider.create(key, {
|
|
1366
|
-
owner,
|
|
1367
|
-
ttl: TTL,
|
|
1368
|
-
});
|
|
1369
|
-
await lock.acquire();
|
|
1370
|
-
let event_ = null;
|
|
1371
|
-
const unsubscribe = await lockProvider.subscribe(LOCK_EVENTS.REFRESHED, (event) => {
|
|
1372
|
-
event_ = event;
|
|
1373
|
-
});
|
|
1374
|
-
await LazyPromise.delay(TTL.divide(2));
|
|
1375
|
-
const newTTL = TTL.multiply(2);
|
|
1376
|
-
await lock.refreshOrFail(newTTL);
|
|
1377
|
-
await LazyPromise.delay(DELAY_TIME);
|
|
1378
|
-
expect(event_?.key).toBe(key);
|
|
1379
|
-
expect(event_?.owner).toBe(owner);
|
|
1380
|
-
expect(event_?.ttl.toMilliseconds()).toBe(newTTL.toMilliseconds());
|
|
1381
|
-
await unsubscribe();
|
|
1382
|
-
});
|
|
1383
|
-
test("Should dispatch UnownedRefreshTryLockEvent when refreshed by different owner", async () => {
|
|
1384
|
-
const key = "a";
|
|
1385
|
-
const owner1 = "b";
|
|
1386
|
-
const lock1 = lockProvider.create(key, {
|
|
1387
|
-
owner: owner1,
|
|
1388
|
-
ttl: TTL,
|
|
1389
|
-
});
|
|
1390
|
-
await lock1.acquire();
|
|
1391
|
-
const owner2 = "c";
|
|
1392
|
-
const lock2 = lockProvider.create(key, {
|
|
1393
|
-
owner: owner2,
|
|
1394
|
-
});
|
|
1395
|
-
let event_ = null;
|
|
1396
|
-
const unsubscribe = await lockProvider.subscribe(LOCK_EVENTS.UNOWNED_REFRESH_TRY, (event) => {
|
|
1397
|
-
event_ = event;
|
|
1398
|
-
});
|
|
1399
|
-
await LazyPromise.delay(TTL.divide(2));
|
|
1400
|
-
const newTTL = TTL.multiply(2);
|
|
1401
|
-
try {
|
|
1402
|
-
await lock2.refreshOrFail(newTTL);
|
|
1403
|
-
await LazyPromise.delay(DELAY_TIME);
|
|
1404
|
-
}
|
|
1405
|
-
catch {
|
|
1406
|
-
/* Empty */
|
|
1407
|
-
}
|
|
1408
|
-
expect(event_?.key).toBe(key);
|
|
1409
|
-
expect(event_?.owner).toBe(owner2);
|
|
1410
|
-
await unsubscribe();
|
|
2785
|
+
}
|
|
2786
|
+
catch {
|
|
2787
|
+
/* EMPTY */
|
|
2788
|
+
}
|
|
2789
|
+
await delay(TimeSpan.fromMilliseconds(10));
|
|
2790
|
+
expect(handlerFn).toHaveBeenCalledTimes(1);
|
|
2791
|
+
expect(handlerFn).toHaveBeenCalledWith({
|
|
2792
|
+
key,
|
|
2793
|
+
owner,
|
|
2794
|
+
});
|
|
2795
|
+
});
|
|
2796
|
+
test("Should dispatch ReleasedLockEvent when key is unexpired and released by same owner", async () => {
|
|
2797
|
+
const key = "a";
|
|
2798
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
2799
|
+
const owner = "b";
|
|
2800
|
+
const lock = lockProvider.create(key, { ttl, owner });
|
|
2801
|
+
await lock.acquire();
|
|
2802
|
+
const handlerFn = vi.fn((_event) => { });
|
|
2803
|
+
await lockProvider.addListener(LOCK_EVENTS.RELEASED, handlerFn);
|
|
2804
|
+
await lock.releaseOrFail();
|
|
2805
|
+
await delay(TimeSpan.fromMilliseconds(10));
|
|
2806
|
+
expect(handlerFn).toHaveBeenCalledTimes(1);
|
|
2807
|
+
expect(handlerFn).toHaveBeenCalledWith({
|
|
2808
|
+
key,
|
|
2809
|
+
owner,
|
|
1411
2810
|
});
|
|
1412
2811
|
});
|
|
1413
2812
|
});
|
|
1414
|
-
describe("
|
|
1415
|
-
|
|
1416
|
-
|
|
1417
|
-
|
|
1418
|
-
|
|
1419
|
-
|
|
1420
|
-
|
|
1421
|
-
|
|
1422
|
-
|
|
1423
|
-
|
|
1424
|
-
|
|
1425
|
-
|
|
1426
|
-
|
|
1427
|
-
|
|
1428
|
-
|
|
1429
|
-
|
|
1430
|
-
|
|
1431
|
-
|
|
1432
|
-
|
|
1433
|
-
|
|
1434
|
-
|
|
1435
|
-
});
|
|
1436
|
-
|
|
1437
|
-
|
|
1438
|
-
|
|
1439
|
-
|
|
1440
|
-
|
|
1441
|
-
|
|
1442
|
-
|
|
1443
|
-
|
|
1444
|
-
|
|
1445
|
-
|
|
1446
|
-
|
|
1447
|
-
|
|
1448
|
-
|
|
1449
|
-
|
|
1450
|
-
|
|
1451
|
-
|
|
1452
|
-
|
|
1453
|
-
|
|
1454
|
-
|
|
1455
|
-
|
|
1456
|
-
|
|
1457
|
-
|
|
1458
|
-
|
|
1459
|
-
|
|
1460
|
-
|
|
1461
|
-
|
|
1462
|
-
|
|
1463
|
-
|
|
1464
|
-
|
|
1465
|
-
|
|
1466
|
-
|
|
1467
|
-
|
|
1468
|
-
|
|
1469
|
-
|
|
1470
|
-
|
|
1471
|
-
|
|
1472
|
-
|
|
1473
|
-
});
|
|
1474
|
-
|
|
1475
|
-
|
|
1476
|
-
|
|
1477
|
-
|
|
1478
|
-
|
|
1479
|
-
|
|
1480
|
-
|
|
1481
|
-
|
|
1482
|
-
|
|
1483
|
-
|
|
1484
|
-
|
|
1485
|
-
|
|
1486
|
-
|
|
1487
|
-
|
|
1488
|
-
|
|
1489
|
-
|
|
1490
|
-
|
|
1491
|
-
|
|
1492
|
-
|
|
1493
|
-
|
|
1494
|
-
|
|
1495
|
-
|
|
1496
|
-
|
|
1497
|
-
|
|
1498
|
-
|
|
1499
|
-
|
|
1500
|
-
|
|
1501
|
-
|
|
1502
|
-
|
|
1503
|
-
|
|
1504
|
-
|
|
1505
|
-
|
|
1506
|
-
|
|
1507
|
-
|
|
1508
|
-
|
|
1509
|
-
|
|
1510
|
-
|
|
1511
|
-
|
|
1512
|
-
|
|
1513
|
-
|
|
1514
|
-
|
|
1515
|
-
|
|
1516
|
-
|
|
1517
|
-
|
|
1518
|
-
|
|
1519
|
-
|
|
1520
|
-
|
|
1521
|
-
|
|
1522
|
-
|
|
1523
|
-
|
|
1524
|
-
|
|
1525
|
-
|
|
1526
|
-
|
|
1527
|
-
|
|
1528
|
-
|
|
1529
|
-
|
|
1530
|
-
|
|
1531
|
-
|
|
1532
|
-
|
|
1533
|
-
|
|
1534
|
-
|
|
1535
|
-
|
|
1536
|
-
|
|
1537
|
-
|
|
1538
|
-
|
|
1539
|
-
|
|
1540
|
-
|
|
1541
|
-
|
|
1542
|
-
|
|
1543
|
-
|
|
1544
|
-
|
|
1545
|
-
|
|
1546
|
-
|
|
1547
|
-
|
|
1548
|
-
|
|
1549
|
-
|
|
1550
|
-
|
|
1551
|
-
|
|
1552
|
-
|
|
1553
|
-
|
|
1554
|
-
|
|
1555
|
-
|
|
1556
|
-
|
|
1557
|
-
|
|
1558
|
-
|
|
1559
|
-
|
|
1560
|
-
|
|
1561
|
-
|
|
1562
|
-
|
|
1563
|
-
|
|
1564
|
-
|
|
1565
|
-
|
|
1566
|
-
|
|
1567
|
-
|
|
1568
|
-
|
|
1569
|
-
|
|
1570
|
-
|
|
1571
|
-
|
|
1572
|
-
|
|
1573
|
-
|
|
1574
|
-
|
|
1575
|
-
|
|
1576
|
-
|
|
1577
|
-
|
|
1578
|
-
|
|
1579
|
-
await
|
|
1580
|
-
|
|
1581
|
-
|
|
1582
|
-
|
|
1583
|
-
|
|
1584
|
-
|
|
1585
|
-
|
|
1586
|
-
|
|
1587
|
-
|
|
1588
|
-
|
|
1589
|
-
|
|
1590
|
-
|
|
1591
|
-
|
|
1592
|
-
|
|
1593
|
-
|
|
1594
|
-
|
|
1595
|
-
|
|
1596
|
-
|
|
1597
|
-
|
|
1598
|
-
|
|
1599
|
-
|
|
1600
|
-
|
|
1601
|
-
|
|
1602
|
-
|
|
1603
|
-
|
|
1604
|
-
|
|
1605
|
-
|
|
1606
|
-
|
|
1607
|
-
}
|
|
1608
|
-
|
|
1609
|
-
|
|
1610
|
-
|
|
1611
|
-
|
|
1612
|
-
|
|
1613
|
-
|
|
1614
|
-
|
|
1615
|
-
|
|
1616
|
-
|
|
1617
|
-
|
|
1618
|
-
|
|
1619
|
-
|
|
1620
|
-
|
|
1621
|
-
|
|
1622
|
-
|
|
1623
|
-
|
|
1624
|
-
|
|
1625
|
-
|
|
1626
|
-
|
|
1627
|
-
|
|
1628
|
-
|
|
1629
|
-
|
|
1630
|
-
|
|
1631
|
-
|
|
1632
|
-
|
|
1633
|
-
|
|
1634
|
-
|
|
1635
|
-
|
|
1636
|
-
|
|
1637
|
-
|
|
1638
|
-
|
|
1639
|
-
|
|
1640
|
-
|
|
1641
|
-
|
|
1642
|
-
|
|
1643
|
-
|
|
1644
|
-
});
|
|
1645
|
-
|
|
1646
|
-
|
|
1647
|
-
|
|
1648
|
-
|
|
1649
|
-
|
|
1650
|
-
|
|
1651
|
-
|
|
1652
|
-
|
|
1653
|
-
|
|
1654
|
-
|
|
1655
|
-
|
|
1656
|
-
|
|
1657
|
-
|
|
1658
|
-
|
|
1659
|
-
|
|
1660
|
-
|
|
1661
|
-
|
|
1662
|
-
|
|
1663
|
-
|
|
1664
|
-
|
|
1665
|
-
|
|
1666
|
-
|
|
1667
|
-
|
|
1668
|
-
|
|
1669
|
-
|
|
1670
|
-
|
|
1671
|
-
|
|
1672
|
-
|
|
1673
|
-
|
|
1674
|
-
|
|
1675
|
-
|
|
1676
|
-
|
|
1677
|
-
|
|
1678
|
-
|
|
1679
|
-
|
|
1680
|
-
|
|
1681
|
-
|
|
1682
|
-
|
|
1683
|
-
|
|
1684
|
-
|
|
1685
|
-
|
|
1686
|
-
|
|
1687
|
-
|
|
1688
|
-
|
|
1689
|
-
|
|
1690
|
-
|
|
1691
|
-
|
|
1692
|
-
|
|
1693
|
-
|
|
1694
|
-
|
|
1695
|
-
|
|
1696
|
-
|
|
1697
|
-
|
|
1698
|
-
|
|
1699
|
-
|
|
1700
|
-
|
|
1701
|
-
|
|
1702
|
-
|
|
1703
|
-
|
|
1704
|
-
|
|
1705
|
-
|
|
1706
|
-
|
|
1707
|
-
|
|
1708
|
-
|
|
1709
|
-
|
|
1710
|
-
|
|
1711
|
-
|
|
1712
|
-
|
|
1713
|
-
|
|
1714
|
-
|
|
1715
|
-
|
|
1716
|
-
|
|
1717
|
-
|
|
1718
|
-
|
|
1719
|
-
|
|
1720
|
-
expect(event_?.key).toBe("a");
|
|
1721
|
-
expect(event_?.owner).toBe(owner);
|
|
1722
|
-
await unsubscribe();
|
|
1723
|
-
});
|
|
1724
|
-
});
|
|
1725
|
-
describe("method: release", () => {
|
|
1726
|
-
test("Should dispatch ReleasedLockEvent when released by same owner", async () => {
|
|
1727
|
-
const key = "a";
|
|
1728
|
-
const owner = "b";
|
|
1729
|
-
const lock = lockProvider.create(key, {
|
|
1730
|
-
owner,
|
|
1731
|
-
});
|
|
1732
|
-
await lock.acquire();
|
|
1733
|
-
let event_ = null;
|
|
1734
|
-
const unsubscribe = await lockProvider.subscribe(LOCK_EVENTS.RELEASED, (event) => {
|
|
1735
|
-
event_ = event;
|
|
1736
|
-
});
|
|
1737
|
-
await lock.release();
|
|
1738
|
-
await LazyPromise.delay(DELAY_TIME);
|
|
1739
|
-
expect(event_?.key).toBe(key);
|
|
1740
|
-
expect(event_?.owner).toBe(owner);
|
|
1741
|
-
await unsubscribe();
|
|
1742
|
-
});
|
|
1743
|
-
test("Should dispatch UnownedReleaseTryLockEvent when released by same owner", async () => {
|
|
1744
|
-
const key = "a";
|
|
1745
|
-
const owner1 = "b";
|
|
1746
|
-
const lock1 = lockProvider.create(key, {
|
|
1747
|
-
owner: owner1,
|
|
1748
|
-
});
|
|
1749
|
-
await lock1.acquire();
|
|
1750
|
-
const owner2 = "c";
|
|
1751
|
-
const lock2 = lockProvider.create(key, {
|
|
1752
|
-
owner: owner2,
|
|
1753
|
-
});
|
|
1754
|
-
let event_ = null;
|
|
1755
|
-
const unsubscribe = await lockProvider.subscribe(LOCK_EVENTS.UNOWNED_RELEASE_TRY, (event) => {
|
|
1756
|
-
event_ = event;
|
|
1757
|
-
});
|
|
1758
|
-
await lock2.release();
|
|
1759
|
-
await LazyPromise.delay(DELAY_TIME);
|
|
1760
|
-
expect(event_?.key).toBe(key);
|
|
1761
|
-
expect(event_?.owner).toBe(owner2);
|
|
1762
|
-
await unsubscribe();
|
|
1763
|
-
});
|
|
1764
|
-
});
|
|
1765
|
-
describe("method: releaseOrFail", () => {
|
|
1766
|
-
test("Should dispatch ReleasedLockEvent when released by same owner", async () => {
|
|
1767
|
-
const key = "a";
|
|
1768
|
-
const owner = "b";
|
|
1769
|
-
const lock = lockProvider.create(key, {
|
|
1770
|
-
owner,
|
|
1771
|
-
});
|
|
1772
|
-
await lock.acquire();
|
|
1773
|
-
let event_ = null;
|
|
1774
|
-
const unsubscribe = await lockProvider.subscribe(LOCK_EVENTS.RELEASED, (event) => {
|
|
1775
|
-
event_ = event;
|
|
1776
|
-
});
|
|
1777
|
-
await lock.releaseOrFail();
|
|
1778
|
-
await LazyPromise.delay(DELAY_TIME);
|
|
1779
|
-
expect(event_?.key).toBe(key);
|
|
1780
|
-
expect(event_?.owner).toBe(owner);
|
|
1781
|
-
await unsubscribe();
|
|
1782
|
-
});
|
|
1783
|
-
test("Should dispatch UnownedReleaseTryLockEvent when released by same owner", async () => {
|
|
1784
|
-
const key = "a";
|
|
1785
|
-
const owner1 = "b";
|
|
1786
|
-
const lock1 = lockProvider.create(key, {
|
|
1787
|
-
owner: owner1,
|
|
1788
|
-
});
|
|
1789
|
-
await lock1.acquire();
|
|
1790
|
-
const owner2 = "c";
|
|
1791
|
-
const lock2 = lockProvider.create(key, {
|
|
1792
|
-
owner: owner2,
|
|
1793
|
-
});
|
|
1794
|
-
let event_ = null;
|
|
1795
|
-
const unsubscribe = await lockProvider.subscribe(LOCK_EVENTS.UNOWNED_RELEASE_TRY, (event) => {
|
|
1796
|
-
event_ = event;
|
|
1797
|
-
});
|
|
1798
|
-
try {
|
|
1799
|
-
await lock2.releaseOrFail();
|
|
1800
|
-
await LazyPromise.delay(DELAY_TIME);
|
|
1801
|
-
}
|
|
1802
|
-
catch {
|
|
1803
|
-
/* Empty */
|
|
1804
|
-
}
|
|
1805
|
-
expect(event_?.key).toBe(key);
|
|
1806
|
-
expect(event_?.owner).toBe(owner2);
|
|
1807
|
-
await unsubscribe();
|
|
1808
|
-
});
|
|
1809
|
-
});
|
|
1810
|
-
describe("method: forceRelease", () => {
|
|
1811
|
-
test("Should dispatch ForceReleasedLockEvent when lock forcefully released", async () => {
|
|
1812
|
-
const key = "a";
|
|
1813
|
-
const owner1 = "b";
|
|
1814
|
-
const lock1 = lockProvider.create(key, {
|
|
1815
|
-
owner: owner1,
|
|
1816
|
-
});
|
|
1817
|
-
await lock1.acquire();
|
|
1818
|
-
const owner2 = "c";
|
|
1819
|
-
const lock2 = lockProvider.create(key, {
|
|
1820
|
-
owner: owner2,
|
|
1821
|
-
});
|
|
1822
|
-
let event_ = null;
|
|
1823
|
-
const unsubscribe = await lockProvider.subscribe(LOCK_EVENTS.FORCE_RELEASED, (event) => {
|
|
1824
|
-
event_ = event;
|
|
1825
|
-
});
|
|
1826
|
-
await lock2.forceRelease();
|
|
1827
|
-
await LazyPromise.delay(DELAY_TIME);
|
|
1828
|
-
expect(event_?.key).toBe(key);
|
|
1829
|
-
await unsubscribe();
|
|
1830
|
-
});
|
|
1831
|
-
});
|
|
1832
|
-
describe("method: refresh", () => {
|
|
1833
|
-
test("Should dispatch RefreshedLockEvent when refreshed by same owner", async () => {
|
|
1834
|
-
const key = "a";
|
|
1835
|
-
const owner = "b";
|
|
1836
|
-
const lock = lockProvider.create(key, {
|
|
1837
|
-
owner,
|
|
1838
|
-
ttl: TTL,
|
|
1839
|
-
});
|
|
1840
|
-
await lock.acquire();
|
|
1841
|
-
let event_ = null;
|
|
1842
|
-
const unsubscribe = await lockProvider.subscribe(LOCK_EVENTS.REFRESHED, (event) => {
|
|
1843
|
-
event_ = event;
|
|
1844
|
-
});
|
|
1845
|
-
await LazyPromise.delay(TTL.divide(2));
|
|
1846
|
-
const newTTL = TTL.multiply(2);
|
|
1847
|
-
await lock.refresh(newTTL);
|
|
1848
|
-
await LazyPromise.delay(DELAY_TIME);
|
|
1849
|
-
expect(event_?.key).toBe(key);
|
|
1850
|
-
expect(event_?.owner).toBe(owner);
|
|
1851
|
-
expect(event_?.ttl.toMilliseconds()).toBe(newTTL.toMilliseconds());
|
|
1852
|
-
await unsubscribe();
|
|
1853
|
-
});
|
|
1854
|
-
test("Should dispatch UnownedRefreshTryLockEvent when refreshed by different owner", async () => {
|
|
1855
|
-
const key = "a";
|
|
1856
|
-
const owner1 = "b";
|
|
1857
|
-
const lock1 = lockProvider.create(key, {
|
|
1858
|
-
owner: owner1,
|
|
1859
|
-
ttl: TTL,
|
|
1860
|
-
});
|
|
1861
|
-
await lock1.acquire();
|
|
1862
|
-
const owner2 = "c";
|
|
1863
|
-
const lock2 = lockProvider.create(key, {
|
|
1864
|
-
owner: owner2,
|
|
1865
|
-
});
|
|
1866
|
-
let event_ = null;
|
|
1867
|
-
const unsubscribe = await lockProvider.subscribe(LOCK_EVENTS.UNOWNED_REFRESH_TRY, (event) => {
|
|
1868
|
-
event_ = event;
|
|
1869
|
-
});
|
|
1870
|
-
await LazyPromise.delay(TTL.divide(2));
|
|
1871
|
-
const newTTL = TTL.multiply(2);
|
|
1872
|
-
await lock2.refresh(newTTL);
|
|
1873
|
-
await LazyPromise.delay(DELAY_TIME);
|
|
1874
|
-
expect(event_?.key).toBe(key);
|
|
1875
|
-
expect(event_?.owner).toBe(owner2);
|
|
1876
|
-
await unsubscribe();
|
|
1877
|
-
});
|
|
1878
|
-
});
|
|
1879
|
-
describe("method: refreshOrFail", () => {
|
|
1880
|
-
test("Should dispatch RefreshedLockEvent when refreshed by same owner", async () => {
|
|
1881
|
-
const key = "a";
|
|
1882
|
-
const owner = "b";
|
|
1883
|
-
const lock = lockProvider.create(key, {
|
|
1884
|
-
owner,
|
|
1885
|
-
ttl: TTL,
|
|
1886
|
-
});
|
|
1887
|
-
await lock.acquire();
|
|
1888
|
-
let event_ = null;
|
|
1889
|
-
const unsubscribe = await lockProvider.subscribe(LOCK_EVENTS.REFRESHED, (event) => {
|
|
1890
|
-
event_ = event;
|
|
1891
|
-
});
|
|
1892
|
-
await LazyPromise.delay(TTL.divide(2));
|
|
1893
|
-
const newTTL = TTL.multiply(2);
|
|
1894
|
-
await lock.refreshOrFail(newTTL);
|
|
1895
|
-
await LazyPromise.delay(DELAY_TIME);
|
|
1896
|
-
expect(event_?.key).toBe(key);
|
|
1897
|
-
expect(event_?.owner).toBe(owner);
|
|
1898
|
-
expect(event_?.ttl.toMilliseconds()).toBe(newTTL.toMilliseconds());
|
|
1899
|
-
await unsubscribe();
|
|
1900
|
-
});
|
|
1901
|
-
test("Should dispatch UnownedRefreshTryLockEvent when refreshed by different owner", async () => {
|
|
1902
|
-
const key = "a";
|
|
1903
|
-
const owner1 = "b";
|
|
1904
|
-
const lock1 = lockProvider.create(key, {
|
|
1905
|
-
owner: owner1,
|
|
1906
|
-
ttl: TTL,
|
|
1907
|
-
});
|
|
1908
|
-
await lock1.acquire();
|
|
1909
|
-
const owner2 = "c";
|
|
1910
|
-
const lock2 = lockProvider.create(key, {
|
|
1911
|
-
owner: owner2,
|
|
1912
|
-
});
|
|
1913
|
-
let event_ = null;
|
|
1914
|
-
const unsubscribe = await lockProvider.subscribe(LOCK_EVENTS.UNOWNED_REFRESH_TRY, (event) => {
|
|
1915
|
-
event_ = event;
|
|
1916
|
-
});
|
|
1917
|
-
await LazyPromise.delay(TTL.divide(2));
|
|
1918
|
-
const newTTL = TTL.multiply(2);
|
|
1919
|
-
try {
|
|
1920
|
-
await lock2.refreshOrFail(newTTL);
|
|
1921
|
-
await LazyPromise.delay(DELAY_TIME);
|
|
1922
|
-
}
|
|
1923
|
-
catch {
|
|
1924
|
-
/* Empty */
|
|
1925
|
-
}
|
|
1926
|
-
expect(event_?.key).toBe(key);
|
|
1927
|
-
expect(event_?.owner).toBe(owner2);
|
|
1928
|
-
await unsubscribe();
|
|
2813
|
+
describe("method: forceRelease", () => {
|
|
2814
|
+
test("Should not dispatch ForceReleasedLockEvent when key doesnt exists", async () => {
|
|
2815
|
+
const key = "a";
|
|
2816
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
2817
|
+
const lock = lockProvider.create(key, { ttl });
|
|
2818
|
+
const handlerFn = vi.fn((_event) => { });
|
|
2819
|
+
await lockProvider.addListener(LOCK_EVENTS.FORCE_RELEASED, handlerFn);
|
|
2820
|
+
await lock.forceRelease();
|
|
2821
|
+
expect(handlerFn).toHaveBeenCalledTimes(0);
|
|
2822
|
+
});
|
|
2823
|
+
test("Should dispatch ForceReleasedLockEvent when key is uenxpired", async () => {
|
|
2824
|
+
const key = "a";
|
|
2825
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
2826
|
+
const lock = lockProvider.create(key, { ttl });
|
|
2827
|
+
await lock.acquire();
|
|
2828
|
+
const handlerFn = vi.fn((_event) => { });
|
|
2829
|
+
await lockProvider.addListener(LOCK_EVENTS.FORCE_RELEASED, handlerFn);
|
|
2830
|
+
await lock.forceRelease();
|
|
2831
|
+
expect(handlerFn).toHaveBeenCalledTimes(1);
|
|
2832
|
+
expect(handlerFn).toHaveBeenCalledWith({
|
|
2833
|
+
key,
|
|
2834
|
+
});
|
|
2835
|
+
});
|
|
2836
|
+
test("Should dispatch ForceReleasedLockEvent when key is unexpireable", async () => {
|
|
2837
|
+
const key = "a";
|
|
2838
|
+
const ttl = null;
|
|
2839
|
+
const lock = lockProvider.create(key, { ttl });
|
|
2840
|
+
await lock.acquire();
|
|
2841
|
+
const handlerFn = vi.fn((_event) => { });
|
|
2842
|
+
await lockProvider.addListener(LOCK_EVENTS.FORCE_RELEASED, handlerFn);
|
|
2843
|
+
await lock.forceRelease();
|
|
2844
|
+
expect(handlerFn).toHaveBeenCalledTimes(1);
|
|
2845
|
+
expect(handlerFn).toHaveBeenCalledWith({
|
|
2846
|
+
key,
|
|
2847
|
+
});
|
|
2848
|
+
});
|
|
2849
|
+
});
|
|
2850
|
+
describe("method: refresh", () => {
|
|
2851
|
+
test("Should dispatch UnownedRefreshTryLockEvent when key doesnt exists", async () => {
|
|
2852
|
+
const key = "a";
|
|
2853
|
+
const newTtl = TimeSpan.fromMinutes(1);
|
|
2854
|
+
const handlerFn = vi.fn((_event) => { });
|
|
2855
|
+
await lockProvider.addListener(LOCK_EVENTS.UNOWNED_REFRESH_TRY, handlerFn);
|
|
2856
|
+
const owner = "b";
|
|
2857
|
+
await lockProvider.create(key, { owner }).refresh(newTtl);
|
|
2858
|
+
expect(handlerFn).toHaveBeenCalledTimes(1);
|
|
2859
|
+
expect(handlerFn).toHaveBeenCalledWith({
|
|
2860
|
+
key,
|
|
2861
|
+
owner,
|
|
2862
|
+
});
|
|
2863
|
+
});
|
|
2864
|
+
test("Should dispatch UnownedRefreshTryLockEvent when key is unexpireable and refreshed by different owner", async () => {
|
|
2865
|
+
const key = "a";
|
|
2866
|
+
const ttl = null;
|
|
2867
|
+
const lock1 = lockProvider.create(key, { ttl });
|
|
2868
|
+
await lock1.acquire();
|
|
2869
|
+
const newTtl = TimeSpan.fromMinutes(1);
|
|
2870
|
+
const owner = "b";
|
|
2871
|
+
const lock2 = lockProvider.create(key, { ttl, owner });
|
|
2872
|
+
const handlerFn = vi.fn((_event) => { });
|
|
2873
|
+
await lockProvider.addListener(LOCK_EVENTS.UNOWNED_REFRESH_TRY, handlerFn);
|
|
2874
|
+
await lock2.refresh(newTtl);
|
|
2875
|
+
expect(handlerFn).toHaveBeenCalledTimes(1);
|
|
2876
|
+
expect(handlerFn).toHaveBeenCalledWith({
|
|
2877
|
+
key,
|
|
2878
|
+
owner,
|
|
2879
|
+
});
|
|
2880
|
+
});
|
|
2881
|
+
test("Should dispatch UnownedRefreshTryLockEvent when key is unexpired and refreshed by different owner", async () => {
|
|
2882
|
+
const key = "a";
|
|
2883
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
2884
|
+
const lock1 = lockProvider.create(key, { ttl });
|
|
2885
|
+
await lock1.acquire();
|
|
2886
|
+
const newTtl = TimeSpan.fromMinutes(1);
|
|
2887
|
+
const owner = "b";
|
|
2888
|
+
const lock2 = lockProvider.create(key, { ttl, owner });
|
|
2889
|
+
const handlerFn = vi.fn((_event) => { });
|
|
2890
|
+
await lockProvider.addListener(LOCK_EVENTS.UNOWNED_REFRESH_TRY, handlerFn);
|
|
2891
|
+
await lock2.refresh(newTtl);
|
|
2892
|
+
expect(handlerFn).toHaveBeenCalledTimes(1);
|
|
2893
|
+
expect(handlerFn).toHaveBeenCalledWith({
|
|
2894
|
+
key,
|
|
2895
|
+
owner,
|
|
2896
|
+
});
|
|
2897
|
+
});
|
|
2898
|
+
test("Should dispatch UnownedRefreshTryLockEvent when key is expired and refreshed by different owner", async () => {
|
|
2899
|
+
const key = "a";
|
|
2900
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
2901
|
+
const lock1 = lockProvider.create(key, { ttl });
|
|
2902
|
+
await lock1.acquire();
|
|
2903
|
+
await delay(ttl);
|
|
2904
|
+
const newTtl = TimeSpan.fromMinutes(1);
|
|
2905
|
+
const owner = "b";
|
|
2906
|
+
const lock2 = lockProvider.create(key, { ttl, owner });
|
|
2907
|
+
const handlerFn = vi.fn((_event) => { });
|
|
2908
|
+
await lockProvider.addListener(LOCK_EVENTS.UNOWNED_REFRESH_TRY, handlerFn);
|
|
2909
|
+
await lock2.refresh(newTtl);
|
|
2910
|
+
expect(handlerFn).toHaveBeenCalledTimes(1);
|
|
2911
|
+
expect(handlerFn).toHaveBeenCalledWith({
|
|
2912
|
+
key,
|
|
2913
|
+
owner,
|
|
2914
|
+
});
|
|
2915
|
+
});
|
|
2916
|
+
test("Should dispatch UnownedRefreshTryLockEvent when key is expired and refreshed by same owner", async () => {
|
|
2917
|
+
const key = "a";
|
|
2918
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
2919
|
+
const owner = "b";
|
|
2920
|
+
const lock = lockProvider.create(key, {
|
|
2921
|
+
ttl,
|
|
2922
|
+
owner,
|
|
2923
|
+
});
|
|
2924
|
+
await lock.acquire();
|
|
2925
|
+
await delay(ttl);
|
|
2926
|
+
const newTtl = TimeSpan.fromMinutes(1);
|
|
2927
|
+
const handlerFn = vi.fn((_event) => { });
|
|
2928
|
+
await lockProvider.addListener(LOCK_EVENTS.UNOWNED_REFRESH_TRY, handlerFn);
|
|
2929
|
+
await lock.refresh(newTtl);
|
|
2930
|
+
expect(handlerFn).toHaveBeenCalledTimes(1);
|
|
2931
|
+
expect(handlerFn).toHaveBeenCalledWith({
|
|
2932
|
+
key,
|
|
2933
|
+
owner,
|
|
2934
|
+
});
|
|
2935
|
+
});
|
|
2936
|
+
test("Should dispatch UnexpireableKeyRefreshTryLockEvent when key is unexpireable and refreshed by same owner", async () => {
|
|
2937
|
+
const key = "a";
|
|
2938
|
+
const ttl = null;
|
|
2939
|
+
const owner = "b";
|
|
2940
|
+
const lock = lockProvider.create(key, { ttl, owner });
|
|
2941
|
+
await lock.acquire();
|
|
2942
|
+
const newTtl = TimeSpan.fromMinutes(1);
|
|
2943
|
+
const handlerFn = vi.fn((_event) => { });
|
|
2944
|
+
await lockProvider.addListener(LOCK_EVENTS.UNEXPIREABLE_KEY_REFRESH_TRY, handlerFn);
|
|
2945
|
+
await lock.refresh(newTtl);
|
|
2946
|
+
expect(handlerFn).toHaveBeenCalledTimes(1);
|
|
2947
|
+
expect(handlerFn).toHaveBeenCalledWith({
|
|
2948
|
+
key,
|
|
2949
|
+
owner,
|
|
2950
|
+
});
|
|
2951
|
+
});
|
|
2952
|
+
test("Should dispatch RefreshedLockEvent when key is unexpired and refreshed by same owner", async () => {
|
|
2953
|
+
const key = "a";
|
|
2954
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
2955
|
+
const owner = "b";
|
|
2956
|
+
const lock = lockProvider.create(key, { ttl, owner });
|
|
2957
|
+
await lock.acquire();
|
|
2958
|
+
const newTtl = TimeSpan.fromMinutes(1);
|
|
2959
|
+
const handlerFn = vi.fn((_event) => { });
|
|
2960
|
+
await lockProvider.addListener(LOCK_EVENTS.REFRESHED, handlerFn);
|
|
2961
|
+
await lock.refresh(newTtl);
|
|
2962
|
+
expect(handlerFn).toHaveBeenCalledTimes(1);
|
|
2963
|
+
expect(handlerFn).toHaveBeenCalledWith({
|
|
2964
|
+
key,
|
|
2965
|
+
owner,
|
|
2966
|
+
ttl: newTtl,
|
|
2967
|
+
});
|
|
2968
|
+
});
|
|
2969
|
+
});
|
|
2970
|
+
describe("method: refreshOrFail", () => {
|
|
2971
|
+
test("Should dispatch UnownedRefreshTryLockEvent when key doesnt exists", async () => {
|
|
2972
|
+
const key = "a";
|
|
2973
|
+
const newTtl = TimeSpan.fromMinutes(1);
|
|
2974
|
+
const handlerFn = vi.fn((_event) => { });
|
|
2975
|
+
await lockProvider.addListener(LOCK_EVENTS.UNOWNED_REFRESH_TRY, handlerFn);
|
|
2976
|
+
const owner = "b";
|
|
2977
|
+
try {
|
|
2978
|
+
await lockProvider
|
|
2979
|
+
.create(key, { owner })
|
|
2980
|
+
.refreshOrFail(newTtl);
|
|
2981
|
+
}
|
|
2982
|
+
catch {
|
|
2983
|
+
/* EMPTY */
|
|
2984
|
+
}
|
|
2985
|
+
expect(handlerFn).toHaveBeenCalledTimes(1);
|
|
2986
|
+
expect(handlerFn).toHaveBeenCalledWith({
|
|
2987
|
+
key,
|
|
2988
|
+
owner,
|
|
2989
|
+
});
|
|
2990
|
+
});
|
|
2991
|
+
test("Should dispatch UnownedRefreshTryLockEvent when key is unexpireable and refreshed by different owner", async () => {
|
|
2992
|
+
const key = "a";
|
|
2993
|
+
const ttl = null;
|
|
2994
|
+
const lock1 = lockProvider.create(key, { ttl });
|
|
2995
|
+
await lock1.acquire();
|
|
2996
|
+
const newTtl = TimeSpan.fromMinutes(1);
|
|
2997
|
+
const owner = "b";
|
|
2998
|
+
const lock2 = lockProvider.create(key, { ttl, owner });
|
|
2999
|
+
const handlerFn = vi.fn((_event) => { });
|
|
3000
|
+
await lockProvider.addListener(LOCK_EVENTS.UNOWNED_REFRESH_TRY, handlerFn);
|
|
3001
|
+
try {
|
|
3002
|
+
await lock2.refreshOrFail(newTtl);
|
|
3003
|
+
}
|
|
3004
|
+
catch {
|
|
3005
|
+
/* EMPTY */
|
|
3006
|
+
}
|
|
3007
|
+
expect(handlerFn).toHaveBeenCalledTimes(1);
|
|
3008
|
+
expect(handlerFn).toHaveBeenCalledWith({
|
|
3009
|
+
key,
|
|
3010
|
+
owner,
|
|
3011
|
+
});
|
|
3012
|
+
});
|
|
3013
|
+
test("Should dispatch UnownedRefreshTryLockEvent when key is unexpired and refreshed by different owner", async () => {
|
|
3014
|
+
const key = "a";
|
|
3015
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
3016
|
+
const lock1 = lockProvider.create(key, { ttl });
|
|
3017
|
+
await lock1.acquire();
|
|
3018
|
+
const newTtl = TimeSpan.fromMinutes(1);
|
|
3019
|
+
const owner = "b";
|
|
3020
|
+
const lock2 = lockProvider.create(key, { ttl, owner });
|
|
3021
|
+
const handlerFn = vi.fn((_event) => { });
|
|
3022
|
+
await lockProvider.addListener(LOCK_EVENTS.UNOWNED_REFRESH_TRY, handlerFn);
|
|
3023
|
+
try {
|
|
3024
|
+
await lock2.refreshOrFail(newTtl);
|
|
3025
|
+
}
|
|
3026
|
+
catch {
|
|
3027
|
+
/* EMPTY */
|
|
3028
|
+
}
|
|
3029
|
+
expect(handlerFn).toHaveBeenCalledTimes(1);
|
|
3030
|
+
expect(handlerFn).toHaveBeenCalledWith({
|
|
3031
|
+
key,
|
|
3032
|
+
owner,
|
|
3033
|
+
});
|
|
3034
|
+
});
|
|
3035
|
+
test("Should dispatch UnownedRefreshTryLockEvent when key is expired and refreshed by different owner", async () => {
|
|
3036
|
+
const key = "a";
|
|
3037
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
3038
|
+
const lock1 = lockProvider.create(key, { ttl });
|
|
3039
|
+
await lock1.acquire();
|
|
3040
|
+
await delay(ttl);
|
|
3041
|
+
const newTtl = TimeSpan.fromMinutes(1);
|
|
3042
|
+
const owner = "b";
|
|
3043
|
+
const lock2 = lockProvider.create(key, { ttl, owner });
|
|
3044
|
+
const handlerFn = vi.fn((_event) => { });
|
|
3045
|
+
await lockProvider.addListener(LOCK_EVENTS.UNOWNED_REFRESH_TRY, handlerFn);
|
|
3046
|
+
try {
|
|
3047
|
+
await lock2.refreshOrFail(newTtl);
|
|
3048
|
+
}
|
|
3049
|
+
catch {
|
|
3050
|
+
/* EMPTY */
|
|
3051
|
+
}
|
|
3052
|
+
expect(handlerFn).toHaveBeenCalledTimes(1);
|
|
3053
|
+
expect(handlerFn).toHaveBeenCalledWith({
|
|
3054
|
+
key,
|
|
3055
|
+
owner,
|
|
3056
|
+
});
|
|
3057
|
+
});
|
|
3058
|
+
test("Should dispatch UnownedRefreshTryLockEvent when key is expired and refreshed by same owner", async () => {
|
|
3059
|
+
const key = "a";
|
|
3060
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
3061
|
+
const owner = "b";
|
|
3062
|
+
const lock = lockProvider.create(key, {
|
|
3063
|
+
ttl,
|
|
3064
|
+
owner,
|
|
3065
|
+
});
|
|
3066
|
+
await lock.acquire();
|
|
3067
|
+
await delay(ttl);
|
|
3068
|
+
const newTtl = TimeSpan.fromMinutes(1);
|
|
3069
|
+
const handlerFn = vi.fn((_event) => { });
|
|
3070
|
+
await lockProvider.addListener(LOCK_EVENTS.UNOWNED_REFRESH_TRY, handlerFn);
|
|
3071
|
+
try {
|
|
3072
|
+
await lock.refreshOrFail(newTtl);
|
|
3073
|
+
}
|
|
3074
|
+
catch {
|
|
3075
|
+
/* EMPTY */
|
|
3076
|
+
}
|
|
3077
|
+
expect(handlerFn).toHaveBeenCalledTimes(1);
|
|
3078
|
+
expect(handlerFn).toHaveBeenCalledWith({
|
|
3079
|
+
key,
|
|
3080
|
+
owner,
|
|
3081
|
+
});
|
|
3082
|
+
});
|
|
3083
|
+
test("Should dispatch UnexpireableKeyRefreshTryLockEvent when key is unexpireable and refreshed by same owner", async () => {
|
|
3084
|
+
const key = "a";
|
|
3085
|
+
const ttl = null;
|
|
3086
|
+
const owner = "b";
|
|
3087
|
+
const lock = lockProvider.create(key, { ttl, owner });
|
|
3088
|
+
await lock.acquire();
|
|
3089
|
+
const newTtl = TimeSpan.fromMinutes(1);
|
|
3090
|
+
const handlerFn = vi.fn((_event) => { });
|
|
3091
|
+
await lockProvider.addListener(LOCK_EVENTS.UNEXPIREABLE_KEY_REFRESH_TRY, handlerFn);
|
|
3092
|
+
try {
|
|
3093
|
+
await lock.refreshOrFail(newTtl);
|
|
3094
|
+
}
|
|
3095
|
+
catch {
|
|
3096
|
+
/* EMPTY */
|
|
3097
|
+
}
|
|
3098
|
+
expect(handlerFn).toHaveBeenCalledTimes(1);
|
|
3099
|
+
expect(handlerFn).toHaveBeenCalledWith({
|
|
3100
|
+
key,
|
|
3101
|
+
owner,
|
|
3102
|
+
});
|
|
3103
|
+
});
|
|
3104
|
+
test("Should dispatch RefreshedLockEvent when key is unexpired and refreshed by same owner", async () => {
|
|
3105
|
+
const key = "a";
|
|
3106
|
+
const ttl = TimeSpan.fromMilliseconds(50);
|
|
3107
|
+
const owner = "b";
|
|
3108
|
+
const lock = lockProvider.create(key, { ttl, owner });
|
|
3109
|
+
await lock.acquire();
|
|
3110
|
+
const newTtl = TimeSpan.fromMinutes(1);
|
|
3111
|
+
const handlerFn = vi.fn((_event) => { });
|
|
3112
|
+
await lockProvider.addListener(LOCK_EVENTS.REFRESHED, handlerFn);
|
|
3113
|
+
await lock.refreshOrFail(newTtl);
|
|
3114
|
+
expect(handlerFn).toHaveBeenCalledTimes(1);
|
|
3115
|
+
expect(handlerFn).toHaveBeenCalledWith({
|
|
3116
|
+
key,
|
|
3117
|
+
owner,
|
|
3118
|
+
ttl: newTtl,
|
|
1929
3119
|
});
|
|
1930
3120
|
});
|
|
1931
3121
|
});
|
|
@@ -1954,17 +3144,17 @@ export function lockProviderTestSuite(settings) {
|
|
|
1954
3144
|
test("Should preserve ttl", async () => {
|
|
1955
3145
|
const key = "a";
|
|
1956
3146
|
const owner = "b";
|
|
1957
|
-
const ttl =
|
|
3147
|
+
const ttl = TimeSpan.fromMilliseconds(50).multiply(2);
|
|
1958
3148
|
const lock = lockProvider.create(key, {
|
|
1959
3149
|
owner,
|
|
1960
3150
|
ttl,
|
|
1961
3151
|
});
|
|
1962
3152
|
await lock.acquire();
|
|
1963
3153
|
const deserializedLock = serde.deserialize(serde.serialize(lock));
|
|
1964
|
-
const delayTime =
|
|
1965
|
-
await
|
|
3154
|
+
const delayTime = TimeSpan.fromMilliseconds(50);
|
|
3155
|
+
await delay(delayTime);
|
|
1966
3156
|
expect(await deserializedLock.isLocked()).toBe(true);
|
|
1967
|
-
await
|
|
3157
|
+
await delay(delayTime);
|
|
1968
3158
|
expect(await deserializedLock.isLocked()).toBe(false);
|
|
1969
3159
|
});
|
|
1970
3160
|
});
|