DEV Community

Alexander Voll
Alexander Voll

Posted on • Originally published at codesphere.ghost.io on

Migrating Node.js to Bun: Really a drop in replacement?

Intro

Migrating Node.js to Bun: Really a drop in replacement?

Over the last few months, Bun has sparked interest in the web development community, claiming for it to be a drop in replacement for Node.js that is much faster at the same time.

We work with Node.js all the time here in the Codesphere Marketing team and wanted to put that to the test.

We tried out, if Bun would really be able to be dropped into the existing repo for our main page and if we could finally ditch Node.

Buns Bundler

Watch mode

Building the code with bun is actually really easy. After installing bun via npm (What the bun team claims will be our last npm command ever), executing bun run index.js instead of node index.js worked fairly well, except for the websockets we use for tracking. More on that later.

What we really liked about it was the —watch flag provided by Bun, which essentially eliminated the need for a watcher like nodemon. To run and then watch a specific file, simply run bun —watch run ./your-file.js. For more complex setups, a watcher might still be necessary, however for our use case, this worked just fine as we use Tailwind for our CSS and compile them that way and our EJS templates get built on the fly when a user accesses one of our pages.

Entrypoints

To be able to build more than one file at the same time, you need to configure entrypoints for the bundler to go through and bundle your code into usable pieces. Since we use EJS and JS, we only need to bundle our JS code. We created a bundling script called bundle.js in the root of our project which we then simply run using bun run ./build.js.

This bundles the files according to the configuration.

Seems easy enough, right? Well… yes and no.

While this works really well, Bun currently doesn’t allow for naming entrypoints like Webpack does. This meant for us to actually be able to use Buns Bundler, we needed to write some extra code to be able to give the right names to our bundles so everything would work without us having to touch all of our EJS templates.

We ended up with this for the configuration:

const path = require('path');

async function buildProject() {
    const entrypoints = [
        "./src/js/features/index.js",
        "./src/js/global/index.js",
        "./src/js/home/index.js",
        "./src/js/main/index.js",
        "./src/js/pricing/index.js",
        "./src/js/tracking/index.js",
    ];

    for (let entry of entrypoints) {
        const dirName = path.basename(path.dirname(entry));

        await Bun.build({
            entrypoints: [entry],
            outdir: './public/js',
            minify: true,
            naming: `${dirName}.[ext]`
        });
    }
}

buildProject();
Enter fullscreen mode Exit fullscreen mode

Installing Dependencies

Using the Bun package manager to install packages worked just as expected. Simply run bun install to install any npm package. No issues here!

The Websocket issue

We work with Websockets for our UX tracking. Our current server setup features an Express server that uses the wslib package to handle our Websocket operations.

This unfortunately didn’t work together with bun. This left us to handling the Websockets with Bun and leaving the rest to Express which also isn’t a very clean solution.

If we were to implement Bun into our production system, this would essentially mean we would need to refactor our server. For a smaller website project like ours this might be sufficient but depending on the size of the project, this might become a daunting task.

However, Bun doesn't promise to be an Express and wslib replacement, rather a Node replacement. Depending on your setup, you will need some time for configuration though.

Conclusion

In our little migration experiment, we noticed that especially build times were A LOT faster than on our current setup using Node and Webpack in combination with nodemon.

Bun is a great and very fast tool and while most tasks worked fine, not all did. Depending on your use case, you might be able to just drop in and get going with Bun but depending on your installed packages, you might need to reconfigure some things to get going.

Now, is Bun a drop in replacement for Node?

Well, this is hard to answer. We would still say yes, as most things worked just fine and you can't expect Bun to replace each and every package you have installed.

We will definitely be considering Bun for our next project. This time not as a drop in replacement though but rather to start out with it from the beginning!

Top comments (0)