Search code examples
javascripttypescriptweb-workersveltekitzxcvbn

How can I run a worker with dependencies in javascript and sveltekit


I am trying to use the module zxcvbn in my project. It is fine for passwords up to around 50 chars. After it takes too long of a time to grade each password.

I'm trying to use workers to run the function and update the state in sveltekit. The code looks like this.

// src/generator/+page.svelte

onMount(() => {
    const w = new Worker("src/routes/generator/worker");
    w.postMessage("password");
    w.onmessage = function (event) {
      console.log(event.data);
    };
  });
// src/generator/worker.ts

import zxcvbn from "zxcvbn";    // throws error "Uncaught SyntaxError: Cannot use import statement outside a module (at worker.ts:1:1)"

const passwordStrength = (password: string) => {
  const res = zxcvbn(password);
  postMessage(res);
};

self.onmessage = (e) => {
  passwordStrength(e.data);
};

I'm new to Sveltekit and javascript/typescript as a whole so any suggestions are welcome.


Solution

  • I ended up importing the worker as such

    // src/generator/+page.svelte
    
    import MyWorker from "src/generator/worker?worker";
    
    
    const w = new MyWorker();
    w.postMessage("password");
    w.onmessage = function (event) {
       console.log(event.data);
    };
    
    // src/generator/worker.ts
    
    import zxcvbn from "zxcvbn";
    
    const passwordStrength = (password: string) => {
      const res = zxcvbn(password);
      postMessage(res);
    };
    
    self.onmessage = (e) => {
      passwordStrength(e.data);
    };
    

    Vite supports importing the worker directly. Then I could run it with no problem and it wouldn't block other javascript. A different solution I saw was to make the worker like this new Worker("/my/path/workerfile?worker", {type: "module"})

    DISCLAIMER: Solution/explanation might not be 100% correct as I am still learning.