Pre-bundle your Meteor project using tsup
. Acts as a replacement for Meteor's
official typescript
Atmosphere package.
This plugin feeds a bundle produced by tsup
into Meteor, including source maps. It works essentially the same way as
the official typescript
package. But it's faster, despite the extra build step.
We've intentionally opted to running the tsup watcher separate from the Meteor runtime as long-running child processes
created by Meteor has a tendency to become unstable after a while. You do need to run the tsup
watcher yourself.
Packages like concurrently
help make this a better experience.
This package is intended only to speed up Meteor server restarts. If you're frustrated with slow updates when working
with client-side code, you should probably look at meteor-vite
drastically improves front-end developer experience through lightning fast HMR. ⚡
Install tsup
and jorgenvatle:tsup
. Optionally also concurrently
to run the tsup
watcher alongside Meteor.
# Install the build plugin
meteor add jorgenvatle:tsup
# If you're using Meteor v3, install the beta version instead
# meteor add jorgenvatle:tsup@2.0-beta.3
# Install npm dependencies
meteor npm i -D tsup concurrently
Create a tsup.config.ts
config file in your Meteor project's root directory.
// tsup.config.ts
import { defineConfig } from 'tsup';
export default defineConfig({
target: 'node14', // For Meteor v3 you'll probably want to use 'node21'
entry: ['./server/main.ts'],
outDir: 'server/_bundle',
skipNodeModulesBundle: true,
sourcemap: true,
platform: 'node',
outExtension: ({ format }) => ({ js: '.server.js' }),
format: "cjs",
loader: {
// Omit any Vue components from the server bundle.
'.vue': 'empty',
},
esbuildPlugins: [
// Prevent ESBuild from trying to resolve Meteor packages.
{
name: 'external-meteor',
setup(build) {
build.onResolve({ filter: /^meteor\// }, (args) => ({
path: args.path,
namespace: 'meteor',
external: true,
}));
}
}
]
})
Update your Meteor server's mainModule
path in your package.json
. And update your start script to also launch tsup
.
// package.json
{
"name": "my-meteor-project",
"scripts": {
"start": "concurrently npm:start:tsup npm:start:meteor",
"start:meteor": "meteor run",
"start:tsup": "tsup --watch"
},
"meteor": {
"mainModule": {
"server": "server/main.js", // This should be a js file. Not .ts. See below.
"client": ...,
}
},
}
Create a server/main.js
file to import your TSUp build output.
// server/main.js
import './_bundle/main.server.js';
Now, just launch Meteor using your updated start script. And you're all set.
meteor npm start
When working with larger Meteor projects, the Meteor file watcher can become excessively sluggish. Meteor processes TypeScript modules individually. This is not only slow, but it also comes with a few other caveats.
Particularly, some modules might not be compiled without emitting any sort of warning message. Leading to issues at runtime where some modules might just not exist in your bundle. This can be incredibly tricky to debug, especially for larger applications.
MIT