Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
7 changes: 7 additions & 0 deletions self-hosting/docker-compose-self-hosted.yml
Original file line number Diff line number Diff line change
@@ -1,4 +1,11 @@
services:
nginx:
image: nginx:stable
container_name: sni-router
network_mode: host
volumes:
- ./nginx.conf:/etc/nginx/nginx.conf:ro
restart: unless-stopped
web:
image: ghcr.io/forwardemail/forwardemail.net-selfhosted:latest
container_name: web
Expand Down
53 changes: 53 additions & 0 deletions self-hosting/nginx.conf
Original file line number Diff line number Diff line change
@@ -0,0 +1,53 @@
worker_rlimit_nofile 65535;
worker_processes auto;

events {
worker_connections 8192;
multi_accept on;
}

# This stream block is acting as a pass-through proxy based on SNI.
# - Each upstream service (web, api, caldav, carddav) still handles TLS.
stream {
# Fail fast. This applies to all upstreams (web, api, caldav, carddav).
proxy_connect_timeout 5s;

# Accommodate large headers/cookies in the initial response chunk
proxy_buffer_size 16k;

# Enable TCP keepalive to detect dead connections and prevent timeouts
proxy_socket_keepalive on;

map $ssl_preread_server_name $backend {
# carddav.example.com, caldav.example.com, api.example.com
~^carddav\. carddav;
~^caldav\. caldav;
~^api\. api;
# example.com and any other hostname
default web;
}

server {
listen 443;
listen [::]:443;

ssl_preread on; # Use SNI information to route to correct backend
proxy_pass $backend;
}

upstream web {
server 127.0.0.1:3000;
}

upstream api {
server 127.0.0.1:4000;
}

upstream caldav {
server 127.0.0.1:5000;
}

upstream carddav {
server 127.0.0.1:6000;
}
}
4 changes: 2 additions & 2 deletions self-hosting/setup.sh
Original file line number Diff line number Diff line change
Expand Up @@ -473,9 +473,9 @@ update_env_file() {
update_default_env() {
update_env_file NODE_ENV production
update_env_file HTTP_PROTOCOL https
update_env_file SQLITE_HOST sqlite.{{DOMAIN}}
update_env_file WEB_URL https://{{DOMAIN}}
update_env_file WEB_HOST {{DOMAIN}}
update_env_file WEB_PORT 443
update_env_file SQLITE_HOST sqlite.{{DOMAIN}}
update_env_file CALDAV_HOST caldav.{{DOMAIN}}
update_env_file CARDDAV_HOST carddav.{{DOMAIN}}
update_env_file API_HOST api.{{DOMAIN}}
Expand Down