APIs are the backbone of modern web applications, allowing different systems to communicate seamlessly. I’ve always relied on Node.js and frameworks like Express.js for API development, but recently, I discovered Bun, a high-performance JavaScript runtime that’s changing the game.
Bun is designed as a drop-in replacement for Node.js, but what makes it stand out is its speed, built-in utilities, and simplified API development process. After experimenting with it, I found that setting up an API with Bun is incredibly smooth and efficient. In this blog, I’ll walk you through the process of creating API endpoints using Bun—from installation to handling GET and POST requests. 🚀
1. What is Bun?
Bun, a modern JavaScript runtime built for speed and efficiency. Unlike Node.js, which often requires additional frameworks and tools, Bun comes with everything I need right out of the box.
What makes Bun stand out for me:
A Built-in HTTP Server – No need for external frameworks like Express.js.
Native Support for Fetch API – Simplifies API development.
Faster Execution – Up to 4x
faster than Node.js.
Built-in Package Manager – Eliminates the need for npm or yarn.
With these features, Bun is quickly becoming my go-to choice for building high-performance APIs with minimal setup.
2. Installing Bun
Before we start building our API, we need to install Bun. Open a terminal and run:
curl -fsSL https://bun.sh/install | bash
Once installed, verify the installation with:
bun --version
This should return the installed Bun version, confirming that it is successfully set up on your system.
3. Setting Up a Bun Project
To start a new project, create a directory and initialize it with Bun:
mkdir bun-api && cd bun-api
bun init
This will generate a package.json
file, similar to npm init
. Now, we are ready to build our API server.
4. Creating a Simple Bun Server
Unlike Node.js, where you would typically use Express.js or Fastify, Bun has a built-in HTTP server. Let's create a file named server.ts
(or server.js
if you're using JavaScript) and write the following code:
import { serve } from "bun";
const server = serve({
port: 3000,
fetch(req) {
const url = new URL(req.url);
if (url.pathname === "/") {
return new Response("Welcome to Bun API!", { status: 200 });
}
if (url.pathname === "/api/hello") {
return new Response(JSON.stringify({ message: "Hello from Bun!" }), {
status: 200,
headers: { "Content-Type": "application/json" },
});
}
return new Response("Not Found", { status: 404 });
},
});
console.log(`Server running on http://localhost:${server.port}`);
Breaking Down the Code:
import { serve } from "bun";
– Imports Bun’s built-in server module.serve({...})
– Starts an HTTP server on port 3000.fetch(req)
– Handles incoming HTTP requests.URL(req.url)
– Parses the request URL.Routing:
/
returns a plain text response./api/hello
returns a JSON response.Any other route returns a 404 Not Found response.
5. Running the Bun API Server
Start the server with:
bun run server.js
Now, visit http://localhost:3000/api/hello
in your browser or test it with curl
:
curl http://localhost:3000/api/hello
You should see the JSON response:
{"message": "Hello from Bun!"}
6. Handling POST Requests in Bun
APIs often need to handle POST requests to accept data from clients. Let's modify our server.js
file to support a POST endpoint:
const server = serve({
port: 3000,
async fetch(req) {
const url = new URL(req.url);
if (req.method === "POST" && url.pathname === "/api/data") {
const body = await req.json();
return new Response(JSON.stringify({ received: body }), {
status: 200,
headers: { "Content-Type": "application/json" },
});
}
return new Response("Not Found", { status: 404 });
},
});
console.log(`Server running on http://localhost:${server.port}`);
How It Works:
Checks if the request method is
POST
and the path is/api/data
.Reads the JSON body using
await req.json()
.Returns the received data as a JSON response.
Testing the POST Request:
Send a POST request using curl
:
curl -X POST http://localhost:3000/api/data \
-H "Content-Type: application/json" \
-d '{"name": "Bun"}'
Response:
{"received":{"name":"Bun"}}
This confirms that Bun successfully processes POST requests and responds with the received data.
7. Structuring the Bun API Project
For larger projects, it’s best to organize your files properly:
bashCopyEditbun-api/
│── server.js # Main entry point
│── routes/
│ ├── hello.js # /api/hello route
│ ├── data.js # /api/data route
│── package.json
│── tsconfig.json # (Optional) TypeScript config
Modify server.js
to import these routes:
import { serve } from "bun";
import helloRoute from "./routes/hello";
import dataRoute from "./routes/data";
const server = serve({
port: 3000,
async fetch(req) {
const url = new URL(req.url);
if (url.pathname === "/api/hello") return helloRoute(req);
if (url.pathname === "/api/data" && req.method === "POST") return dataRoute(req);
return new Response("Not Found", { status: 404 });
},
});
console.log(`Server running on http://localhost:${server.port}`);
Now, each route can be managed in its own file, improving maintainability.
8. Conclusion
Bun is revolutionizing the way we build APIs by offering speed, simplicity, and built-in utilities that eliminate the need for extra dependencies. With its native HTTP server, Fetch API support, and blazing-fast performance, it’s a solid choice for modern backend development.
As I explored Bun, I found that it makes API development quicker and more efficient, and I’m excited to see how it evolves. If you haven’t tried it yet, now’s the perfect time to dive in and experience the difference. 🚀
Key Takeaways:
✔️ Bun is a fast, modern alternative to Node.js.
✔️ It has a built-in HTTP server with serve()
.
✔️ API development with Bun is simpler and faster than using Express.js.
✔️ It supports both GET and POST requests with minimal code.
If you're looking for a high-performance JavaScript runtime, Bun is worth trying! 🚀