Обратный прокси
Обратный прокси
Используйте эту страницу, если вы запускаете OpenChamber за Nginx, Nginx Proxy Manager, Caddy, Cloudflare или другим обратным прокси.
Прежде чем проксировать
- Сначала убедитесь, что OpenChamber работает напрямую.
- Откройте
http://<server-ip>:3000или ваш кастомный порт из той же сети. - Добавляйте обратный прокси только после того, как прямое подключение заработало.
Что должен поддерживать прокси
- WebSockets для живой передачи сообщений:
/api/event/ws/api/global/event/ws/api/terminal/ws
- SSE без буферизации:
/api/event/api/global/event/api/notifications/stream/api/openchamber/events/api/terminal/:sessionId/stream
- Большие тела запросов для вложений и файловых операций
- Долгие read-таймауты для живых потоков и терминальных сессий
Важные правила
- Включите проксирование WebSocket.
- Отключите буферизацию на SSE-маршрутах.
- Отключите gzip на прокси, если OpenChamber уже сжимает ответы.
- Держите сжатие включённым только на одном уровне.
- Прокидывайте стандартные прокси-заголовки:
Host,X-Forwarded-For,X-Forwarded-Proto. - Увеличьте лимиты размера тела, если пользователи загружают файлы.
Быстрый чеклист
- OpenChamber доступен напрямую в LAN
- WebSockets включены в прокси
- На SSE-маршрутах буферизация выключена
gzip offна хосте прокси или сжатие прокси отключено иным способомclient_max_body_sizeдостаточно велик для вложенийproxy_read_timeoutдостаточно долог для потоков
Пример: Nginx
Показать пример конфига
client_max_body_size 50M;
client_body_buffer_size 50M;
proxy_request_buffering off;
proxy_http_version 1.1;
proxy_set_header Connection "";
proxy_set_header Host $host;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
proxy_set_header X-Forwarded-Proto $scheme;
proxy_set_header X-Forwarded-Host $host;
gzip off;
location = /api/terminal/ws {
proxy_pass http://127.0.0.1:3000;
proxy_set_header Upgrade $http_upgrade;
proxy_set_header Connection "upgrade";
proxy_buffering off;
proxy_cache off;
proxy_read_timeout 3600s;
proxy_send_timeout 3600s;
}
location = /api/global/event/ws {
proxy_pass http://127.0.0.1:3000;
proxy_set_header Upgrade $http_upgrade;
proxy_set_header Connection "upgrade";
proxy_buffering off;
proxy_cache off;
proxy_read_timeout 3600s;
proxy_send_timeout 3600s;
}
location = /api/event/ws {
proxy_pass http://127.0.0.1:3000;
proxy_set_header Upgrade $http_upgrade;
proxy_set_header Connection "upgrade";
proxy_buffering off;
proxy_cache off;
proxy_read_timeout 3600s;
proxy_send_timeout 3600s;
}
location ~ ^/api/(event|global/event|notifications/stream|openchamber/events)$ {
proxy_pass http://127.0.0.1:3000;
proxy_set_header Accept "text/event-stream";
proxy_set_header Cache-Control "no-cache";
proxy_buffering off;
proxy_cache off;
gzip off;
add_header X-Accel-Buffering "no" always;
add_header Cache-Control "no-cache, no-transform" always;
proxy_read_timeout 3600s;
proxy_send_timeout 3600s;
}
location ~ ^/api/terminal/.+/stream$ {
proxy_pass http://127.0.0.1:3000;
proxy_set_header Accept "text/event-stream";
proxy_set_header Cache-Control "no-cache";
proxy_buffering off;
proxy_cache off;
gzip off;
add_header X-Accel-Buffering "no" always;
add_header Cache-Control "no-cache, no-transform" always;
proxy_read_timeout 3600s;
proxy_send_timeout 3600s;
}
location /api {
proxy_pass http://127.0.0.1:3000;
proxy_read_timeout 3600s;
proxy_send_timeout 3600s;
}
location / {
proxy_pass http://127.0.0.1:3000;
}
Пример: Nginx Proxy Manager
Показать пример для вкладки Advanced
client_max_body_size 50M;
client_body_buffer_size 50M;
proxy_request_buffering off;
proxy_http_version 1.1;
proxy_set_header Connection "";
proxy_set_header Host $host;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
proxy_set_header X-Forwarded-Proto $scheme;
proxy_set_header X-Forwarded-Host $host;
gzip off;
location = /api/terminal/ws {
proxy_pass http://127.0.0.1:3000;
proxy_set_header Upgrade $http_upgrade;
proxy_set_header Connection "upgrade";
proxy_buffering off;
proxy_cache off;
proxy_read_timeout 3600s;
proxy_send_timeout 3600s;
proxy_connect_timeout 30s;
}
location = /api/global/event/ws {
proxy_pass http://127.0.0.1:3000;
proxy_set_header Upgrade $http_upgrade;
proxy_set_header Connection "upgrade";
proxy_buffering off;
proxy_cache off;
proxy_read_timeout 3600s;
proxy_send_timeout 3600s;
proxy_connect_timeout 30s;
}
location = /api/event/ws {
proxy_pass http://127.0.0.1:3000;
proxy_set_header Upgrade $http_upgrade;
proxy_set_header Connection "upgrade";
proxy_buffering off;
proxy_cache off;
proxy_read_timeout 3600s;
proxy_send_timeout 3600s;
proxy_connect_timeout 30s;
}
location = /api/event {
proxy_pass http://127.0.0.1:3000;
proxy_set_header Accept "text/event-stream";
proxy_set_header Cache-Control "no-cache";
proxy_buffering off;
proxy_cache off;
gzip off;
add_header X-Accel-Buffering "no" always;
add_header Cache-Control "no-cache, no-transform" always;
proxy_read_timeout 3600s;
proxy_send_timeout 3600s;
proxy_connect_timeout 30s;
}
location = /api/global/event {
proxy_pass http://127.0.0.1:3000;
proxy_set_header Accept "text/event-stream";
proxy_set_header Cache-Control "no-cache";
proxy_buffering off;
proxy_cache off;
gzip off;
add_header X-Accel-Buffering "no" always;
add_header Cache-Control "no-cache, no-transform" always;
proxy_read_timeout 3600s;
proxy_send_timeout 3600s;
proxy_connect_timeout 30s;
}
location = /api/notifications/stream {
proxy_pass http://127.0.0.1:3000;
proxy_set_header Accept "text/event-stream";
proxy_set_header Cache-Control "no-cache";
proxy_buffering off;
proxy_cache off;
gzip off;
add_header X-Accel-Buffering "no" always;
add_header Cache-Control "no-cache, no-transform" always;
proxy_read_timeout 3600s;
proxy_send_timeout 3600s;
proxy_connect_timeout 30s;
}
location = /api/openchamber/events {
proxy_pass http://127.0.0.1:3000;
proxy_set_header Accept "text/event-stream";
proxy_set_header Cache-Control "no-cache";
proxy_buffering off;
proxy_cache off;
gzip off;
add_header X-Accel-Buffering "no" always;
add_header Cache-Control "no-cache, no-transform" always;
proxy_read_timeout 3600s;
proxy_send_timeout 3600s;
proxy_connect_timeout 30s;
}
location ~ ^/api/terminal/.+/stream$ {
proxy_pass http://127.0.0.1:3000;
proxy_set_header Accept "text/event-stream";
proxy_set_header Cache-Control "no-cache";
proxy_buffering off;
proxy_cache off;
gzip off;
add_header X-Accel-Buffering "no" always;
add_header Cache-Control "no-cache, no-transform" always;
proxy_read_timeout 3600s;
proxy_send_timeout 3600s;
proxy_connect_timeout 30s;
}
location /api {
proxy_pass http://127.0.0.1:3000;
proxy_read_timeout 3600s;
proxy_send_timeout 3600s;
proxy_connect_timeout 30s;
}
location / {
proxy_pass http://127.0.0.1:3000;
}
Также включите Websockets Support в Nginx Proxy Manager для этого хоста.
Частые признаки проблем
Страница грузится, но отправка сообщений падает
- WebSockets не включены в прокси
/api/event/wsили/api/global/event/wsне прокидывается корректно
Уведомления или живой статус не обновляются
- один из SSE-маршрутов буферизуется или кэшируется
- отсутствует
X-Accel-Buffering "no"
Загрузка файлов падает
client_max_body_sizeслишком мал
Всё работает локально, но ломается только за прокси
- прокси сжимает и буферизует живой трафик
- в прокси нет поддержки WebSocket
Пример: Caddy
Показать пример конфига
reverse_proxy 127.0.0.1:3000 {
# WebSocket support is automatic in Caddy
# Flush SSE responses immediately
flush_interval -1
# Pass through Host and proxy headers
header_up Host {host}
header_up X-Real-IP {remote_host}
header_up X-Forwarded-For {remote_host}
header_up X-Forwarded-Proto {scheme}
# Increase timeouts for long-lived streams
transport http {
read_timeout 3600s
write_timeout 3600s
}
}
Caddy обрабатывает WebSocket-апгрейды автоматически — дополнительная настройка не нужна. Директива flush_interval -1 гарантирует, что SSE-чанки пересылаются немедленно, без буферизации.
CDN и предупреждение о двойном сжатии
Если вы ставите CDN (например, Cloudflare) перед обратным прокси, учтите двойное сжатие:
- OpenChamber сжимает HTTP-ответы gzip’ом (порог 1 КБ).
- Cloudflare и другие CDN тоже сжимают ответы по умолчанию.
- Это может вызвать дважды сжатые ответы или неверные заголовки
Content-Encoding.
Чтобы этого избежать, отключите сжатие на одном уровне:
- Cloudflare: Rules → Compression → отключить (или режим «Passthrough»).
- Nginx:
gzip off(уже показано в примерах выше). - Caddy: Caddy по умолчанию не пересжимает, если апстрим уже отдаёт сжатый контент.
SSE-маршруты исключены из сжатия самим OpenChamber, но CDN может их буферизовать. Проверьте документацию вашего CDN, как отключить буферизацию на SSE-путях.