Andrew
Walpole
Principal Web
Developer &
Engineering
Manager
Designer
Leader
Teacher
Learner
Maker
Listen along to this post as you read, or subscribe to the blog
Use Vite for JavaScript Libraries
More than once I’ve written some snazzy JavaScript code that I want to quickly turn into a sharable library, but the process of how to best and easily do that has bogged me down enough to drop the idea entirely.
In this post, I’ll walk through how you can build a set of JavaScript into a library provided in both ESM
and UMD
format using vite.
There’s not a lot of secret sauce here, in fact, most of what I’m about to show you is lifted right from the vite docs. But I find it helpful when 3rd-party people can verify a technique.
Setup
Starting from a fresh directory we need to:
- Initialize the project
- Install vite
- Setup some files
npm init --yes
npm i vite --save-dev
mkdir lib && touch lib/main.js vite.config.js index.html
lib/main.js
will be your main library entry point that vite will compile and index.html
is actually optional, but what it’s really great for is showing an example of how you use your library, which tends to be a small but nagging pain point in building a library that you want folks to use.
Configure
Let’s now configure vite to build your library. To do that we need to edit two files: vite.config.js
and package.json
.
vite.config.js
const path = require('path')
const { defineConfig } = require('vite')
module.exports = defineConfig({
build: {
lib: {
entry: path.resolve(__dirname, 'lib/main.js'),
name: 'YOUR_LIBRARY_NAME',
fileName: (format) => `YOUR_LIBRARY_NAME.${format}.js`
}
}
});
The magic here is that vite has a library mode, and that’s exactly what we’re using. By default it will build your entry point into ESM
and UMD
formats into a /dist
folder.
package.json
{
"name": "YOUR_LIBRARY_NAME",
"version": "1.0.0",
"description": "A GOOD DESCRIPTION",
"files":["dist"],
"main":"./dist/YOUR_LIBRARY_NAME.umd.js",
"module":"./dist/YOUR_LIBRARY_NAME.es.js",
"exports": {
".": {
"import": "./dist/YOUR_LIBRARY_NAME.es.js",
"require": "./dist/YOUR_LIBRARY_NAME.umd.js"
}
},
"scripts": {
"dev": "vite",
"build": "vite build",
"preview": "vite preview"
},
...
}
We wrap-up config by telling your package.json
where your compiled library will live. This is not technically required, but if someone installs your library as a dependency, npm/yarn will know where to pull code from.
Write the library
Your lib/main.js
file is where you will export all of your code from. If your library is simple you could put all of the code right in there, or if it’s more complex with multiple files, it just needs to import and reexport all the things you want to bundle into the library. It’s also worth noting that if you import external dependencies into your library files they will also get bundled together in the final output.
As an example, I have recently created a wrapper library for petite-vue called PV. You can check out the library code as well as the index.html
to see how I’m using that to test and build a demo of the library.
Build the library
npm run build
or vite build
will bundle up your library into /dist
while npm run dev
or vite
will start a server to view your index.html
which makes it easy to test things out as you build the library.
And that’s all there is to it! If you need to further customize your library, vite is really just exposing a proxy for rollup, and you can add rollupOptions
to your vite.config.js
to customize your build settings, like multiple entry points.