Deploy Streamlit with NGINX with SSL

Hello,

I have docker container with NGINX and with that configuration

map $http_upgrade $connection_upgrade {
default upgrade;
β€˜β€™ close;
}

server {
    listen 80;
    listen 443 ssl;
    server_name server_name.com;

    ssl_certificate /etc/nginx/ssl/fullchain.pem;
    ssl_certificate_key /etc/nginx/ssl/privkey.pem;

    location / {
        proxy_pass http://192.168.50.140:8501;
        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_http_version 1.1;
        proxy_set_header Upgrade $http_upgrade;
        proxy_set_header Connection "upgrade";
    }

    location /_stcore/stream {
        proxy_pass http://192.168.50.140:8501/_stcore/stream;
        proxy_http_version 1.1;
        proxy_set_header Upgrade $http_upgrade;
        proxy_set_header Connection "upgrade";
        proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
        proxy_set_header Host $host;
        proxy_read_timeout 86400;
    }
}

On my server I have a basic application streamlit. For testing connection I leave just that

import streamlit as st


def main():
    st.title("Basic Streamlit App")

    st.write("This is a basic Streamlit app for testing purposes.")

    # Add more Streamlit components as needed
    st.write("Feel free to modify this code and add more components.")


if __name__ == "__main__":
    main()

I set version 1.23.0 but with latest version I had the same issue.

Connection via http is working.
Connection with https is not working
I got
WebsocketConnection WebSocket onerror
main.e13854e4.js:2 WebSocket connection to β€˜wss://server_name.com/_stcore/stream’ failed:

I read guide and went through the solutions but nothing helped

also this article

I added necessary configuration based on that
https://nginx.org/en/docs/http/websocket.html

I added that one as well /_stcore/stream to my NGINX configuration.

Please help me. Maybe I missed some detailes. Thank you.

1 Like

Getting same error:

  • working on http
  • not working on https

Here is my nginx config file:

server {

    server_name my_domain;

    listen [::]:443 ssl; # managed by Certbot
    listen 443 ssl; # managed by Certbot

    ssl_certificate /etc/letsencrypt/live/my_domain/fullchain.pem; # managed by Certbot
    ssl_certificate_key /etc/letsencrypt/live/my_domain/privkey.pem; # managed by Certbot
    include /etc/letsencrypt/options-ssl-nginx.conf; # managed by Certbot
    ssl_dhparam /etc/letsencrypt/ssl-dhparams.pem; # managed by Certbot

    keepalive_timeout 5;

    location / {
        proxy_pass http://127.0.0.1:8501/;
        proxy_set_header Host $http_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_redirect off;
        proxy_http_version 1.1;

        proxy_set_header Upgrade $http_upgrade;
        proxy_set_header Connection "upgrade";
        proxy_read_timeout 86400;
    }

    location /_stcore/stream {
        proxy_pass http://127.0.0.1:8501/_stcore/stream;
        proxy_http_version 1.1; 
        proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
        proxy_set_header Host $host;
        proxy_set_header Upgrade $http_upgrade;
        proxy_set_header Connection "upgrade";
        proxy_set_header Sec-WebSocket-Extensions $http_sec_websocket_extentions;
        proxy_read_timeout 86400;
        proxy_set_header X-Real-IP $remote_addr;
        proxy_set_header X-Forwarded-Proto $scheme;
    }

}

server { # managed by Certbot
    if ($host = my_domain) { # managed by Certbot
        return 301 https://$host$request_uri; # managed by Certbot
    } # managed by Certbot

        listen 80; # managed by Certbot
        listen [::]:80; # managed by Certbot

        server_name my_domain; # managed by Certbot
    return 404; # managed by Certbot
} # managed by Certbot

And my config.toml:

[server]
port = 8501
serverPort = 443
serverAddress = "my_domain"
enableCORS = false
enableXsrfProtection = false
gatherUsageStats = false

And I launch my streamlit app with this command:

$ streamlit run app.py

Thanks for bringing support!

:grin:

OK it’s solved!

I had both services opened on port 8501

  • nginx
  • streamlit

I did proceed as follows:

  • push streamlit to port 8502
  • kept nginx on port 8501

NGINX FILE

server {
    listen 80; 
    server_name my_domain; 

    location / {
        proxy_pass http://127.0.0.1:8502/;
        proxy_http_version 1.1;
        proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
        proxy_set_header Host $host;
        proxy_set_header Upgrade $http_upgrade;
        proxy_set_header Connection "upgrade";
        proxy_read_timeout 86400;

    }

    # location / {
    #     return 301 https://$host$request_uri;
    # }
}

server {

    server_name my_domain;

    listen [::]:443 ssl; # managed by Certbot
    listen 443 ssl; # managed by Certbot

    ssl_certificate /etc/letsencrypt/live/my_domain/fullchain.pem; # managed by Certbot
    ssl_certificate_key /etc/letsencrypt/live/my_domain/privkey.pem; # managed by Certbot
    include /etc/letsencrypt/options-ssl-nginx.conf; # managed by Certbot
    ssl_dhparam /etc/letsencrypt/ssl-dhparams.pem; # managed by Certbot

    keepalive_timeout 10;

    location / {
        proxy_pass http://127.0.0.1:8502/;
        proxy_set_header Host $http_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_redirect off;
        proxy_http_version 1.1;

        proxy_set_header Upgrade $http_upgrade;
        proxy_set_header Connection "upgrade";
        proxy_read_timeout 86400;
    }

    location /_stcore/stream {
        proxy_pass http://127.0.0.1:8502/_stcore/stream;
        proxy_http_version 1.1; 
        proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
        proxy_set_header Host $host;
        proxy_set_header Upgrade $http_upgrade;
        proxy_set_header Connection "upgrade";
        proxy_set_header Sec-WebSocket-Extensions $http_sec_websocket_extentions;
        proxy_read_timeout 86400;
        proxy_set_header X-Real-IP $remote_addr;
        proxy_set_header X-Forwarded-Proto $scheme;
    }

    location ^~ /healthz {
        proxy_pass http://127.0.0.1:8502/healthz;
    }

}

CONFIG.TOML

[server]
port = 8502
enableCORS = false
enableXsrfProtection = false
headless = true

And think about restarting both services:

$ streamlit run app.py
$ sudo service nginx restart

:tada: