Hello,
Is there any way to use ts-node with WebWorkers __but__ without using webpack?
When I do:
const worker = new Worker('path-to/workerFile.ts', { // ... });
I get:
TypeError [ERR_WORKER_UNSUPPORTED_EXTENSION]: The worker script extension must be ".js" or ".mjs". Received ".ts"
at new Worker (internal/worker.js:272:15)
// ....
Any ideas?
Tomer
This is a node.js error, it doesn鈥檛 look like it based on the error message.
@blakeembrey thanks for your quick reply :)
Not sure I fully understand what you mean by "it doesn鈥檛 look like it based on the error message".
I know it's a node.js error, but still, I think it's a ts-node related topic, cause correct me if I'm wrong but after stating a ts-node app, it compiles the ts and executing the js.
But with WebWorkers, it gets a bit more complicated cause web worker require a file path, so if I want to use a .ts as the worker input that's the exception node throws.
So, I can write all the worker code in js or compile ts file on my own.
Maybe it will be a good idea to somehow detect the worker's path and switch it with the compiled path?
@kutomer It might be possible as a plugin to ts-node, not sure it will belong here. It's a tricky task because you're suggesting changing compiled code which I haven't wanted to do so far. I do think, if someone were to do it, it should be implemented as a plugin like tsconfig-paths or a plugin to the compiler AST. I won't have the time to implement the change, but happy to link and improve the TypeScript plugin process in ts-node to support the use-case.
@blakeembrey thanks again,
Do you think I can somehow get the file's compiled path? something like require.resolve()?
There鈥檚 a couple of issues with that:
What we could do is expose the internal compiler/config at runtime and you could generate/write the file yourself. Perhaps with a little TsWorker wrapper? Would this be a good starting point?
that's definitely sound like a good starting point but unfortunately, I don't have the time right now to do that so I guess I'll just migrate to webpack :(
anyway, I really appreciate your help! thanks again
I have the same issue, is there any good solution for this?
The problem is the worker has a separate require() cache and require.extensions. ts-node is not installed in the worker, and node does not expose an API that would let us auto-install ourselves into all workers. Also, I'm not sure that would be a good idea. Third-party libraries using worker_threads shouldn't pay a performance hit just so we can install duplicate copies of ourselves into every worker.
Fortunately, I think the solution is simple: when you want to spawn a worker with ts-node, use our ts-node/register endpoint to install us.
new Worker(`
require('ts-node/register');
require(require('worker_threads').workerData.runThisFileInTheWorker);
`, {
eval: true,
workerData: {
runThisFileInTheWorker: '/path/to/worker-script.ts'
}
});
To add to the above, if you want non-relative paths to be resolved according to your tsconfig baseUrl and paths, you should install the tsconfig-paths module, and spawn the worker like so:
new Worker(`
require('tsconfig-paths/register');
require('ts-node/register');
require(require('worker_threads').workerData.runThisFileInTheWorker);
`, {
eval: true,
workerData: {
runThisFileInTheWorker: '/path/to/worker-script.ts'
}
});
@cspotcode You saved my whole day!
Most helpful comment
The problem is the worker has a separate require() cache and
require.extensions.ts-nodeis not installed in the worker, and node does not expose an API that would let us auto-install ourselves into all workers. Also, I'm not sure that would be a good idea. Third-party libraries usingworker_threadsshouldn't pay a performance hit just so we can install duplicate copies of ourselves into every worker.Fortunately, I think the solution is simple: when you want to spawn a worker with
ts-node, use ourts-node/registerendpoint to install us.