-
-
Notifications
You must be signed in to change notification settings - Fork 6.4k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
TypeScript WebWorker scripts imported with new URL()
get inlined as data:video/mp2t
#11823
Comments
Hi, @kulmajaba. When you write your code like workerFactory(new URL('./worker.ts', import.meta.url), { type: 'module' }); the URL is treated as an asset url, and will be transformed by the asset plugin in an unintended way. The correct way to get the url of a worker can be found here: import myWorkerUrl from './worker?worker&url' If you also like es module for your workers, you should also change this option. |
@K024 The query suffix does work, so I suppose there are two separate problems at play:
|
I'm trying to import a worker script in my Electron app(main process).
|
Did you find any solution for this? |
This solution does not work for using a factory and thus doesn't actually work for SharedWorker with a Worker fallback (which in turn is required for Android support). |
As a workaround, You can name the factory So this should work: const Worker = (workerScript: URL, workerOptions: WorkerOptions) => () => new globalThis.Worker(workerScript, workerOptions);
const main = () => {
const factory = Worker(new URL('./worker.ts', import.meta.url), { type: 'module' });
const worker = factory();
...
}; Example of how I'm using this: const hasSharedWorker = (globalThis.SharedWorker as any) != (globalThis.Worker as any)
const SharedWorker = hasSharedWorker ? globalThis.SharedWorker : Worker
const worker = new SharedWorker(
new URL("./worker.ts", import.meta.url),
{ type: "module", name: "pinto:back", credentials: "include" }
)
const port = hasSharedWorker ? (worker as SharedWorker).port : worker as Worker |
Also note that Vite is also not adding a timestamp to the generated URLs in dev mode: import api from "/vite-dev/repository/api.ts?t=1712992006878";
const worker = new SharedWorker(
new URL('' + "/vite-dev/entrypoints/worker.ts?type=module&worker_file", import.meta.url),
{ type: "module", name: "pinto:back", credentials: "include" }
); I'm not sure if this is intentional. I can see reasons for and against it. If you include a timestamp, you might end up with two different shared workers running at the same time. However, if you don't, you might end up with the old shared worker still running and no new worker starting up. This makes it impossible to write and easily test code that is supposed to handle this exact scenario in production. This is possibly a new issue. |
This unfortunately does not help with // Vite has an issue where it thinks a TS file is a video (MPEG transport stream) unless you directly pass it to a worker
// And we can't use the import worker syntax because it conflicts with Bun module resolution
// So we trick it into think we are initialising a web worker
class Worker {
url: URL;
opts: WorkerOptions;
constructor(url: URL, opts: WorkerOptions) {
this.url = url;
this.opts = opts;
}
getUrl() {
return this.url;
}
}
const tempWorker = new Worker(
new URL("./my-worker.ts", import.meta.url),
{
type: "module"
}
);
const workerPool = workerpool.pool(tempWorker.getUrl().toString(), {
workerOpts: {
type: "module"
}
}); |
Vite also does this with the regular |
Describe the bug
With a vanilla TS project, using WebWorkers with the recommended
URL
syntax works fine:Building the project gives me two separate files, a main file and the worker file.
However, if the worker is created with e.g. a factory pattern and still using the URL syntax, some interesting things happen:
Now, the worker is inlined as Base64, but the MIME type is wrong and set to
data:video/mp2t
(because .ts is a valid video file extension too).The use case for a pattern like this is e.g. creating a Promisified version of the WebWorker interface and making it usable with any worker.
Reproduction
https://stackblitz.com/edit/vitejs-vite-8ewkf4?file=src/main.ts
Steps to reproduce
Run
npm run build
and check the bundled code.System Info
Used Package Manager
npm
Logs
No response
Validations
The text was updated successfully, but these errors were encountered: