user www-data;
worker_processes auto;
pid /run/nginx.pid;
include /etc/nginx/modules-enabled/*.conf;

events {
        worker_connections 1024;  # maximum number of connections that a worker process can handle concurrently
        # multi_accept on;  # enabling multi_accept can help improve performance under high load, but may increase the number of simultaneous connections that a worker process can handle

}

http {
        ##
        # Basic Settings
        ##

        sendfile on;  # enable sendfile for performance optimization
        tcp_nopush on;  # enable TCP no-pushing
        tcp_nodelay on;  # enable TCP no-delay
        keepalive_timeout 65;  # sets the timeout for keep-alive connections
        types_hash_max_size 2048;  # maximum size of the types hash table
        # server_tokens off;  # disable server token (i.e., server signature) in response headers to improve security

        # server_names_hash_bucket_size 64;
        # server_name_in_redirect off;

        include /etc/nginx/mime.types;  # include MIME types file
        default_type application/octet-stream;  # default MIME type for unknown file types

        ##
        # SSL Settings
        ##

        ssl_protocols TLSv1.2;  # specify SSL/TLS protocols to use
        ssl_prefer_server_ciphers on;  # prefer server ciphers over client ciphers

        ##
        # Logging Settings
        ##

        access_log /var/log/nginx/access.log;  # path to access log file
        error_log /var/log/nginx/error.log;  # path to error log file

        ##
        # Gzip Settings
        ##
        gzip on;  # enable Gzip compression

        ##
        # Virtual Host Configs
        ##

        include /etc/nginx/conf.d/*.conf;  # include all configuration files in conf.d directory
        include /etc/nginx/sites-enabled/*;  # include all enabled sites configuration files

        # WebSocket Proxy: https://www.nginx.com/blog/websocket-nginx/
        map $http_upgrade $connection_upgrade {
                default upgrade;
                '' close;
        }

        upstream websocket {
                ip_hash; # load balancing by IP to guarantee session persistence
                server localhost:7860;  # The port should be the gradio web server port
                # server localhost:7861;  # extra gradio server if more than one
        }

        limit_conn_status 429;
        limit_conn_zone $binary_remote_addr zone=perip:10m;  # limit number of connections per IP
        limit_conn_zone $server_name zone=perserver:10m;  # limit number of connections per server

        server {
                listen 443 ssl;  # the listening port of our server
		        ssl_certificate [PATH_TO_SSL_CERT];
		        ssl_certificate_key [PATH_TO_PRIVATE_KEY];
		        server_name chat.lmsys.org; # replace the url with your own domain url
                limit_conn perserver 1024;  # connections per server
                location / {
                        proxy_pass http://websocket;  # proxy all requests to the defined upstream server
                        limit_conn perip 5;  # connections per IP
                        proxy_set_header Host $host;  # set the Host header for the upstream server
                        proxy_set_header X-Real-IP $remote_addr;  # set the client IP address as the real IP for the upstream server
                        proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;  # set the client IP addresses in the X-Forwarded-For header
                        proxy_http_version 1.1;  # use HTTP version 1.1 for upstream communication
                        proxy_set_header Upgrade $http_upgrade;
                        proxy_set_header Connection "Upgrade";  # set the Connection header to Upgrade to enable WebSocket communication
                }
        }
	
	# the following block routes all HTTP traffic to HTTPS via nginx
	server {
		listen 80;
		server_name chat.lmsys.org;
		return 301 https://chat.lmsys.org$request_uri;
	}

}
