# The Current Landscape for Next.js Real Time in 2026#
"Next.js real time" usually means one of four product needs: chat, live dashboards, notifications, or collaborative editing. Each of those has different requirements for latency, fan-out, ordering, delivery guarantees, and security.
Next.js itself does not provide a single built-in real-time transport. You choose a transport and then fit it into Next.js constraints: serverless timeouts, edge runtime limitations, connection limits, and how you handle auth and multi-region delivery.
ℹ️ Note: This comparison focuses on three practical choices that ship today in production: WebSockets, Server-Sent Events (SSE), and Supabase Realtime. WebRTC can be relevant for audio and video, but it is a different problem space.
If you are unsure which runtime you are deploying to, start here: Next.js Edge Runtime vs Node.js Runtime on Vercel and Cloudflare. Runtime choices directly impact whether long-lived connections are even possible.
# Quick Comparison Table#
| Criteria | WebSockets | SSE | Supabase Realtime |
|---|---|---|---|
| Direction | Bidirectional | Server to client only | Bidirectional channels and database change feeds |
| Transport | Single TCP connection upgraded from HTTP | Standard HTTP stream | WebSockets to Supabase Realtime service |
| Browser support | Excellent | Excellent | Excellent |
| Fits serverless and edge | Usually no for hosting inside Next.js | Sometimes, but often fragile on serverless | Yes, because the long-lived connection is not hosted in your Next.js app |
| Scaling model | Harder, needs pub-sub and sticky sessions | Easier than WS for fan-out, still needs state handling | Managed scaling, depends on Supabase plan and architecture |
| Auth complexity | Medium to high | Medium | Medium, integrates with Supabase Auth and JWT |
| Typical latency | Low | Low to medium | Low to medium, depends on region and load |
| Best for | Chat, presence, multiplayer-like interactions | Live dashboards, notification feeds, progress updates | Rapid development with Postgres-backed events and channels |
| Biggest pitfall | Hosting and horizontal scaling | Not bidirectional and can be buffered by proxies | Lock-in and cost surprises at scale |
# What Actually Matters in Real-Time Systems#
Picking a protocol is not the first decision. The first decision is the interaction model.
Decision criteria that change the outcome#
| Question | Why it matters | Strong signal to pick |
|---|---|---|
| Do clients need to send events frequently? | If yes, server to client only streams are awkward | WebSockets or Supabase channels |
| Is your source of truth Postgres? | If yes, database change feeds remove a lot of glue code | Supabase Realtime |
| How many concurrent connections? | Costs and architecture explode with long-lived connections | SSE for broadcast, managed realtime for speed |
| Do you need ordering and idempotency? | Real-time without dedupe creates double updates | Any option, but must add event IDs and replay handling |
| Are you on Vercel serverless or edge? | Long-lived connections may not be supported | SSE only if tested, or external WS provider |
| Do you need presence and typing indicators? | Requires fast bidirectional messages | WebSockets or Supabase channels |
| Is multi-region required? | Latency and cross-region sync become the main issue | Managed services or global pub-sub |
🎯 Key Takeaway: The best "Next.js real time" solution is the one that matches your interaction model and hosting constraints, not the one with the lowest latency on paper.
# Option 1: WebSockets in Next.js#
WebSockets provide a persistent, bidirectional connection. That makes them ideal for interactive workloads: chat, presence, collaborative cursors, and anything where the client is not only consuming updates but also sending small events frequently.
The hosting reality: where WebSockets actually live#
If you deploy Next.js to serverless functions, you generally should not host WebSocket servers inside your Next.js app. Serverless is designed for short-lived requests, not long-lived connections. Even when you can technically open a socket, you hit practical issues: cold starts, connection limits, timeouts, and no guarantee the same instance handles the same client later.
In practice, WebSockets for Next.js apps usually live in one of these places:
| Hosting approach | Pros | Cons | Typical use |
|---|---|---|---|
| Dedicated Node server (VPS, container, Kubernetes) | Full control, predictable behavior | You own scaling, patching, and uptime | Serious chat, presence, collaboration |
| Managed WS provider | Fast setup, scales well | Vendor cost, vendor API | Products needing predictable realtime without DevOps |
| "Hybrid" with Next.js for HTTP and separate WS service | Best of both worlds | More moving parts | Most production setups |
Minimal WebSocket server example#
Keep the WebSocket server separate from Next.js if you are on serverless. This example uses ws on Node.
// server.js
import http from "http";
import { WebSocketServer } from "ws";
const server = http.createServer();
const wss = new WebSocketServer({ server });
wss.on("connection", (socket) => {
socket.on("message", (raw) => {
const msg = raw.toString();
wss.clients.forEach((client) => client.send(msg));
});
});
server.listen(8080);This is intentionally simple. A production version needs authentication, per-room routing, message validation, and rate limiting.
Scaling WebSockets: the hidden work#
A single WebSocket process works until it does not. The common inflection point is when you need horizontal scaling. At that point, you need a shared pub-sub layer so clients connected to different instances still receive the same events.
Typical architecture:
- WebSocket nodes handle connections.
- A pub-sub system fans out events: Redis PubSub, Redis Streams, NATS, Kafka, or managed equivalents.
- A shared store holds presence and room membership, or you implement consistent hashing.
The reason this matters: chat might be 1 message per second per active user, but presence and typing often multiply your event volume. A team chat with 5,000 concurrent users can easily generate tens of thousands of small events per minute when you include typing, read receipts, presence, and retries.
Auth for WebSockets in Next.js#
The safest pattern is to issue a short-lived token from Next.js over HTTPS, then validate it during the WebSocket handshake. Use the same provider you use for your web sessions.
If you need a practical overview of auth choices in Next.js, including Supabase and other common options, use: Next.js authentication guide: NextAuth vs Clerk vs Supabase.
⚠️ Warning: Do not trust "roomId" or "userId" sent by the client over WebSocket messages. Treat every message like an API request: validate auth, authorize access to the room, and enforce rate limits.
# Option 2: Server-Sent Events (SSE) in Next.js#
SSE uses a standard HTTP response that stays open and streams events. The client receives events, but it cannot send events back on the same connection. That makes SSE excellent for "push-only" needs: dashboards, notification feeds, job progress, and streaming logs.
Why SSE often wins for dashboards and notifications#
SSE is simple:
- Works over HTTP and is proxy-friendly.
- Automatic reconnection is built into the browser EventSource API.
- One-way nature reduces complexity and abuse surface area.
For many products, dashboards are read-heavy. If you have 10,000 dashboard viewers and only a handful of writers, SSE is often cheaper and easier than WebSockets because your servers do not need to track bidirectional state.
SSE caveats that matter in production#
SSE is still a long-lived connection. That means your hosting platform must support streaming responses reliably. Some serverless environments buffer responses, which breaks real-time streaming. You must test on your target platform.
If you are deploying to edge runtimes, confirm streaming support and timeouts. The runtime implications are covered here: Next.js Edge Runtime vs Node.js Runtime on Vercel and Cloudflare.
SSE route handler example in Next.js#
This example shows a basic SSE endpoint. It does not include a real event source, but it demonstrates correct headers and periodic heartbeats.
// app/api/events/route.js
export async function GET() {
const encoder = new TextEncoder();
const stream = new ReadableStream({
start(controller) {
const send = (event, data) => {
controller.enqueue(encoder.encode(`event: ${event}\n`));
controller.enqueue(encoder.encode(`data: ${data}\n\n`));
};
send("connected", "ok");
const interval = setInterval(() => {
send("heartbeat", String(Date.now()));
}, 15000);
// No clean shutdown shown here for brevity
},
});
return new Response(stream, {
headers: {
"Content-Type": "text/event-stream",
"Cache-Control": "no-cache, no-transform",
Connection: "keep-alive",
},
});
}Client side:
const es = new EventSource("/api/events");
es.addEventListener("heartbeat", (e) => console.log(e.data));Scaling SSE#
SSE scales well for broadcast-style updates, but you still need an event source that can fan out. The common patterns:
- Poll your database and stream deltas to clients.
- Consume from a queue or pub-sub and stream to connected clients.
- Use a managed pub-sub and attach SSE as the delivery mechanism.
SSE becomes awkward when you need high-frequency upstream messages from clients. You can combine SSE plus regular HTTPS POST requests for client actions, but at that point WebSockets may be simpler.
💡 Tip: For dashboards, reduce event volume by sending aggregated updates every 250 to 1000 milliseconds, not per-row changes. Users perceive "real time" as anything under ~1 second for most business dashboards, and you save significant compute and bandwidth.
# Option 3: Supabase Realtime with Next.js#
Supabase Realtime gives you two main real-time capabilities:
- 1Postgres change feeds for insert, update, delete events.
- 2Realtime channels for broadcasting messages, presence, and state sync.
The big advantage for Next.js is hosting: the long-lived WebSocket connection is between the browser and Supabase, not between the browser and your Next.js deployment. That avoids the biggest operational pain point of WebSockets on serverless platforms.
Where Supabase Realtime fits best#
Supabase Realtime is a strong fit when:
- Your source of truth is Postgres.
- You want "database-driven" real-time updates without building a pub-sub layer.
- You need auth integrated with database permissions via Row Level Security.
- You want to ship quickly and accept some vendor coupling.
It is especially effective for internal tools, SaaS admin panels, and early-stage products where time-to-market matters more than custom scaling architecture.
Supabase Realtime subscription example#
This example subscribes to Postgres changes for a table. Keep authorization in mind: RLS policies still apply.
// subscribe.js
import { createClient } from "@supabase/supabase-js";
const supabase = createClient(
process.env.NEXT_PUBLIC_SUPABASE_URL,
process.env.NEXT_PUBLIC_SUPABASE_ANON_KEY
);
const channel = supabase
.channel("orders-feed")
.on(
"postgres_changes",
{ event: "*", schema: "public", table: "orders" },
(payload) => console.log(payload)
)
.subscribe();For chat-like features, channels are often a better fit than raw database change feeds, because chat needs message validation, per-room access checks, and sometimes message transformations.
Auth and authorization with Supabase Realtime#
Supabase’s real advantage is consistent auth across:
- Client SDK session handling
- JWT claims
- Postgres Row Level Security policies
That said, you still need to design authorization carefully. A common mistake is subscribing to broad table change feeds and filtering on the client. The correct approach is to enforce access at the database level using RLS and query patterns that scope data per tenant and per user.
If you need to compare auth approaches in Next.js before committing to Supabase, use: Next.js authentication guide: NextAuth vs Clerk vs Supabase.
Cost and scaling considerations#
Supabase Realtime cost is usually not the first cost you hit. The bigger drivers are:
- Number of connected clients
- Message rate and payload size
- Database workload caused by writes and triggers
- Egress bandwidth
If your product becomes event-heavy, you need to measure and budget based on actual usage. For example, presence updates every 2 seconds for 5,000 users is 2,500 updates per second if you model presence naïvely. Even if each update is small, you pay in bandwidth and processing.
# Feature-by-Feature Trade-Offs That Decide the Winner#
This is where most teams make the real decision: hosting, scalability, auth, and cost are not abstract, they become day-two problems.
Hosting constraints#
| Constraint | WebSockets | SSE | Supabase Realtime |
|---|---|---|---|
| Works on typical serverless Next.js hosting | Usually no | Sometimes, must test | Yes |
| Works across proxies and CDNs | Sometimes tricky | Usually yes | Usually yes |
| Operational burden | High if self-hosted | Medium | Low to medium |
If you cannot run long-lived connections in your Next.js environment, WebSockets and SSE inside Next.js are the wrong starting point. That pushes you toward managed realtime or a separate realtime service.
Scalability and fan-out#
| Scaling concern | WebSockets | SSE | Supabase Realtime |
|---|---|---|---|
| Horizontal scaling | Needs pub-sub | Needs pub-sub | Managed |
| Broadcast to many users | Good with pub-sub | Very good | Good, depends on plan and patterns |
| Presence and per-room state | Custom code | Not ideal | Built-in primitives via channels |
Authentication and access control#
| Auth requirement | WebSockets | SSE | Supabase Realtime |
|---|---|---|---|
| Use existing Next.js session cookies | Possible, but handshake needs care | Possible | Usually separate session using Supabase client |
| Per-room authorization | Custom | Custom | Channel policies and RLS-backed data patterns |
| Multi-tenant security | Possible, but you must build it | Possible, but you must build it | Strong if RLS is designed correctly |
Cost model and common surprises#
| Cost driver | WebSockets | SSE | Supabase Realtime |
|---|---|---|---|
| Idle connections | You pay for memory and connection slots | Similar | Paid indirectly via plan limits and bandwidth |
| Fan-out | Pub-sub infra and network | Pub-sub and network | Managed, but still network and plan limits |
| Engineering cost | Highest | Medium | Lowest initially |
# Decision Criteria by Use Case#
This section maps product needs to a concrete choice. These are not theoretical recommendations; they reflect common production patterns and failure modes.
Chat apps#
Chat is bidirectional. You need message send, delivery acknowledgements, typing indicators, presence, read receipts, and moderation workflows.
| Requirement | Recommended option | Why |
|---|---|---|
| Bidirectional messages | WebSockets or Supabase channels | SSE alone is not enough |
| Presence and typing | WebSockets or Supabase channels | Requires frequent low-latency upstream events |
| Large scale rooms | WebSockets with pub-sub | You need control over fan-out and throttling |
| Fast MVP with Postgres | Supabase Realtime | Less glue code, fast iteration |
If your Next.js app is on serverless hosting, chat almost always ends up as a separate realtime service. Supabase is a good option if your data model fits Postgres and you accept managed constraints.
Live dashboards#
Dashboards are mostly server to client. They benefit from simple broadcast updates and resilient reconnection.
| Requirement | Recommended option | Why |
|---|---|---|
| Live KPIs and charts | SSE | Simple, reliable, low overhead |
| Updates from DB writes | Supabase change feeds or SSE fed by queue | Depends on whether you want DB-driven realtime |
| Strict low latency under 200 ms | WebSockets or managed realtime | SSE can still be fast, but buffering can happen |
For dashboards, you typically get better ROI by reducing event volume than by shaving latency. The real metric is user-perceived freshness, not protocol choice.
Notifications#
Notifications are often bursty and do not require strict ordering. They also frequently need offline support, which points to queues and persistence.
| Requirement | Recommended option | Why |
|---|---|---|
| In-app notification stream | SSE | Great fit for server push |
| Cross-device and offline | SSE plus persistence | Store notifications and replay on reconnect |
| Mobile push integration | Separate push system | Web push and APNs are separate from realtime transports |
A common pattern is: persist notifications to DB, stream new notifications in real time, and on reconnect fetch missed ones using Last-Event-ID or a timestamp.
Collaborative editing#
Collaboration is the hardest. You need concurrency control and conflict resolution, not just transport.
| Requirement | Recommended option | Why |
|---|---|---|
| Cursor and presence | WebSockets or Supabase channels | High-frequency state sync |
| Document updates with conflict resolution | WebSockets plus CRDT or OT | Transport is the easy part |
| MVP with low concurrency | Supabase channels | Good enough before you hit hard scaling needs |
⚠️ Warning: Collaborative editing fails when teams treat it as "real-time messaging." You need a data model for merges and conflicts. Without CRDT or OT, users will overwrite each other even if your transport is perfect.
# Observability: How to Keep Next.js Real Time Stable#
Real-time systems are sensitive to small issues: reconnect storms, message amplification, and silent disconnects. If you do not measure, you will only see the problem when users complain.
Track these minimum metrics:
| Metric | Why it matters | Typical symptom |
|---|---|---|
| Concurrent connections | Capacity and cost planning | Sudden spikes during releases |
| Reconnect rate | Detect instability | Connection flapping or proxy timeouts |
| Message rate per user | Abuse and runaway clients | Costs grow linearly, UX degrades |
| Event delivery lag | Real-time freshness | Dashboards show stale values |
| Error rates per channel or room | Permissions and data issues | Users missing updates |
Instrument both server and client. Client-side logs are often the only way to understand mobile network behavior.
A practical baseline for logs, metrics, and tracing is here: Web app observability guide: logging, metrics, tracing.
💡 Tip: Add a unique
eventIdto every event and store the last processedeventIdin memory. It prevents double-applying updates after reconnect, which is one of the most common real-time bugs in production.
# Our Practical Recommendation#
If your goal is to ship "Next.js real time" features quickly with minimal DevOps, Supabase Realtime is hard to beat, especially for Postgres-backed dashboards and early-stage chat. You get managed WebSockets, integrated auth, and database-driven eventing without building a pub-sub layer.
If you need deep control, predictable scaling under heavy bidirectional traffic, or you are building collaboration at scale, you will eventually outgrow simplistic setups. WebSockets with a dedicated realtime service and a proper pub-sub backbone becomes the long-term architecture.
If your use case is mostly broadcast updates, SSE is the simplest and often the most reliable. It is also easier to secure and observe because the server is the only writer on the stream.
# Key Takeaways#
- Choose based on interaction model: bidirectional needs point to WebSockets or Supabase channels, broadcast-only feeds often fit SSE.
- Do not host WebSockets inside serverless Next.js route handlers for production; run a separate realtime service or use a managed provider.
- Use Supabase Realtime when Postgres is your source of truth and you want faster delivery with integrated auth and RLS.
- For dashboards, optimize event frequency and aggregation first; users rarely need per-row updates faster than 1 second.
- Invest in observability early: track concurrent connections, reconnect rate, message rate, and delivery lag to prevent silent failures.
# Conclusion#
WebSockets, SSE, and Supabase Realtime can all power Next.js real time features, but they solve different product problems and come with different operational costs. Pick the simplest option that meets your interaction model and hosting constraints, then add the missing pieces: authorization, replay and idempotency, and observability.
If you want help choosing the right architecture or implementing a production-grade realtime layer in Next.js, contact Samioda and we will review your use case, hosting setup, and scaling goals, then propose an implementation plan you can ship confidently.
FAQ
Founder & Senior Developer at Samioda. 8+ years building React, Next.js, Flutter and n8n automation solutions for clients across Europe.
More in Web Development
All →Next.js Rate Limiting & Bot Protection: Patterns for APIs, Server Actions, and Edge (2026 Guide)
Practical Next.js rate limiting patterns for Route Handlers, Server Actions, and Edge runtime — with token bucket strategies, Redis-backed limits, WAF/CDN rules, monitoring, and false-positive mitigation.
Next.js SaaS Onboarding Checklist: Accounts, Permissions, Emails, and Trials (App Router, 2026)
A production-ready Next.js SaaS onboarding checklist covering authentication, organizations, invites, RBAC, transactional emails, and trial-to-paid conversion with practical patterns, libraries, and pitfalls.
React Query at Scale: Cache Invalidation, Pagination, and Mutation Patterns for Real Apps
React Query cache invalidation best practices for real-world apps: scalable query key design, invalidation strategy, optimistic updates, infinite queries, and background refetching in Next.js App Router.
Need help with your project?
We build custom solutions using the technologies discussed in this article. Senior team, fixed prices.
Related Articles
Next.js + Supabase SaaS Starter Architecture (App Router): Auth, RLS, Billing, and Multi-Tenancy
A production-ready blueprint for a Next.js App Router + Supabase SaaS starter architecture: auth, Postgres data model, RLS policies, Stripe billing, and multi-tenant organization design with concrete examples.
Next.js Edge Runtime vs Node.js Runtime (Vercel and Cloudflare): What to Run Where
A practical decision framework for choosing Next.js Edge Runtime vs Node.js Runtime in 2026, with real examples, limitations, and a final use-case matrix.
Next.js + Supabase RLS for Multi‑Tenant SaaS: Policies, Roles, and Safe Data Access
A practical guide to Next.js App Router and Supabase Row Level Security for multi-tenant SaaS: table design, policies, roles, server-side access patterns, common pitfalls, and a deployment checklist.