Интеграция Socket.IO для real-time коммуникации на сайте

Наша компания занимается разработкой, поддержкой и обслуживанием сайтов любой сложности. От простых одностраничных сайтов до масштабных кластерных систем построенных на микро сервисах. Опыт разработчиков подтвержден сертификатами от вендоров.
Разработка и обслуживание любых видов сайтов:
Информационные сайты или веб-приложения
Сайты визитки, landing page, корпоративные сайты, онлайн каталоги, квиз, промо-сайты, блоги, новостные ресурсы, информационные порталы, форумы, агрегаторы
Сайты или веб-приложения электронной коммерции
Интернет-магазины, B2B-порталы, маркетплейсы, онлайн-обменники, кэшбэк-сайты, биржи, дропшиппинг-платформы, парсеры товаров
Веб-приложения для управления бизнес-процессами
CRM-системы, ERP-системы, корпоративные порталы, системы управления производством, парсеры информации
Сайты или веб-приложения электронных услуг
Доски объявлений, онлайн-школы, онлайн-кинотеатры, конструкторы сайтов, порталы предоставления электронных услуг, видеохостинги, тематические порталы

Это лишь некоторые из технических типов сайтов, с которыми мы работаем, и каждый из них может иметь свои специфические особенности и функциональность, а также быть адаптированным под конкретные потребности и цели клиента

Предлагаемые услуги
Показано 1 из 1 услугВсе 2065 услуг
Интеграция Socket.IO для real-time коммуникации на сайте
Средняя
~3-5 рабочих дней
Часто задаваемые вопросы
Наши компетенции:
Этапы разработки
Последние работы
  • image_website-b2b-advance_0.png
    Разработка сайта компании B2B ADVANCE
    1214
  • image_web-applications_feedme_466_0.webp
    Разработка веб-приложения для компании FEEDME
    1161
  • image_websites_belfingroup_462_0.webp
    Разработка веб-сайта для компании БЕЛФИНГРУПП
    852
  • image_ecommerce_furnoro_435_0.webp
    Разработка интернет магазина для компании FURNORO
    1041
  • image_crm_enviok_479_0.webp
    Разработка веб-приложения для компании Enviok
    823
  • image_bitrix-bitrix-24-1c_fixper_448_0.png
    Разработка веб-сайта для компании ФИКСПЕР
    815

Интеграция Socket.IO для real-time коммуникации на сайте

Socket.IO — библиотека для двунаправленной коммуникации между сервером и клиентом. В отличие от чистого WebSocket, Socket.IO обеспечивает автоматическое переподключение, fallback на long-polling, комнаты и неймспейсы.

Установка и базовая настройка

npm install socket.io       # сервер
npm install socket.io-client # клиент

Сервер (Node.js + Express)

import { createServer } from 'http';
import { Server } from 'socket.io';
import express from 'express';

const app = express();
const httpServer = createServer(app);

const io = new Server(httpServer, {
  cors: {
    origin: process.env.CLIENT_URL,
    credentials: true
  },
  pingTimeout: 60000,
  pingInterval: 25000
});

// Middleware аутентификации
io.use(async (socket, next) => {
  const token = socket.handshake.auth.token;
  try {
    const payload = jwt.verify(token, process.env.JWT_SECRET);
    socket.data.userId = payload.sub;
    socket.data.user = await userRepo.findById(payload.sub);
    next();
  } catch {
    next(new Error('Authentication error'));
  }
});

io.on('connection', (socket) => {
  const userId = socket.data.userId;
  console.log(`User ${userId} connected: ${socket.id}`);

  // Присоединить к персональной комнате
  socket.join(`user:${userId}`);

  // Обработчики событий
  socket.on('join:room', async ({ roomId }) => {
    const canJoin = await checkRoomAccess(userId, roomId);
    if (!canJoin) {
      socket.emit('error', { message: 'Access denied' });
      return;
    }
    socket.join(`room:${roomId}`);
    socket.to(`room:${roomId}`).emit('user:joined', {
      userId, user: socket.data.user
    });
  });

  socket.on('message:send', async ({ roomId, content }) => {
    const message = await messageRepo.create({ roomId, userId, content });
    io.to(`room:${roomId}`).emit('message:new', message);
  });

  socket.on('disconnect', () => {
    console.log(`User ${userId} disconnected`);
    // Уведомить комнаты о выходе
    io.emit('user:offline', { userId });
  });
});

httpServer.listen(3000);

Клиент (React)

// hooks/useSocket.ts
import { useEffect, useRef } from 'react';
import { io, Socket } from 'socket.io-client';
import { useAuthStore } from '@/stores/auth';

export function useSocket(): Socket | null {
  const socketRef = useRef<Socket | null>(null);
  const token = useAuthStore(s => s.token);

  useEffect(() => {
    if (!token) return;

    const socket = io(process.env.NEXT_PUBLIC_WS_URL, {
      auth: { token },
      reconnection: true,
      reconnectionDelay: 1000,
      reconnectionAttempts: 5,
      transports: ['websocket', 'polling']
    });

    socket.on('connect', () => console.log('Socket connected'));
    socket.on('connect_error', (err) => console.error('Connection error:', err));

    socketRef.current = socket;

    return () => {
      socket.disconnect();
      socketRef.current = null;
    };
  }, [token]);

  return socketRef.current;
}

// Компонент чата
function ChatRoom({ roomId }) {
  const socket = useSocket();
  const [messages, setMessages] = useState([]);

  useEffect(() => {
    if (!socket) return;

    socket.emit('join:room', { roomId });

    socket.on('message:new', (message) => {
      setMessages(prev => [...prev, message]);
    });

    return () => {
      socket.off('message:new');
      socket.emit('leave:room', { roomId });
    };
  }, [socket, roomId]);

  const sendMessage = (content: string) => {
    socket?.emit('message:send', { roomId, content });
  };

  return <ChatUI messages={messages} onSend={sendMessage} />;
}

Масштабирование через Redis Adapter

При нескольких Node.js процессах Socket.IO нужен Redis для синхронизации:

import { createAdapter } from '@socket.io/redis-adapter';
import { createClient } from 'redis';

const pubClient = createClient({ url: process.env.REDIS_URL });
const subClient = pubClient.duplicate();

await Promise.all([pubClient.connect(), subClient.connect()]);

io.adapter(createAdapter(pubClient, subClient));

// Теперь io.to('room:123').emit() работает across всех Node.js процессов

Уведомления из других сервисов

// Из бэкенд-сервиса отправить уведомление конкретному пользователю
// через Redis pub/sub (без прямого доступа к Socket.IO серверу)
const publisher = createClient({ url: process.env.REDIS_URL });

await publisher.publish('socket:notify', JSON.stringify({
  room: `user:${userId}`,
  event: 'order:status_changed',
  data: { orderId, newStatus: 'shipped' }
}));

Сроки

Socket.IO сервер + клиентский хук + чат-комнаты + Redis adapter — 1–2 недели.