@servicetitan/web-components 30.0.0 → 30.1.1
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/contexts/mfe-data-context.d.ts +8 -4
- package/dist/contexts/mfe-data-context.d.ts.map +1 -1
- package/dist/contexts/mfe-data-context.js +1 -1
- package/dist/contexts/mfe-data-context.js.map +1 -1
- package/dist/event-bus.d.ts +53 -15
- package/dist/event-bus.d.ts.map +1 -1
- package/dist/event-bus.js +46 -17
- package/dist/event-bus.js.map +1 -1
- package/dist/index.d.ts +1 -0
- package/dist/index.d.ts.map +1 -1
- package/dist/loader.d.ts +1 -1
- package/dist/loader.d.ts.map +1 -1
- package/dist/loader.js +5 -2
- package/dist/loader.js.map +1 -1
- package/dist/types.d.ts +5 -2
- package/dist/types.d.ts.map +1 -1
- package/package.json +14 -14
- package/src/__tests__/event-bus-types.test.ts +619 -0
- package/src/__tests__/event-bus.test.ts +5 -18
- package/src/contexts/mfe-data-context.ts +8 -5
- package/src/event-bus.ts +113 -31
- package/src/index.ts +2 -0
- package/src/loader.tsx +6 -1
- package/src/types.ts +11 -2
|
@@ -0,0 +1,619 @@
|
|
|
1
|
+
import { symbolToken } from '@servicetitan/react-ioc';
|
|
2
|
+
import { EventBus } from '../event-bus';
|
|
3
|
+
|
|
4
|
+
jest.mock('../event-bus', () => {
|
|
5
|
+
return {
|
|
6
|
+
EventBus: jest.fn().mockImplementation(() => {
|
|
7
|
+
return {
|
|
8
|
+
job: {
|
|
9
|
+
emit: jest.fn(),
|
|
10
|
+
on: jest.fn(),
|
|
11
|
+
off: jest.fn(),
|
|
12
|
+
},
|
|
13
|
+
emit: jest.fn(),
|
|
14
|
+
on: jest.fn(),
|
|
15
|
+
off: jest.fn(),
|
|
16
|
+
};
|
|
17
|
+
}),
|
|
18
|
+
};
|
|
19
|
+
});
|
|
20
|
+
|
|
21
|
+
describe(`[web-components] ${EventBus.name}`, () => {
|
|
22
|
+
describe('type definitions', () => {
|
|
23
|
+
interface InterfaceDataType {
|
|
24
|
+
value: string;
|
|
25
|
+
}
|
|
26
|
+
|
|
27
|
+
describe('EventBus<T>', () => {
|
|
28
|
+
test('rejects invalid data type', () => {
|
|
29
|
+
// @ts-expect-error Types of property 'foo' are incompatible.
|
|
30
|
+
eventBus = EventBus<{ foo: () => void }>;
|
|
31
|
+
});
|
|
32
|
+
});
|
|
33
|
+
|
|
34
|
+
describe('when eventBus is not typed', () => {
|
|
35
|
+
const eventBus = new EventBus();
|
|
36
|
+
|
|
37
|
+
describe('emit', () => {
|
|
38
|
+
test('accepts valid event with valid data', () => {
|
|
39
|
+
eventBus.emit('foo', '');
|
|
40
|
+
eventBus.emit('foo', 123);
|
|
41
|
+
eventBus.emit('foo', true);
|
|
42
|
+
eventBus.emit('bar', { value: 1 });
|
|
43
|
+
eventBus.emit('foo', ['']);
|
|
44
|
+
eventBus.emit('foo', [123]);
|
|
45
|
+
eventBus.emit('foo', [true]);
|
|
46
|
+
eventBus.emit('bar', [{ value: 1 }]);
|
|
47
|
+
eventBus.emit('bar', [{ value: [1] }]);
|
|
48
|
+
eventBus.emit(123, '');
|
|
49
|
+
eventBus.emit(Symbol(), '');
|
|
50
|
+
});
|
|
51
|
+
|
|
52
|
+
test('accepts event with no data', () => {
|
|
53
|
+
eventBus.emit('foo');
|
|
54
|
+
});
|
|
55
|
+
|
|
56
|
+
test('accepts data declared as interface', () => {
|
|
57
|
+
const data: InterfaceDataType = { value: '' };
|
|
58
|
+
eventBus.emit('foo', data);
|
|
59
|
+
});
|
|
60
|
+
|
|
61
|
+
test('rejects invalid event', () => {
|
|
62
|
+
// @ts-expect-error Argument of type '() => void' is not assignable to parameter of type 'string | number | symbol | SymbolToken<any>'.
|
|
63
|
+
eventBus.emit(() => {}, '');
|
|
64
|
+
|
|
65
|
+
// @ts-expect-error Argument of type 'Date' is not assignable to parameter of type 'string | number | symbol | SymbolToken<any>'.
|
|
66
|
+
eventBus.emit(new Date(), '');
|
|
67
|
+
|
|
68
|
+
// @ts-expect-error Argument of type 'boolean' is not assignable to parameter of type 'string | number | symbol | SymbolToken<any>'.
|
|
69
|
+
eventBus.emit(true, '');
|
|
70
|
+
});
|
|
71
|
+
|
|
72
|
+
test('rejects invalid data', () => {
|
|
73
|
+
/*
|
|
74
|
+
* Note: This case isn't caught
|
|
75
|
+
* @ts-expect-error Argument of type '() => void' is not assignable to parameter of type 'JSON | JSONPrimitive'
|
|
76
|
+
* eventBus.emit('foo', () => {});
|
|
77
|
+
*/
|
|
78
|
+
|
|
79
|
+
// @ts-expect-error Type '() => void' is not assignable to type 'never'.
|
|
80
|
+
eventBus.emit('foo', { fn: () => {} });
|
|
81
|
+
|
|
82
|
+
// @ts-expect-error Type 'Date' is not assignable to type 'never'.
|
|
83
|
+
eventBus.emit('foo', { date: new Date() });
|
|
84
|
+
|
|
85
|
+
// @ts-expect-error Type 'Map<string, any>' is not assignable to type 'never'.
|
|
86
|
+
eventBus.emit('foo', { map: new Map<string, any>() });
|
|
87
|
+
|
|
88
|
+
// @ts-expect-error Type 'Set<string>' is not assignable to type 'never'.
|
|
89
|
+
eventBus.emit('foo', { set: new Set<string>() });
|
|
90
|
+
|
|
91
|
+
// @ts-expect-error Type 'symbol' is not assignable to type 'never'.
|
|
92
|
+
eventBus.emit('foo', { symbol: Symbol() });
|
|
93
|
+
});
|
|
94
|
+
});
|
|
95
|
+
|
|
96
|
+
describe('on', () => {
|
|
97
|
+
test('accepts valid event with any handler', () => {
|
|
98
|
+
eventBus.on('foo', () => {});
|
|
99
|
+
eventBus.on('bar', (_value: string) => {});
|
|
100
|
+
eventBus.on('baz', ({ value: _value }: { value: Date }) => {});
|
|
101
|
+
eventBus.on(Symbol(), () => {});
|
|
102
|
+
eventBus.on(123, () => {});
|
|
103
|
+
});
|
|
104
|
+
|
|
105
|
+
test('rejects invalid event', () => {
|
|
106
|
+
// @ts-expect-error Argument of type 'Date' is not assignable to parameter of type 'JSON | JSONPrimitive'.
|
|
107
|
+
eventBus.on(new Date(), () => {});
|
|
108
|
+
});
|
|
109
|
+
});
|
|
110
|
+
|
|
111
|
+
describe('off', () => {
|
|
112
|
+
test('accepts valid event with any handler', () => {
|
|
113
|
+
eventBus.off('foo', () => {});
|
|
114
|
+
eventBus.off('bar', (_value: string) => {});
|
|
115
|
+
eventBus.off('baz', ({ value: _value }: { value: Date }) => {});
|
|
116
|
+
eventBus.off(Symbol(), () => {});
|
|
117
|
+
eventBus.off(123, () => {});
|
|
118
|
+
});
|
|
119
|
+
|
|
120
|
+
test('rejects invalid event', () => {
|
|
121
|
+
// @ts-expect-error Argument of type 'Date' is not assignable to parameter of type 'JSON | JSONPrimitive'.
|
|
122
|
+
eventBus.off(new Date(), () => {});
|
|
123
|
+
});
|
|
124
|
+
});
|
|
125
|
+
|
|
126
|
+
describe('job.emit', () => {
|
|
127
|
+
test('accepts valid event', () => {
|
|
128
|
+
eventBus.job.emit('foo');
|
|
129
|
+
});
|
|
130
|
+
|
|
131
|
+
test('rejects invalid event', () => {
|
|
132
|
+
// @ts-expect-error Argument of type 'Date' is not assignable to parameter of type 'JSON | JSONPrimitive'.
|
|
133
|
+
eventBus.job.emit(new Date());
|
|
134
|
+
});
|
|
135
|
+
});
|
|
136
|
+
|
|
137
|
+
describe('job.on', () => {
|
|
138
|
+
test('accepts valid event with valid handler', () => {
|
|
139
|
+
eventBus.job.on('foo', () => {});
|
|
140
|
+
eventBus.job.on('foo', ({ resolve }) => resolve({ value: '' }));
|
|
141
|
+
eventBus.job.on('foo', ({ reject }) => reject(new Error('Oops!')));
|
|
142
|
+
eventBus.job.on('foo', ({ reject }) => reject('Oops!'));
|
|
143
|
+
eventBus.job.on(Symbol(), () => {});
|
|
144
|
+
eventBus.job.on(123, () => {});
|
|
145
|
+
});
|
|
146
|
+
|
|
147
|
+
test('rejects invalid event', () => {
|
|
148
|
+
// @ts-expect-error Argument of type 'Date' is not assignable to parameter of type 'JSON | JSONPrimitive'.
|
|
149
|
+
eventBus.job.on(new Date(), () => {});
|
|
150
|
+
});
|
|
151
|
+
|
|
152
|
+
test('rejects invalid handler', () => {
|
|
153
|
+
eventBus.job.on('foo', ({ reject }) => {
|
|
154
|
+
// @ts-expect-error Argument of type '123' is not assignable to parameter of type 'string | Error | undefined'.
|
|
155
|
+
reject(123);
|
|
156
|
+
});
|
|
157
|
+
});
|
|
158
|
+
});
|
|
159
|
+
|
|
160
|
+
describe('job.off', () => {
|
|
161
|
+
test('accepts valid event with valid handler', () => {
|
|
162
|
+
eventBus.job.off('foo', () => {});
|
|
163
|
+
eventBus.job.off('foo', ({ resolve }) => resolve({ value: '' }));
|
|
164
|
+
eventBus.job.off('foo', ({ reject }) => reject(new Error('Oops!')));
|
|
165
|
+
eventBus.job.off('foo', ({ reject }) => reject('Oops!'));
|
|
166
|
+
eventBus.job.off(Symbol(), () => {});
|
|
167
|
+
eventBus.job.off(123, () => {});
|
|
168
|
+
});
|
|
169
|
+
|
|
170
|
+
test('rejects invalid event', () => {
|
|
171
|
+
// @ts-expect-error Argument of type 'Date' is not assignable to parameter of type 'JSON | JSONPrimitive'.
|
|
172
|
+
eventBus.job.off(new Date(), () => {});
|
|
173
|
+
});
|
|
174
|
+
|
|
175
|
+
test('rejects invalid handler', () => {
|
|
176
|
+
eventBus.job.off('foo', ({ reject }) => {
|
|
177
|
+
// @ts-expect-error Argument of type '123' is not assignable to parameter of type 'string | Error | undefined'.
|
|
178
|
+
reject(123);
|
|
179
|
+
});
|
|
180
|
+
});
|
|
181
|
+
});
|
|
182
|
+
|
|
183
|
+
describe('when event is symbolToken', () => {
|
|
184
|
+
const token = symbolToken<{ value: number }>('token');
|
|
185
|
+
const untypedToken = symbolToken('untyped-token');
|
|
186
|
+
const optionalPayloadToken = symbolToken<{ value: number } | undefined>(
|
|
187
|
+
'optionalToken'
|
|
188
|
+
);
|
|
189
|
+
|
|
190
|
+
describe('emit', () => {
|
|
191
|
+
test('accepts valid data', () => {
|
|
192
|
+
eventBus.emit(token, { value: 1 });
|
|
193
|
+
eventBus.emit(optionalPayloadToken, { value: 1 });
|
|
194
|
+
eventBus.emit(optionalPayloadToken);
|
|
195
|
+
eventBus.emit(untypedToken);
|
|
196
|
+
});
|
|
197
|
+
|
|
198
|
+
test('rejects invalid data', () => {
|
|
199
|
+
// @ts-expect-error Type 'string' is not assignable to type 'number'
|
|
200
|
+
eventBus.emit(token, { value: '' });
|
|
201
|
+
});
|
|
202
|
+
|
|
203
|
+
test('rejects missing data', () => {
|
|
204
|
+
// @ts-expect-error Expected 2 arguments, but got 1
|
|
205
|
+
eventBus.emit(token);
|
|
206
|
+
});
|
|
207
|
+
|
|
208
|
+
test('rejects invalid data type', () => {
|
|
209
|
+
const token = symbolToken<{ value: () => void }>('token');
|
|
210
|
+
|
|
211
|
+
// @ts-expect-error Argument of type 'SymbolToken<{ value: () => void; }>' is not assignable to parameter of type ...
|
|
212
|
+
eventBus.emit(token, { value: () => {} });
|
|
213
|
+
});
|
|
214
|
+
});
|
|
215
|
+
|
|
216
|
+
describe('on', () => {
|
|
217
|
+
test('accepts valid handler', () => {
|
|
218
|
+
eventBus.on(token, () => {});
|
|
219
|
+
eventBus.on(token, data => data.value++);
|
|
220
|
+
eventBus.on(untypedToken, data => data.value++);
|
|
221
|
+
});
|
|
222
|
+
|
|
223
|
+
test('rejects invalid handler', () => {
|
|
224
|
+
// @ts-expect-error Argument of type '(_: number) => void' is not assignable to parameter of type ...
|
|
225
|
+
eventBus.on(token, (_: number) => {});
|
|
226
|
+
|
|
227
|
+
// @ts-expect-error Argument of type '(data: { value: string; }) => number' is not assignable to parameter of type ...
|
|
228
|
+
eventBus.on(token, (data: { value: string }) => data.value.split(''));
|
|
229
|
+
});
|
|
230
|
+
});
|
|
231
|
+
|
|
232
|
+
describe('off', () => {
|
|
233
|
+
test('accepts valid handler', () => {
|
|
234
|
+
eventBus.off(token, () => {});
|
|
235
|
+
eventBus.off(token, (data: { value: number }) => data.value++);
|
|
236
|
+
});
|
|
237
|
+
|
|
238
|
+
test('rejects invalid handler', () => {
|
|
239
|
+
// @ts-expect-error Argument of type '(_: number) => void' is not assignable to parameter of type ...
|
|
240
|
+
eventBus.off(token, (_: number) => {});
|
|
241
|
+
|
|
242
|
+
// @ts-expect-error Argument of type '(data: { value: string; }) => number' is not assignable to parameter of type ...
|
|
243
|
+
eventBus.off(token, (data: { value: string }) => data.value.split(''));
|
|
244
|
+
});
|
|
245
|
+
});
|
|
246
|
+
|
|
247
|
+
describe('job.emit', () => {
|
|
248
|
+
test('accepts token', () => {
|
|
249
|
+
eventBus.job.emit(token);
|
|
250
|
+
});
|
|
251
|
+
});
|
|
252
|
+
|
|
253
|
+
describe('job.on', () => {
|
|
254
|
+
test('accepts valid handler', () => {
|
|
255
|
+
eventBus.job.on(token, ({ resolve }) => resolve({ value: 1 }));
|
|
256
|
+
eventBus.job.on(token, ({ reject }) => reject(new Error('Oops!')));
|
|
257
|
+
eventBus.job.on(token, ({ reject }) => reject('Oops!'));
|
|
258
|
+
eventBus.job.on(optionalPayloadToken, ({ resolve }) =>
|
|
259
|
+
resolve({ value: 1 })
|
|
260
|
+
);
|
|
261
|
+
eventBus.job.on(optionalPayloadToken, ({ resolve }) => resolve());
|
|
262
|
+
});
|
|
263
|
+
|
|
264
|
+
test('rejects invalid handler', () => {
|
|
265
|
+
eventBus.job.on(token, ({ resolve }) => {
|
|
266
|
+
// @ts-expect-error Type 'string' is not assignable to type 'number'.ts(2322)
|
|
267
|
+
resolve({ value: '' });
|
|
268
|
+
});
|
|
269
|
+
eventBus.job.on(token, ({ reject }) => {
|
|
270
|
+
// @ts-expect-error Argument of type '123' is not assignable to parameter of type 'string | Error | undefined'.
|
|
271
|
+
reject(123);
|
|
272
|
+
});
|
|
273
|
+
});
|
|
274
|
+
});
|
|
275
|
+
|
|
276
|
+
describe('job.off', () => {
|
|
277
|
+
test('accepts valid handler', () => {
|
|
278
|
+
eventBus.job.off(token, ({ resolve }) => resolve({ value: 1 }));
|
|
279
|
+
eventBus.job.off(token, ({ reject }) => reject(new Error('Oops!')));
|
|
280
|
+
eventBus.job.off(token, ({ reject }) => reject('Oops!'));
|
|
281
|
+
});
|
|
282
|
+
|
|
283
|
+
test('rejects invalid handler', () => {
|
|
284
|
+
eventBus.job.off(token, ({ resolve }) => {
|
|
285
|
+
// @ts-expect-error Type 'string' is not assignable to type 'number'.ts(2322)
|
|
286
|
+
resolve({ value: '' });
|
|
287
|
+
});
|
|
288
|
+
eventBus.job.off(token, ({ reject }) => {
|
|
289
|
+
// @ts-expect-error Argument of type '123' is not assignable to parameter of type 'string | Error | undefined'.
|
|
290
|
+
reject(123);
|
|
291
|
+
});
|
|
292
|
+
});
|
|
293
|
+
});
|
|
294
|
+
});
|
|
295
|
+
|
|
296
|
+
describe('with legacy type declaration', () => {
|
|
297
|
+
const numberToken = symbolToken<number>('number-token');
|
|
298
|
+
const untypedToken = symbolToken('untyped-token');
|
|
299
|
+
|
|
300
|
+
describe('emit', () => {
|
|
301
|
+
test('accepts valid event with valid data', () => {
|
|
302
|
+
eventBus.emit<number>('foo', 123);
|
|
303
|
+
eventBus.emit<number>(numberToken, 123);
|
|
304
|
+
eventBus.emit<number>(untypedToken, 123);
|
|
305
|
+
eventBus.emit<InterfaceDataType>('foo', { value: '' });
|
|
306
|
+
});
|
|
307
|
+
|
|
308
|
+
test('rejects invalid data type', () => {
|
|
309
|
+
// @ts-expect-error Type 'Function' does not satisfy the constraint 'Serializable<Function>'.
|
|
310
|
+
eventBus.emit<Function>('foo', () => {});
|
|
311
|
+
// @ts-expect-error Type '{ date: Date; }' does not satisfy the constraint 'Serializable<{ date: Date; }>'.
|
|
312
|
+
eventBus.emit<{ date: Date }>('foo', { date: new Date() });
|
|
313
|
+
});
|
|
314
|
+
|
|
315
|
+
test('rejects invalid data', () => {
|
|
316
|
+
// @ts-expect-error Type 'string' is not assignable to type 'number'.
|
|
317
|
+
eventBus.emit<number>('foo', '');
|
|
318
|
+
// @ts-expect-error Type 'string' is not assignable to type 'number'.
|
|
319
|
+
eventBus.emit<number>(numberToken, '');
|
|
320
|
+
// @ts-expect-error Type 'string' is not assignable to type 'number'.
|
|
321
|
+
eventBus.emit<number>(untypedToken, '');
|
|
322
|
+
});
|
|
323
|
+
});
|
|
324
|
+
|
|
325
|
+
describe('on', () => {
|
|
326
|
+
test('accepts valid handler', () => {
|
|
327
|
+
eventBus.on<number>('foo', (_: number) => {});
|
|
328
|
+
eventBus.on<number>(numberToken, (_: number) => {});
|
|
329
|
+
eventBus.on<number>(untypedToken, (_: number) => {});
|
|
330
|
+
eventBus.on<InterfaceDataType>('foo', (_: InterfaceDataType) => {});
|
|
331
|
+
});
|
|
332
|
+
|
|
333
|
+
test('rejects invalid data type', () => {
|
|
334
|
+
// @ts-expect-error Type 'Function' does not satisfy the constraint 'Serializable<Function>'.
|
|
335
|
+
eventBus.on<Function>('foo', () => {});
|
|
336
|
+
// @ts-expect-error Type 'Function' does not satisfy the constraint 'Serializable<Function>'.
|
|
337
|
+
eventBus.on<{ date: Date }>('foo', () => {});
|
|
338
|
+
});
|
|
339
|
+
|
|
340
|
+
test('rejects invalid handler', () => {
|
|
341
|
+
// @ts-expect-error Argument of type '(_: string) => void' is not assignable to parameter of type ...
|
|
342
|
+
eventBus.on<number>('foo', (_: string) => {});
|
|
343
|
+
// @ts-expect-error Argument of type '(_: string) => void' is not assignable to parameter of type ...
|
|
344
|
+
eventBus.on<number>(numberToken, (_: string) => {});
|
|
345
|
+
// @ts-expect-error Argument of type '(_: string) => void' is not assignable to parameter of type ...
|
|
346
|
+
eventBus.on<number>(untypedToken, (_: string) => {});
|
|
347
|
+
});
|
|
348
|
+
});
|
|
349
|
+
|
|
350
|
+
describe('off', () => {
|
|
351
|
+
test('accepts valid handler', () => {
|
|
352
|
+
eventBus.off<number>('foo', (_: number) => {});
|
|
353
|
+
eventBus.off<number>(numberToken, (_: number) => {});
|
|
354
|
+
eventBus.off<number>(untypedToken, (_: number) => {});
|
|
355
|
+
eventBus.off<InterfaceDataType>('foo', (_: InterfaceDataType) => {});
|
|
356
|
+
});
|
|
357
|
+
|
|
358
|
+
test('rejects invalid data type', () => {
|
|
359
|
+
// @ts-expect-error Type 'Function' does not satisfy the constraint 'Serializable<Function>'.
|
|
360
|
+
eventBus.off<Function>('foo', () => {});
|
|
361
|
+
// @ts-expect-error Type 'Function' does not satisfy the constraint 'Serializable<Function>'.
|
|
362
|
+
eventBus.off<{ date: Date }>('foo', () => {});
|
|
363
|
+
});
|
|
364
|
+
|
|
365
|
+
test('rejects invalid handler', () => {
|
|
366
|
+
// @ts-expect-error Argument of type '(_: number) => void' is not assignable to parameter of type ...
|
|
367
|
+
eventBus.off<string>('foo', (_: number) => {});
|
|
368
|
+
// @ts-expect-error Argument of type '(_: string) => void' is not assignable to parameter of type ...
|
|
369
|
+
eventBus.off<number>(numberToken, (_: string) => {});
|
|
370
|
+
// @ts-expect-error Argument of type '(_: string) => void' is not assignable to parameter of type ...
|
|
371
|
+
eventBus.off<number>(untypedToken, (_: string) => {});
|
|
372
|
+
});
|
|
373
|
+
});
|
|
374
|
+
});
|
|
375
|
+
});
|
|
376
|
+
|
|
377
|
+
describe('when eventBus is typed', () => {
|
|
378
|
+
interface TestEvents {
|
|
379
|
+
'number-event': { value: number };
|
|
380
|
+
'string-event': { value: string };
|
|
381
|
+
'array-event': [string, { value: string }];
|
|
382
|
+
'optional-data-event': { value: number } | undefined;
|
|
383
|
+
'interface-data-event': InterfaceDataType;
|
|
384
|
+
}
|
|
385
|
+
|
|
386
|
+
const eventBus = new EventBus<TestEvents>();
|
|
387
|
+
|
|
388
|
+
describe('emit', () => {
|
|
389
|
+
test('accepts valid events and data', () => {
|
|
390
|
+
eventBus.emit('number-event', { value: 1 });
|
|
391
|
+
eventBus.emit('string-event', { value: '' });
|
|
392
|
+
eventBus.emit('optional-data-event', { value: 1 });
|
|
393
|
+
eventBus.emit('optional-data-event');
|
|
394
|
+
const data: InterfaceDataType = { value: '' };
|
|
395
|
+
eventBus.emit('interface-data-event', data);
|
|
396
|
+
});
|
|
397
|
+
|
|
398
|
+
test('rejects invalid event', () => {
|
|
399
|
+
// @ts-expect-error '"foo"' is not assignable to parameter of type 'keyof TestEvents'
|
|
400
|
+
eventBus.emit('foo', { value: 1 });
|
|
401
|
+
});
|
|
402
|
+
|
|
403
|
+
test('rejects invalid data', () => {
|
|
404
|
+
// @ts-expect-error Type 'string' is not assignable to type 'number'
|
|
405
|
+
eventBus.emit('number-event', { value: '' });
|
|
406
|
+
|
|
407
|
+
// @ts-expect-error 'foo' does not exist in type '{ value: number; }'
|
|
408
|
+
eventBus.emit('number-event', { foo: 1 });
|
|
409
|
+
});
|
|
410
|
+
|
|
411
|
+
test('rejects missing data', () => {
|
|
412
|
+
// @ts-expect-error Expected 2 arguments, but got 1
|
|
413
|
+
eventBus.emit('number-event');
|
|
414
|
+
});
|
|
415
|
+
|
|
416
|
+
test('accepts event with no data', () => {
|
|
417
|
+
new EventBus<{ foo: never }>().emit('foo');
|
|
418
|
+
new EventBus<{ foo: undefined }>().emit('foo');
|
|
419
|
+
});
|
|
420
|
+
});
|
|
421
|
+
|
|
422
|
+
describe('on', () => {
|
|
423
|
+
test('accepts valid event and handler', () => {
|
|
424
|
+
eventBus.on('number-event', () => {});
|
|
425
|
+
eventBus.on('number-event', data => data.value++);
|
|
426
|
+
eventBus.on('string-event', data => data.value.split(''));
|
|
427
|
+
});
|
|
428
|
+
|
|
429
|
+
test('rejects invalid event', () => {
|
|
430
|
+
// @ts-expect-error Argument of type '"foo"' is not assignable to parameter of type 'keyof TestEvents'
|
|
431
|
+
eventBus.on('foo', () => {});
|
|
432
|
+
});
|
|
433
|
+
|
|
434
|
+
test('rejects invalid handler', () => {
|
|
435
|
+
// @ts-expect-error Property 'split' does not exist on type 'number'.
|
|
436
|
+
eventBus.on('number-event', data => data.value.split(''));
|
|
437
|
+
|
|
438
|
+
// @ts-expect-error An arithmetic operand must be of type 'any', 'number', 'bigint' or an enum type.
|
|
439
|
+
eventBus.on('string-event', data => data.value++);
|
|
440
|
+
});
|
|
441
|
+
});
|
|
442
|
+
|
|
443
|
+
describe('off', () => {
|
|
444
|
+
test('accepts valid event and handler', () => {
|
|
445
|
+
eventBus.off('number-event', () => {});
|
|
446
|
+
eventBus.off('number-event', data => data.value++);
|
|
447
|
+
eventBus.off('string-event', data => data.value.split(''));
|
|
448
|
+
});
|
|
449
|
+
|
|
450
|
+
test('rejects invalid event', () => {
|
|
451
|
+
// @ts-expect-error Argument of type '"foo"' is not assignable to parameter of type 'keyof TestEvents'
|
|
452
|
+
eventBus.off('foo', () => {});
|
|
453
|
+
});
|
|
454
|
+
|
|
455
|
+
test('rejects invalid handler', () => {
|
|
456
|
+
// @ts-expect-error Property 'split' does not exist on type 'number'.
|
|
457
|
+
eventBus.off('number-event', data => data.value.split(''));
|
|
458
|
+
|
|
459
|
+
// @ts-expect-error An arithmetic operand must be of type 'any', 'number', 'bigint' or an enum type.
|
|
460
|
+
eventBus.off('string-event', data => data.value++);
|
|
461
|
+
});
|
|
462
|
+
});
|
|
463
|
+
|
|
464
|
+
describe('job.emit', () => {
|
|
465
|
+
test('accepts valid event', () => {
|
|
466
|
+
eventBus.job.emit('number-event');
|
|
467
|
+
eventBus.job.emit('string-event');
|
|
468
|
+
});
|
|
469
|
+
|
|
470
|
+
test('rejects invalid event', () => {
|
|
471
|
+
// @ts-expect-error Argument of type '"foo"' is not assignable to parameter of type 'keyof TestEvents'.
|
|
472
|
+
eventBus.job.emit('foo');
|
|
473
|
+
});
|
|
474
|
+
});
|
|
475
|
+
|
|
476
|
+
describe('job.on', () => {
|
|
477
|
+
test('accepts valid event and handler', () => {
|
|
478
|
+
eventBus.job.on('number-event', () => {});
|
|
479
|
+
eventBus.job.on('number-event', ({ resolve }) => resolve({ foo: 1 }));
|
|
480
|
+
eventBus.job.on('string-event', ({ resolve }) => resolve({ foo: 1 }));
|
|
481
|
+
eventBus.job.on('string-event', ({ reject }) => reject(new Error('Oops!')));
|
|
482
|
+
eventBus.job.on('number-event', ({ reject }) => reject('Oops!'));
|
|
483
|
+
});
|
|
484
|
+
|
|
485
|
+
test('rejects invalid event', () => {
|
|
486
|
+
// @ts-expect-error Argument of type '"foo"' is not assignable to parameter of type 'keyof TestEvents'.
|
|
487
|
+
eventBus.job.on('foo', () => {});
|
|
488
|
+
});
|
|
489
|
+
|
|
490
|
+
test('rejects invalid handler', () => {
|
|
491
|
+
// @ts-expect-error Argument of type '123' is not assignable to parameter of type 'string | Error | undefined'
|
|
492
|
+
eventBus.job.on('number-event', ({ reject }) => reject(123));
|
|
493
|
+
});
|
|
494
|
+
});
|
|
495
|
+
|
|
496
|
+
describe('job.off', () => {
|
|
497
|
+
test('accepts valid event and handler', () => {
|
|
498
|
+
eventBus.job.off('number-event', () => {});
|
|
499
|
+
eventBus.job.off('number-event', ({ resolve }) => resolve({ foo: 1 }));
|
|
500
|
+
eventBus.job.off('string-event', ({ resolve }) => resolve({ foo: 1 }));
|
|
501
|
+
eventBus.job.off('string-event', ({ reject }) => reject(new Error('Oops!')));
|
|
502
|
+
eventBus.job.off('number-event', ({ reject }) => reject('Oops!'));
|
|
503
|
+
});
|
|
504
|
+
|
|
505
|
+
test('rejects invalid event', () => {
|
|
506
|
+
// @ts-expect-error Argument of type '"foo"' is not assignable to parameter of type 'keyof TestEvents'.
|
|
507
|
+
eventBus.job.off('foo', () => {});
|
|
508
|
+
});
|
|
509
|
+
|
|
510
|
+
test('rejects invalid handler', () => {
|
|
511
|
+
// @ts-expect-error Argument of type '123' is not assignable to parameter of type 'string | Error | undefined'
|
|
512
|
+
eventBus.job.off('number-event', ({ reject }) => reject(123));
|
|
513
|
+
});
|
|
514
|
+
});
|
|
515
|
+
|
|
516
|
+
describe('when event is symbolToken', () => {
|
|
517
|
+
const token = symbolToken<{ value: number }>('token');
|
|
518
|
+
const optionalPayloadToken = symbolToken<{ value: number } | undefined>(
|
|
519
|
+
'optionalToken'
|
|
520
|
+
);
|
|
521
|
+
|
|
522
|
+
const eventBus = new EventBus<TestEvents>();
|
|
523
|
+
|
|
524
|
+
describe('emit', () => {
|
|
525
|
+
test('accepts valid data', () => {
|
|
526
|
+
eventBus.emit(token, { value: 1 });
|
|
527
|
+
eventBus.emit(optionalPayloadToken, { value: 1 });
|
|
528
|
+
eventBus.emit(optionalPayloadToken);
|
|
529
|
+
});
|
|
530
|
+
|
|
531
|
+
test('rejects invalid data', () => {
|
|
532
|
+
// @ts-expect-error Type 'string' is not assignable to type 'number'
|
|
533
|
+
eventBus.emit(token, { value: '' });
|
|
534
|
+
});
|
|
535
|
+
|
|
536
|
+
test('rejects missing value', () => {
|
|
537
|
+
// @ts-expect-error Expected 2 arguments, but got 1
|
|
538
|
+
eventBus.emit(token);
|
|
539
|
+
});
|
|
540
|
+
});
|
|
541
|
+
|
|
542
|
+
describe('on', () => {
|
|
543
|
+
test('accepts valid handler', () => {
|
|
544
|
+
eventBus.on(token, () => {});
|
|
545
|
+
eventBus.on(token, data => data.value++);
|
|
546
|
+
});
|
|
547
|
+
|
|
548
|
+
test('rejects invalid handler', () => {
|
|
549
|
+
// @ts-expect-error Argument of type '(_: number) => void' is not assignable to parameter of type ...
|
|
550
|
+
eventBus.on(token, (_: number) => {});
|
|
551
|
+
|
|
552
|
+
// @ts-expect-error Argument of type '(data: { value: string; }) => number' is not assignable to parameter of type ...
|
|
553
|
+
eventBus.on(token, (data: { value: string }) => data.value.split(''));
|
|
554
|
+
});
|
|
555
|
+
});
|
|
556
|
+
|
|
557
|
+
describe('off', () => {
|
|
558
|
+
test('accepts valid handler', () => {
|
|
559
|
+
eventBus.off(token, () => {});
|
|
560
|
+
eventBus.off(token, data => data.value++);
|
|
561
|
+
});
|
|
562
|
+
|
|
563
|
+
test('rejects invalid handler', () => {
|
|
564
|
+
// @ts-expect-error Argument of type '(_: number) => void' is not assignable to parameter of type ...
|
|
565
|
+
eventBus.off(token, (_: number) => {});
|
|
566
|
+
|
|
567
|
+
// @ts-expect-error Argument of type '(data: { value: string; }) => number' is not assignable to parameter of type ...
|
|
568
|
+
eventBus.off(token, (data: { value: string }) => data.value.split(''));
|
|
569
|
+
});
|
|
570
|
+
});
|
|
571
|
+
|
|
572
|
+
describe('job.emit', () => {
|
|
573
|
+
test('accepts token', () => {
|
|
574
|
+
eventBus.job.emit(token);
|
|
575
|
+
});
|
|
576
|
+
});
|
|
577
|
+
|
|
578
|
+
describe('job.on', () => {
|
|
579
|
+
test('accepts valid handler', () => {
|
|
580
|
+
eventBus.job.on(token, ({ resolve }) => resolve({ value: 1 }));
|
|
581
|
+
eventBus.job.on(token, ({ reject }) => reject(new Error('Oops!')));
|
|
582
|
+
eventBus.job.on(token, ({ reject }) => reject('Oops!'));
|
|
583
|
+
eventBus.job.on(optionalPayloadToken, ({ resolve }) => resolve());
|
|
584
|
+
});
|
|
585
|
+
|
|
586
|
+
test('rejects invalid handler', () => {
|
|
587
|
+
eventBus.job.on(token, ({ resolve }) => {
|
|
588
|
+
// @ts-expect-error Type 'string' is not assignable to type 'number'.ts(2322)
|
|
589
|
+
resolve({ value: '' });
|
|
590
|
+
});
|
|
591
|
+
eventBus.job.on(token, ({ reject }) => {
|
|
592
|
+
// @ts-expect-error Argument of type '123' is not assignable to parameter of type 'string | Error | undefined'.
|
|
593
|
+
reject(123);
|
|
594
|
+
});
|
|
595
|
+
});
|
|
596
|
+
});
|
|
597
|
+
|
|
598
|
+
describe('job.off', () => {
|
|
599
|
+
test('accepts valid handler', () => {
|
|
600
|
+
eventBus.job.off(token, ({ resolve }) => resolve({ value: 1 }));
|
|
601
|
+
eventBus.job.off(token, ({ reject }) => reject(new Error('Oops!')));
|
|
602
|
+
eventBus.job.off(token, ({ reject }) => reject('Oops!'));
|
|
603
|
+
});
|
|
604
|
+
|
|
605
|
+
test('rejects invalid handler', () => {
|
|
606
|
+
eventBus.job.off(token, ({ resolve }) => {
|
|
607
|
+
// @ts-expect-error Type 'string' is not assignable to type 'number'.ts(2322)
|
|
608
|
+
resolve({ value: '' });
|
|
609
|
+
});
|
|
610
|
+
eventBus.job.off(token, ({ reject }) => {
|
|
611
|
+
// @ts-expect-error Argument of type '123' is not assignable to parameter of type 'string | Error | undefined'.
|
|
612
|
+
reject(123);
|
|
613
|
+
});
|
|
614
|
+
});
|
|
615
|
+
});
|
|
616
|
+
});
|
|
617
|
+
});
|
|
618
|
+
});
|
|
619
|
+
});
|
|
@@ -1,6 +1,5 @@
|
|
|
1
1
|
import * as mitt from 'mitt';
|
|
2
|
-
import {
|
|
3
|
-
import { useEventBus, EventBus } from '../event-bus';
|
|
2
|
+
import { EventBus, typedEventBusToken, EVENT_BUS_TOKEN } from '../event-bus';
|
|
4
3
|
|
|
5
4
|
jest.mock('mitt', () => jest.fn());
|
|
6
5
|
|
|
@@ -126,22 +125,10 @@ describe(`[web-components] ${EventBus.name}`, () => {
|
|
|
126
125
|
});
|
|
127
126
|
});
|
|
128
127
|
|
|
129
|
-
describe(`[web-components] ${
|
|
130
|
-
|
|
131
|
-
return renderHook(() => useEventBus());
|
|
132
|
-
}
|
|
128
|
+
describe(`[web-components] ${typedEventBusToken.name}`, () => {
|
|
129
|
+
const subject = () => typedEventBusToken<any>();
|
|
133
130
|
|
|
134
|
-
test('
|
|
135
|
-
expect(subject()
|
|
136
|
-
});
|
|
137
|
-
|
|
138
|
-
test('when the component using useEventBus is re-rendered, useEventBus provides the same event bus instance', () => {
|
|
139
|
-
const { result, rerender } = subject();
|
|
140
|
-
|
|
141
|
-
const firstInstance = result.current;
|
|
142
|
-
rerender();
|
|
143
|
-
|
|
144
|
-
const secondInstance = result.current;
|
|
145
|
-
expect(firstInstance).toBe(secondInstance);
|
|
131
|
+
test('returns EVENT_BUS_TOKEN', () => {
|
|
132
|
+
expect(subject()).toBe(EVENT_BUS_TOKEN);
|
|
146
133
|
});
|
|
147
134
|
});
|