Echtzeit-Kommunikation ist 2026 kein Nice-to-have mehr — sie ist Standard. Live-Chats, kollaborative Editoren, Dashboards mit Push-Updates: Nutzer erwarten, dass sich die UI sofort aktualisiert. Claude Code kennt das WebSocket-Ökosystem in- und auswendig und generiert produktionsreifen Socket.io-Code in Sekunden.
In diesem Guide zeigen wir, wie du WebSockets und Socket.io mit Claude Code 2026 einsetzt — von den Grundlagen bis zur gesicherten Echtzeit-App mit Räumen und Auth-Middleware.
1. WebSocket-Grundlagen vs. Socket.io
Bevor wir in den Code einsteigen, die wichtigste Frage: Wann nutzt du natives WebSocket, wann Socket.io?
| Feature | Natives WebSocket | Socket.io |
| Browser-Support | ✓ Alle modernen Browser | ✓ + automatisches Fallback |
| Reconnect-Logik | ✗ Muss selbst gebaut werden | ✓ Eingebaut |
| Räume & Namespaces | ✗ Nicht vorhanden | ✓ Nativ unterstützt |
| Event-System | Nur message-Events | Custom Events à la EventEmitter |
| Middleware | ✗ Keine | ✓ Auth, Rate-Limiting etc. |
| Overhead | Minimal | ~20 KB extra Client-Bundle |
Faustregel: Für einfache 1:1 Streams (z.B. Server-Sent-Events reichen nicht) nutze natives WebSocket. Für alles mit mehreren Nutzern, Räumen, Auth oder komplexer Event-Logik: Socket.io.
Claude Code Prompt: "Erkläre mir den Unterschied zwischen WebSocket und Socket.io und zeig mir ein Minimal-Beispiel beider Ansätze für einen Chat-Endpoint."
2. Socket.io Server-Setup mit Node.js & Express
Server Node.js + Express + Socket.io
Installation: npm install express socket.io cors
server/index.js
import express from 'express';
import { createServer } from 'http';
import { Server } from 'socket.io';
import cors from 'cors';
const app = express();
app.use(cors());
app.use(express.json());
const httpServer = createServer(app);
const io = new Server(httpServer, {
cors: {
origin: process.env.CLIENT_URL || 'http://localhost:5173',
methods: ['GET', 'POST'],
credentials: true
}
});
// Nachrichten-Speicher (in Produktion: Redis/DB)
const messages = new Map();
io.on('connection', (socket) => {
console.log(`✓ Client verbunden: ${socket.id}`);
// Chat-Nachricht empfangen und an Raum weiterleiten
socket.on('chat:message', (data) => {
const msg = {
id: crypto.randomUUID(),
userId: socket.data.userId,
username: socket.data.username,
text: data.text.slice(0, 1000), // Input sanitieren
room: data.room,
timestamp: new Date().toISOString(),
};
// An alle im Raum senden (inkl. Sender)
io.to(data.room).emit('chat:message', msg);
});
socket.on('disconnect', () => {
console.log(`✗ Client getrennt: ${socket.id}`);
});
});
httpServer.listen(3001, () => {
console.log('🚀 Socket.io Server läuft auf Port 3001');
});
3. Client-Integration in React
Client React Hook für Socket.io
Installation: npm install socket.io-client
Der beste Ansatz 2026: einen eigenen React-Hook, der die Socket-Verbindung verwaltet und sauber aufräumt.
hooks/useSocket.ts
import { useEffect, useRef, useCallback } from 'react';
import { io, Socket } from 'socket.io-client';
export function useSocket(token: string | null) {
const socketRef = useRef<Socket | null>(null);
useEffect(() => {
if (!token) return;
socketRef.current = io(import.meta.env.VITE_API_URL, {
auth: { token }, // JWT wird in Auth-Middleware geprüft
transports: ['websocket'], // Kein Polling-Fallback nötig
reconnectionAttempts: 5,
reconnectionDelay: 1000,
});
return () => {
socketRef.current?.disconnect();
};
}, [token]);
const emit = useCallback((event: string, data: unknown) => {
socketRef.current?.emit(event, data);
}, []);
return { socket: socketRef.current, emit };
}
components/ChatRoom.tsx (Ausschnitt)
const { socket, emit } = useSocket(authToken);
const [messages, setMessages] = useState<Message[]>([]);
useEffect(() => {
if (!socket) return;
socket.on('chat:message', (msg: Message) => {
setMessages(prev => [...prev, msg]);
});
return () => { socket.off('chat:message'); };
}, [socket]);
const sendMessage = () => {
emit('chat:message', { text: input, room: currentRoom });
setInput('');
};
4. Räume (Rooms) und Namespaces
Rooms Räume für isolierte Kommunikation
Rooms = temporäre Gruppen innerhalb eines Namespace. Namespaces = separate Kanäle mit eigener Middleware.
server/rooms.js
// Namespace für Chat-Funktionalität
const chatNS = io.of('/chat');
const collabNS = io.of('/collab');
chatNS.on('connection', (socket) => {
// Raum beitreten
socket.on('room:join', (roomId: string) => {
socket.join(roomId);
// Alle anderen im Raum benachrichtigen
socket.to(roomId).emit('room:user-joined', {
userId: socket.data.userId,
username: socket.data.username
});
// Aktive User im Raum zurücksenden
const room = chatNS.adapter.rooms.get(roomId);
socket.emit('room:active-users', {
count: room?.size ?? 0
});
});
// Raum verlassen
socket.on('room:leave', (roomId: string) => {
socket.leave(roomId);
socket.to(roomId).emit('room:user-left', {
userId: socket.data.userId
});
});
});
5. Authentifizierung über Socket-Middleware
Auth JWT-Middleware für Socket.io
Authentifizierung passiert vor dem Connection-Handshake — unauthentifizierte Clients kommen nicht rein.
server/middleware/auth.js
import jwt from 'jsonwebtoken';
export function socketAuthMiddleware(socket, next) {
const token = socket.handshake.auth.token;
if (!token) {
return next(new Error('Kein Auth-Token'));
}
try {
const payload = jwt.verify(token, process.env.JWT_SECRET);
// User-Daten an Socket heften — in Handlern über socket.data verfügbar
socket.data.userId = payload.sub;
socket.data.username = payload.username;
socket.data.roles = payload.roles;
next();
} catch (err) {
next(new Error('Ungültiges Token'));
}
}
// Middleware registrieren
io.use(socketAuthMiddleware);
// Client-seitig: Fehler abfangen
socket.on('connect_error', (err) => {
if (err.message === 'Ungültiges Token') {
auth.logout(); // User zur Login-Seite
}
});
6. Real-World Beispiel: Collaborative Editor
Ein kollaborativer Editor zeigt alle Socket.io-Features in Aktion: Räume, Auth, Echtzeit-Events und Cursor-Synchronisierung.
server/collab-editor.js
const docs = new Map(); // docId → { content, version, cursors }
collabNS.use(socketAuthMiddleware);
collabNS.on('connection', (socket) => {
socket.on('doc:join', (docId: string) => {
socket.join(docId);
const doc = docs.get(docId) ?? {
content: '', version: 0, cursors: {}
};
socket.emit('doc:state', doc);
});
socket.on('doc:change', ({ docId, delta, version }) => {
const doc = docs.get(docId);
if (!doc || doc.version !== version) {
socket.emit('doc:conflict', { current: doc });
return;
}
doc.content = applyDelta(doc.content, delta);
doc.version++;
// An alle anderen senden (nicht zurück an Sender)
socket.to(docId).emit('doc:change', { delta, version: doc.version });
});
socket.on('cursor:move', ({ docId, position }) => {
socket.to(docId).emit('cursor:update', {
userId: socket.data.userId,
username: socket.data.username,
position
});
});
});
Claude Code als Socket.io-Experte
Claude Code beschleunigt Socket.io-Entwicklung massiv — er kennt alle Fallstricke:
- Memory Leaks vermeiden: Claude erinnert dich immer an
socket.off() in React-Cleanup-Funktionen
- Event-Namenskonventionen:
entity:action Schema (z.B. chat:message, doc:change)
- Scaling mit Redis Adapter: Für Multi-Server-Setups generiert Claude sofort
@socket.io/redis-adapter Konfiguration
- Rate-Limiting: Event-basiertes Rate-Limiting mit In-Memory-Countern oder Redis
- TypeScript Types: Vollständig typisierte Server/Client Event-Maps
Claude Code Prompt-Tipp: "Erstelle ein vollständiges Socket.io Setup mit TypeScript, JWT-Auth-Middleware, Redis-Adapter für Horizontal-Scaling und Rate-Limiting pro Socket."
Echtzeit-Apps mit Claude Code bauen
Von WebSocket-Grundlagen bis zur skalierbaren Collaboration-App — Claude Code ist dein Pair-Programmer für Echtzeit-Features. Jetzt kostenlos starten und dein erstes Socket.io-Projekt in Minuten aufsetzen.
Kostenlos testen →