Unverified Commit 484dfc52 authored by davelopez's avatar davelopez
Browse files

Revert "reuse single worker"

This reverts commit 236492f87f47f2a46235aee00fb6317148b139d4.
parent c8db62f6
Loading
Loading
Loading
Loading
+37 −43
Original line number Diff line number Diff line
import { toValue } from "@vueuse/core";
import { onScopeDispose, ref, watchEffect } from "vue";
import { onScopeDispose, ref, watch } from "vue";

let worker;
let idCounter = 0;
let workerReferenceCount = 0;
export function useFilterObjectArray(array, filter, objectFields, asRegex = false) {
    const worker = new Worker(new URL("./filter.worker.js", import.meta.url));

export function useFilterObjectArray(array, filter, objectFields) {
    if (!worker) {
        worker = new Worker(new URL("./filter.worker.js", import.meta.url));
    }

    workerReferenceCount += 1;
    const id = idCounter++;
    const filtered = ref([]);
    filtered.value = toValue(array);

    const post = (message) => {
        worker.postMessage({ id, ...message });
        worker.postMessage(message);
    };

    const filtered = ref([]);
    filtered.value = toValue(array);
    watch(
        () => toValue(array),
        (arr) => {
            post({ type: "setArray", array: arr });
        },
        {
            immediate: true,
        }
    );

    watch(
        () => toValue(filter),
        (f) => {
            post({ type: "setFilter", filter: f });
        },
        {
            immediate: true,
        }
    );

    watch(
        () => toValue(objectFields),
        (fields) => {
            post({ type: "setFields", fields });
        },
        {
            immediate: true,
        }
    );

    const onMessage = (e) => {
    worker.onmessage = (e) => {
        const message = e.data;

        // exit if message is not meant for this composable instance
        if (message.id !== id) {
            return;
        }

        if (message.type === "result") {
            filtered.value = message.filtered;
        } else {
            post({ type: "clear" });
            worker.removeEventListener("message", onMessage);
        }
    };

    worker.addEventListener("message", onMessage);

    watchEffect(() => {
        post({ type: "setArray", array: toValue(array) });
    });

    watchEffect(() => {
        post({ type: "setFilter", filter: toValue(filter) });
    });

    watchEffect(() => {
        post({ type: "setFields", fields: toValue(objectFields) });
    });

    onScopeDispose(() => {
        workerReferenceCount -= 1;

        if (workerReferenceCount <= 0) {
        worker.terminate();
            worker = null;
        }
    });

    return filtered;
+12 −49
Original line number Diff line number Diff line
import { runFilter } from "@/composables/filter/filterFunction";

function createOptions() {
    return {
        array: [],
        filter: "",
        fields: [],
    };
}

const optionsById = new Map();
const timerById = new Map();
let array = [];
let filter = "";
let fields = [];

self.addEventListener("message", (e) => {
    const message = e.data;

    if (!optionsById.has(message.id)) {
        optionsById.set(message.id, createOptions());
    }

    const options = optionsById.get(message.id);

    switch (message.type) {
        case "setArray":
            options.array = message.array;
            break;

        case "setFields":
            options.fields = message.fields;
            break;

        case "setFilter":
            options.filter = message.filter;
            break;

        case "clear":
            optionsById.delete(message.id);
            break;

        default:
            break;
    if (message.type === "setArray") {
        array = message.array;
    } else if (message.type === "setFields") {
        fields = message.fields;
    } else if (message.type === "setFilter") {
        filter = message.filter;
    }

    if (timerById.has(message.id)) {
        clearTimeout(timerById.get(message.id));
    }

    timerById.set(
        message.id,
        setTimeout(() => {
            if (options.array.length > 0 && options.fields.length > 0) {
                const filtered = runFilter(options.filter, options.array, options.fields);
    if (array.length > 0 && fields.length > 0) {
        const filtered = runFilter(filter, array, fields);
        self.postMessage({ type: "result", filtered });
    }

            timerById.delete(message.id);
        }, 10)
    );
});