|
1 |
| -/* eslint-disable @typescript-eslint/no-unsafe-member-access */ |
2 |
| -import { compress, Compressor } from './Compressor'; |
3 |
| - |
4 |
| -const compressor = new Compressor(); |
| 1 | +import { Compressor } from './Compressor'; |
5 | 2 |
|
6 | 3 | interface Handlers {
|
7 |
| - clear: () => void; |
| 4 | + clear: (mode?: string) => void; |
8 | 5 | addEvent: (data: string) => void;
|
9 | 6 | finish: () => Uint8Array;
|
10 |
| - compress: (data: string) => Uint8Array; |
11 | 7 | }
|
12 | 8 |
|
13 |
| -const handlers: Handlers = { |
14 |
| - clear: () => { |
15 |
| - compressor.clear(); |
16 |
| - }, |
| 9 | +class CompressionHandler implements Handlers { |
| 10 | + private _compressor: Compressor; |
| 11 | + private _bufferCompressor?: Compressor; |
| 12 | + |
| 13 | + public constructor() { |
| 14 | + this._compressor = new Compressor(); |
| 15 | + } |
| 16 | + |
| 17 | + public clear(mode?: string): void { |
| 18 | + /* |
| 19 | + In buffer mode, we want to make sure to always keep the last round of events around. |
| 20 | + So when the time comes and we finish the buffer, we can ensure that we have at least one set of events. |
| 21 | + Without this change, it can happen that you finish right after the last checkout (=clear), |
| 22 | + and thus have no (or very few) events buffered. |
| 23 | +
|
| 24 | + Now, in buffer mode, we basically have to compressors, which are swapped and reset on clear: |
| 25 | + * On first `clear` in buffer mode, we initialize the buffer compressor. |
| 26 | + The regular compressor keeps running as the "current" one |
| 27 | + * On consequitive `clear` calls, we swap the buffer compressor in as the "current" one, and initialize a new buffer compressor |
| 28 | + This will clear any events that were buffered before the _last_ clear call. |
| 29 | +
|
| 30 | + This sadly means we need to keep the buffer twice in memory. But it's a tradeoff we have to make. |
| 31 | + */ |
| 32 | + if (mode === 'buffer') { |
| 33 | + // This means it is the first clear in buffer mode - just initialize a new compressor for the alternate compressor |
| 34 | + if (!this._bufferCompressor) { |
| 35 | + this._bufferCompressor = new Compressor(); |
| 36 | + } else { |
| 37 | + // Else, swap the alternative compressor in as "normal" compressor, and initialize a new alterntive compressor |
| 38 | + this._compressor = this._bufferCompressor; |
| 39 | + this._bufferCompressor = new Compressor(); |
| 40 | + } |
| 41 | + return; |
| 42 | + } |
| 43 | + |
| 44 | + /* |
| 45 | + In non-buffer mode, we just clear the current compressor (and make sure an eventual buffer compressor is reset) |
| 46 | + */ |
| 47 | + this._bufferCompressor = undefined; |
| 48 | + |
| 49 | + this._compressor.clear(); |
| 50 | + } |
17 | 51 |
|
18 |
| - addEvent: (data: string) => { |
19 |
| - return compressor.addEvent(data); |
20 |
| - }, |
| 52 | + public addEvent(data: string): void { |
| 53 | + if (this._bufferCompressor) { |
| 54 | + this._bufferCompressor.addEvent(data); |
| 55 | + } |
21 | 56 |
|
22 |
| - finish: () => { |
23 |
| - return compressor.finish(); |
24 |
| - }, |
| 57 | + return this._compressor.addEvent(data); |
| 58 | + } |
25 | 59 |
|
26 |
| - compress: (data: string) => { |
27 |
| - return compress(data); |
28 |
| - }, |
29 |
| -}; |
| 60 | + public finish(): Uint8Array { |
| 61 | + if (this._bufferCompressor) { |
| 62 | + this._bufferCompressor.clear(); |
| 63 | + this._bufferCompressor = undefined; |
| 64 | + } |
| 65 | + |
| 66 | + return this._compressor.finish(); |
| 67 | + } |
| 68 | +} |
| 69 | + |
| 70 | +const handlers = new CompressionHandler(); |
30 | 71 |
|
31 | 72 | /**
|
32 | 73 | * Handler for worker messages.
|
33 | 74 | */
|
34 |
| -export function handleMessage(e: MessageEvent): void { |
35 |
| - const method = e.data.method as string; |
36 |
| - const id = e.data.id as number; |
37 |
| - const data = e.data.arg as string; |
| 75 | +export function handleMessage(event: MessageEvent): void { |
| 76 | + const data = event.data as { |
| 77 | + method: keyof Handlers; |
| 78 | + id: number; |
| 79 | + arg: string; |
| 80 | + }; |
| 81 | + |
| 82 | + const { method, id, arg } = data; |
38 | 83 |
|
39 |
| - // @ts-ignore this syntax is actually fine |
40 |
| - if (method in handlers && typeof handlers[method] === 'function') { |
| 84 | + if (typeof handlers[method] === 'function') { |
41 | 85 | try {
|
42 |
| - // @ts-ignore this syntax is actually fine |
43 |
| - const response = handlers[method](data); |
44 |
| - // @ts-ignore this syntax is actually fine |
| 86 | + const response = handlers[method](arg); |
45 | 87 | postMessage({
|
46 | 88 | id,
|
47 | 89 | method,
|
48 | 90 | success: true,
|
49 | 91 | response,
|
50 | 92 | });
|
51 | 93 | } catch (err) {
|
52 |
| - // @ts-ignore this syntax is actually fine |
53 | 94 | postMessage({
|
54 | 95 | id,
|
55 | 96 | method,
|
56 | 97 | success: false,
|
57 |
| - response: err.message, |
| 98 | + response: (err as Error).message, |
58 | 99 | });
|
59 | 100 |
|
60 | 101 | // eslint-disable-next-line no-console
|
|
0 commit comments