/*!
 * Copyright (c) 2026 Vertex Software LLC. All rights reserved.
 */
import { Async } from "@vertexvis/utils";
export const DEFAULT_TIMEOUT_IN_MS = 1000 * 10;
export class StreamApiEventDispatcher {
    constructor(stream, predicate, transform, timeout = DEFAULT_TIMEOUT_IN_MS) {
        this.stream = stream;
        this.predicate = predicate;
        this.transform = transform;
        this.timeout = timeout;
        this.listeners = [];
        this.handleMessage = this.handleMessage.bind(this);
    }
    on(listener) {
        this.listeners = [...this.listeners, listener];
        if (this.eventDisposable == null || this.requestDisposable == null) {
            this.addListeners();
        }
    }
    off(listener) {
        this.listeners = this.listeners.filter((l) => l !== listener);
        if (this.listeners.length === 0) {
            this.removeListeners();
        }
    }
    once() {
        let handler;
        return Async.timeout(this.timeout, new Promise((resolve) => {
            handler = (data) => {
                resolve(data);
                this.off(handler);
            };
            this.on(handler);
        })).finally(() => {
            this.off(handler);
        });
    }
    handleMessage(msg) {
        if (this.predicate(msg)) {
            const transformed = this.transform(msg);
            if (transformed != null) {
                this.listeners.forEach((l) => l(transformed));
            }
        }
    }
    addListeners() {
        this.eventDisposable = this.stream.onEvent(this.handleMessage);
        this.requestDisposable = this.stream.onRequest(this.handleMessage);
    }
    removeListeners() {
        var _a, _b;
        (_a = this.eventDisposable) === null || _a === void 0 ? void 0 : _a.dispose();
        (_b = this.requestDisposable) === null || _b === void 0 ? void 0 : _b.dispose();
    }
}
//# sourceMappingURL=dispatcher.js.map
