# Node.js on Vercel: What Works, What Breaks, and What to Use Instead

> Vercel supports Node.js, but only as serverless functions. Here is why Express and full-stack Node apps keep hitting walls and what developers use instead.
- **Author**: parth-kanpariya
- **Published**: 2026-04-28
- **Modified**: 2026-04-28
- **Category**: Alternatives
- **URL**: https://kuberns.com/blogs/vercel-node-js/

---

import { Image } from 'astro:assets';

Vercel is the first platform most Node.js developers try. It has a great developer experience, instant deployments from GitHub, and a free tier that makes experimentation easy.

But somewhere between "this works perfectly" and "why is my Express server timing out", things get complicated.

**Vercel does support Node.js.** For simple, stateless API endpoints, it genuinely works well. But the moment your Node.js backend needs persistent connections, WebSockets, background workers, or runs longer than 10 seconds, you are no longer working with the platform. You are fighting it.

This post covers exactly what happens when you try to run a real Node.js backend on Vercel, where it breaks, and what developers are using instead in 2026.

## What Node.js on Vercel Actually Means

Before looking at deployment steps and errors, it helps to understand the architecture. Most developers who run into problems do so because they expect Vercel to behave like a traditional Node.js host.

### Vercel Converts Your Node.js App into Serverless Functions

Vercel does not run a Node.js server. It runs **Vercel Functions**, a serverless execution model where each HTTP request triggers a short-lived function instance.

Here is what that means in practice:

- Each incoming request spins up a new function instance
- The function handles the request, then is destroyed
- No persistent server process runs between requests
- Memory and state are not preserved across invocations

For a simple REST endpoint that receives a request and returns JSON, this works perfectly. For anything that depends on a running server, things break in ways that are not always obvious.

### What the api/ Folder Convention Does to Your Express App

Vercel's Node.js runtime expects your code to live inside an `api/` folder. Each file in that folder becomes a separate serverless endpoint.

If you try to point Vercel at a traditional Express `server.js` entry point without restructuring, it will either show your source files in the browser or throw a deployment error.

Your Express app must be exported as a handler function, not started as a server:

```js
// api/index.js
const express = require('express');
const app = express();

app.get('/hello', (req, res) => {
  res.json({ message: 'Hello from Node.js on Vercel' });
});

// Export for Vercel, do NOT call app.listen()
module.exports = (req, res) => app(req, res);
```

No `app.listen()`. No `server.js`. Vercel manages the server lifecycle itself.

### The vercel.json Configuration Node.js Requires

Without a `vercel.json` file, Vercel may not correctly route requests to your Node.js handler. Here is the minimal config:

```json
{
  "version": 2,
  "builds": [
    { "src": "api/index.js", "use": "@vercel/node" }
  ],
  "routes": [
    { "src": "/api/(.*)", "dest": "api/index.js" }
  ]
}
```

This tells Vercel to build `api/index.js` using the Node.js runtime and route all `/api/*` traffic to it.

> **Skipping Vercel entirely?** If you want your Node.js server to run as-is without restructuring into serverless functions, see how [Kuberns auto-deploys your Node.js app from GitHub](https://kuberns.com/blogs/how-to-deploy-nodejs-app/) in under 5 minutes.

## How to Deploy a Node.js App on Vercel

Once you understand the serverless model, the deployment process is straightforward.

### Step 1: Structure Your Project for Vercel's Node.js Runtime

Your project should look like this:

```
my-node-app/
├── api/
│   └── index.js       # Your Express app exported as a handler
├── public/            # Static assets (optional)
├── vercel.json        # Routing and build config
├── package.json
└── .env               # Local only, never commit this
```

Install your dependencies as usual. Vercel reads `package.json` and installs them automatically during the build.

### Step 2: Configure vercel.json

Add the `vercel.json` shown above to your project root. If your app has multiple route groups, you can add them as separate entries in the `builds` and `routes` arrays.

For a Node.js app with a database connection, make sure your connection logic uses a cached client pattern. Vercel does not keep your function warm between requests, so a fresh connection attempt on every invocation is the default behaviour.

### Step 3: Connect Your GitHub Repo and Deploy

1. Push your project to GitHub
2. Go to [vercel.com](https://vercel.com) and click **Add New Project**
3. Import your repository
4. Vercel will auto-detect the framework. If it does not detect Node.js correctly, set the Framework Preset to **Other**
5. Click **Deploy**

Vercel builds your project and gives you a live URL. Preview deployments are created automatically for every pull request, which is one of Vercel's genuinely useful features for [CI/CD workflows and GitHub integration](https://kuberns.com/blogs/vercel-github-integration/).

### Step 4: Set Environment Variables on Vercel

Never hardcode secrets in your code. In the Vercel dashboard:

1. Go to your project settings
2. Open the **Environment Variables** tab
3. Add each key-value pair (for example: `MONGODB_URI`, `JWT_SECRET`, `PORT`)
4. Redeploy for the variables to take effect

Vercel supports separate environment variables for Production, Preview, and Development environments.

> **Already using GitHub for deployments?** Read how [Vercel GitHub integration works and where it breaks for full-stack teams](https://kuberns.com/blogs/vercel-github-integration/) before you commit to the workflow.

## Common Node.js Errors on Vercel (And Why They Happen)

These are the errors developers consistently report when running Node.js on Vercel. The causes are all rooted in the same serverless architecture constraint.

### Files Showing Instead of the App Running

**Why it happens:** Vercel cannot find a valid entry point. Without a `vercel.json` that defines your builds and routes, Vercel treats your project as a static site and serves the raw files.

The fix direction: Add a `vercel.json` with explicit `builds` pointing to your `api/index.js` using `@vercel/node`, and a `routes` entry directing all traffic there. If you need a persistent server instead of patching configs, [deploying Node.js on a container-based platform](https://kuberns.com/blogs/how-to-deploy-nodejs-app/) avoids this entirely.

### Function Timeout Errors on the Free Plan

**Why it happens:** Vercel Hobby plan limits serverless function execution to **10 seconds**. Any handler that takes longer is killed mid-execution. No error is returned to the user, and no retry happens.

The fix direction: Upgrade to Pro for a 300-second limit, or move workloads that run longer to a platform without execution time caps.

### WebSocket Connections Silently Failing

**Why it happens:** Vercel's serverless model does not support persistent connections. WebSocket handshakes are rejected. Socket.io, `ws`, and native WebSocket servers cannot run on Vercel regardless of configuration.

The fix direction: WebSockets require a persistent server process. Vercel is architecturally incompatible with them.

### Database Connection Pool Exhaustion

**Why it happens:** Every serverless function invocation opens a new database connection. Under moderate traffic, your MongoDB Atlas or Postgres instance runs out of available connections. You will see `MongoServerSelectionError` or `too many clients` errors in your logs.

The fix direction: Use connection caching within the function module scope to reuse connections across warm invocations. This reduces the problem but does not eliminate it, since Vercel may spin up hundreds of parallel instances under load.

### Background Jobs and Cron Tasks Not Running

**Why it happens:** Serverless functions respond to HTTP requests and then stop. There is no always-on process to run queues, workers, or scheduled tasks. Vercel Pro supports cron-triggered functions, but these are still one-shot invocations with a maximum duration, not persistent workers.

The fix direction: Background processing requires a persistent runtime. If your Node.js app has queues, workers, or scheduled jobs, serverless is the wrong execution model.

> **Running into these errors often?** See how teams move from broken serverless deployments to [AI-automated CI/CD pipelines that catch issues before they reach production](https://kuberns.com/blogs/best-ai-solutions-for-automating-code-deployments-and-cicd/).

## Where Vercel Falls Short for Node.js Backends

The errors above are symptoms of a deeper architectural mismatch. Here is what Vercel's serverless model does not support for full Node.js backends:

**No persistent server process.** Your app does not run continuously. It runs once per request, then stops. Any design pattern that depends on an always-on server (in-memory caches, connection pools, event emitters, background workers) breaks by default.

**Execution timeout.** 10 seconds on the free plan. 300 seconds on Pro (paid). An Express middleware chain hitting a slow database query, a file upload, or an external API with variable latency will regularly exceed these limits.

**No WebSocket support.** Real-time features simply do not work. This rules out collaborative tools, live dashboards, chat applications, streaming AI responses, and anything using socket.io or native WebSocket connections.

**Cold starts on low-traffic endpoints.** If your endpoint has not been called recently, the first request triggers a cold start. Node.js cold starts on Vercel are faster than Python, but still add latency that affects user experience on infrequently-used routes.

**Connection pool exhaustion at scale.** Postgres and MongoDB have connection limits. A serverless Node.js app that opens a new connection per invocation will exhaust those limits under real traffic. Workarounds exist, but they add complexity and do not fully solve the problem.

**No Docker or containerised deployments.** If your Node.js app uses a Dockerfile, Vercel will not build it. Vercel is not a container platform.

For simple stateless APIs, none of this matters. For anything beyond that, these are not minor inconveniences. They are architectural limits that cannot be configured away.

> **Looking for a platform built for full Node.js backends?** Compare the [best Vercel alternatives for developers and teams](https://kuberns.com/blogs/best-vercel-alternatives/) and see which ones support persistent servers, WebSockets, and background workers.

## The Faster Way to Run Node.js in Production is to Use Kuberns

[Kuberns](https://kuberns.com) runs your Node.js app as a **persistent container on AWS**, not as a serverless function. Your server stays running. Connections stay open. Workers run continuously. WebSockets work natively.

Here is what makes the deployment experience different.

### How the Kuberns AI Agent Detects Your Node.js Stack Automatically

When you connect your GitHub repository to Kuberns, the Agentic AI reads your project before you configure anything:

- It reads `package.json` to identify your Node version and dependencies
- It detects your framework: Express, NestJS, Fastify, Koa, or plain Node
- It identifies your build command (`npm run build`) and start command (`npm start` or `node server.js`)
- It detects the port your app listens on from your code or environment defaults
- It reads any existing `.env.example` or environment variable references

You do not need to fill in a build configuration form. The AI fills it in for you.

### Step-by-Step: Deploy Your Node.js App on Kuberns

**Step 1: Connect your GitHub repo**

Log in to [dashboard.kuberns.com](https://dashboard.kuberns.com), click **New Deployment**, and connect your GitHub account. Select the repository containing your Node.js app.

**Step 2: Review the auto-detected configuration**

Kuberns AI scans your project and pre-fills the deployment config:

- Runtime: Node.js (version detected from `package.json` or `.nvmrc`)
- Build command: auto-detected (e.g., `npm run build`)
- Start command: auto-detected (e.g., `node dist/server.js` or `npm start`)
- Port: auto-detected from your app code

You can override any field before deploying.

**Step 3: Add environment variables**

Add your production environment variables in the Kuberns dashboard (DATABASE_URL, API keys, secrets). These are encrypted and injected at runtime.

**Step 4: Click Deploy**

Kuberns builds your container, provisions infrastructure on AWS, and gives you a live HTTPS URL in under 5 minutes. Every subsequent push to your main branch triggers an automatic redeploy.

No `vercel.json`. No serverless function restructuring. No timeout limits. Your Express server runs exactly as it does locally.

> **Building a full-stack app, not just an API?** See how teams [deploy full-stack apps with AI-powered infrastructure](https://kuberns.com/blogs/deploy-full-stack-app-with-ai/) and get frontend, backend, and database running together from a single GitHub push.

<a href="https://dashboard.kuberns.com" target="_blank" rel="noopener noreferrer">
  <img src="https://kuberns-blogs.s3.ap-south-1.amazonaws.com/deploy-on-kuberns-bannner6.png" alt="Deploy Node.js on Kuberns" style={{ width: "100%", height: "auto" }} />
</a>

## Vercel Node.js vs Kuberns: Quick Comparison

| Feature | Vercel | Kuberns |
|---|---|---|
| Runtime model | Serverless functions | Persistent containers |
| Execution timeout | 10s (Hobby) / 300s (Pro) | No timeout |
| WebSocket support | No | Yes |
| Background workers | No (cron only on Pro) | Yes |
| Cold starts | Yes | No |
| Docker support | No | Yes |
| Auto stack detection | Partial | Full AI detection |
| Database connection pooling | Manual workaround required | Native persistent connections |
| CI/CD from GitHub | Yes | Yes |
| Free tier | Yes | Yes (free credits) |

> **Not sure which PaaS fits your team size and budget?** Read the [best PaaS providers comparison for 2026](https://kuberns.com/blogs/best-paas-providers/) to see how Kuberns, Vercel, Railway, and Render stack up on price, features, and scaling.

## Conclusion

Vercel is an excellent platform. For frontend frameworks, Next.js, static sites, and simple serverless APIs, it is one of the best tools available.

But Node.js on Vercel is serverless Node.js. That distinction matters more than most tutorials acknowledge.

If your Node.js app is a stateless REST API with fast endpoints and no persistent state requirements, Vercel works fine. Deploy it, use it, and move on.

If your app runs Express with middleware chains, connects to a database with a connection pool, uses WebSockets, runs background jobs, or has any endpoint that takes longer than 10 seconds, you will hit Vercel's limits quickly. Not because you are doing something wrong, but because the platform was not designed for that use case.

For full Node.js backends, [deploying a full-stack app with AI-powered infrastructure](https://kuberns.com/blogs/deploy-full-stack-app-with-ai/) on a container-based platform removes every one of those constraints. Kuberns auto-detects your stack, handles the infrastructure, and runs your app the way Node.js was designed to run.

<a href="https://dashboard.kuberns.com" target="_blank" rel="noopener noreferrer">
  <img src="https://kuberns-blogs.s3.ap-south-1.amazonaws.com/CTA_banner.png" alt="Deploy on Kuberns" style={{ width: '100%', height: 'auto', cursor: 'pointer' }} />
</a>

## Frequently Asked Questions

### Can you run Express.js on Vercel?

Yes, but not as a traditional server. Vercel wraps your Express app as a serverless function. This means each request spins up a new function instance. Express works for stateless REST APIs, but features that rely on persistent state, WebSockets, or long-running processes will not behave as expected.

### What is the Node.js timeout limit on Vercel?

On the Hobby (free) plan, Vercel serverless functions time out after 10 seconds. On the Pro plan, the limit is 300 seconds. Any Node.js operation that runs longer than the plan limit will be terminated mid-execution with no retry.

### Does Vercel support WebSockets for Node.js?

No. Vercel does not support WebSockets. Any Node.js app using socket.io, `ws`, or native WebSocket connections will fail on Vercel. If your app needs real-time communication, you need a platform that runs persistent server processes, such as Kuberns.

### Why are my Node.js files showing instead of running on Vercel?

This happens when Vercel cannot detect your project's entry point. It usually means your `vercel.json` is missing or misconfigured. You need to define a `builds` entry pointing to your `api/index.js` file using `@vercel/node`, and a `routes` entry to direct traffic to it.

### Can I use MongoDB with Node.js on Vercel?

Yes, but you will hit connection pool exhaustion quickly. Because Vercel spawns a new function instance per request, each invocation opens a fresh MongoDB connection. Under moderate traffic, you will exceed MongoDB Atlas's connection limits. Using a connection caching pattern helps, but does not fully solve the problem at scale.

### Can I run cron jobs or background tasks with Node.js on Vercel?

Vercel Pro and above supports scheduled cron functions via `vercel.json`, but these are still serverless invocations with a maximum duration. You cannot run persistent background workers, queues, or long-running jobs. For Node.js apps that need background processing, a container-based platform like Kuberns is more suitable. You can also read about [AI-powered solutions for automating deployments and CI/CD](https://kuberns.com/blogs/best-ai-solutions-for-automating-code-deployments-and-cicd/) to understand what a modern deployment pipeline looks like.

### What is the best alternative to Vercel for Node.js backends?

Kuberns is a strong alternative for full Node.js backends. It deploys your Express, NestJS, or Fastify app as a persistent container, not a serverless function. There are no execution timeouts, WebSockets work natively, background workers run continuously, and database connection pools stay open. You can deploy directly from GitHub in under 5 minutes.

---
- [More Alternatives articles](https://kuberns.com/blogs/category/alternatives/1/)
- [All articles](https://kuberns.com/blogs/)