diff --git a/.claude/HISTORY.md b/.claude/HISTORY.md index b9e10f76..44f3dad2 100644 --- a/.claude/HISTORY.md +++ b/.claude/HISTORY.md @@ -1420,3 +1420,32 @@ _Last updated: 2026-02-11_ - **Login Issue Resolution**: - Form field is `username` not `email` (GoToSocial quirk) - Admin user: `admin@secubox.in` / `TestAdmin123!` + +## 2026-02-14: Fixed Streamlit apps + WAF compatibility + +### Problem +- Streamlit apps showing blank page with loading spinner when accessed via public URLs +- Direct access to backends (192.168.255.1:xxxx) worked fine +- Issue was mitmproxy WAF not handling WebSocket connections properly + +### Root Cause +- HAProxy `waf_enabled=1` routed ALL vhosts through `mitmproxy_inspector` backend +- mitmproxy's `haproxy_router` addon wasn't properly handling WebSocket upgrade connections +- WebSocket connections disconnected immediately, breaking Streamlit's real-time UI + +### Solution +1. Added `waf_bypass` option to `/usr/sbin/haproxyctl`: + - Vhosts with `waf_bypass=1` route directly to their backends + - Other vhosts still go through mitmproxy WAF +2. Set `waf_bypass=1` for Streamlit vhosts (yling, bazi, bweep, bweek, wuyun, pix, hermes, evolution, control) +3. Updated haproxy_router.py addon with WebSocket event handlers (for future improvement) + +### Files Modified +- `/usr/sbin/haproxyctl` - Added waf_bypass option check +- `/srv/mitmproxy-in/addons/haproxy_router.py` - Added WebSocket handlers +- `/srv/lxc/mitmproxy-in/config` - Enabled HAPROXY_ROUTER_ENABLED=1 + +### Result +- Streamlit apps work with full WebSocket support +- Other services still protected by mitmproxy WAF +- Hybrid approach balances security and functionality diff --git a/package/secubox/secubox-app-haproxy/files/usr/sbin/haproxyctl b/package/secubox/secubox-app-haproxy/files/usr/sbin/haproxyctl index 4134d843..571e9f35 100644 --- a/package/secubox/secubox-app-haproxy/files/usr/sbin/haproxyctl +++ b/package/secubox/secubox-app-haproxy/files/usr/sbin/haproxyctl @@ -723,7 +723,8 @@ _emit_sorted_path_acls() { # Generate use_backend rule (use WAF backend if enabled) local effective_backend="$backend" - [ "$waf_enabled" = "1" ] && effective_backend="$waf_backend" + config_get waf_bypass "$section" waf_bypass "0" + [ "$waf_enabled" = "1" ] && [ "$waf_bypass" != "1" ] && effective_backend="$waf_backend" if [ -n "$host_acl_name" ]; then echo " use_backend $effective_backend if host_${host_acl_name} ${acl_name}" else @@ -788,7 +789,8 @@ _add_vhost_acl() { esac # Use WAF backend if enabled, otherwise use original backend local effective_backend="$backend" - [ "$waf_enabled" = "1" ] && effective_backend="$waf_backend" + config_get waf_bypass "$section" waf_bypass "0" + [ "$waf_enabled" = "1" ] && [ "$waf_bypass" != "1" ] && effective_backend="$waf_backend" echo " use_backend $effective_backend if host_${acl_name}" }