I've read through all of the related traefik / websocket issues here and other forums, but I wasn't able to solve the problem for my setup.
I'm trying to run Dataiku DSS behind Traefik as reverse proxy. But I'm still new to Traefik and can't figure out how to make websockets for my service work via Traefik.
I'm using the following config:
traefik.yml:
api:
dashboard: true
entryPoints:
http:
address: ":80"
https:
address: ":443"
providers:
docker:
endpoint: "unix:///var/run/docker.sock"
exposedByDefault: false
certificatesResolvers:
http:
acme:
email: admin@example.com
storage: acme.json
httpChallenge:
entryPoint: http
traefik/docker-compose.yml:
version: '3'
services:
traefik:
image: traefik:v2.0
container_name: traefik
restart: unless-stopped
security_opt:
- no-new-privileges:true
networks:
- proxy
ports:
- 80:80
- 443:443
volumes:
- /etc/localtime:/etc/localtime:ro
- /var/run/docker.sock:/var/run/docker.sock:ro
- ./data/traefik.yml:/traefik.yml:ro
- ./data/acme.json:/acme.json
labels:
- "traefik.enable=true"
- "traefik.http.routers.traefik.entrypoints=http"
- "traefik.http.routers.traefik.rule=Host(`traefik.example.com`)"
- "traefik.http.middlewares.traefik-auth.basicauth.users=<USER>:<PW>"
- "traefik.http.middlewares.traefik-https-redirect.redirectscheme.scheme=https"
- "traefik.http.routers.traefik.middlewares=traefik-https-redirect"
- "traefik.http.routers.traefik-secure.entrypoints=https"
- "traefik.http.routers.traefik-secure.rule=Host(`traefik.example.com`)"
- "traefik.http.routers.traefik-secure.middlewares=traefik-auth"
- "traefik.http.routers.traefik-secure.tls=true"
- "traefik.http.routers.traefik-secure.tls.certresolver=http"
- "traefik.http.routers.traefik-secure.service=api@internal"
networks:
proxy:
external: true
dataiku/docker-compose.yml:
version: '3.7'
services:
dataiku:
build:
context: .
dockerfile: Dockerfile
restart: on-failure
volumes:
- dss_data:/home/dataiku/dss
labels:
- traefik.enable=true
- traefik.http.routers.dataiku.entrypoints=http
- traefik.http.routers.dataiku.rule=Host(`dataiku.example.com`)
#- traefik.http.middlewares.dataiku-https-redirect.redirectscheme.scheme=https
#- traefik.http.routers.dataiku.middlewares=dataiku-https-redirect
#- traefik.http.routers.dataiku-secure.entrypoints=https
#- traefik.http.routers.dataiku-secure.rule=Host(`dataiku.example.com`)
#- traefik.http.routers.dataiku-secure.tls=true
#- traefik.http.routers.dataiku-secure.tls.certresolver=http
#- traefik.http.routers.dataiku-secure.service=dataiku
- traefik.http.services.dataiku.loadbalancer.server.port=10000
- traefik.docker.network=proxy
volumes:
dss_data:
networks:
proxy:
external: true
However, when I run dataiku, I see that the websocket connections fail. In Firefox, I see that right after the WS connection is attempted, I get the following error: XSRF validation failed
.
On Chrome, I see the following: Error during WebSocket handshake: Sent non-empty 'Sec-WebSocket-Protocol' header but no response was received
The request headers looks like this:
Host: example.com
User-Agent: ...
Accept: */*
Accept-Language: en-US,en;q=0.5
Accept-Encoding: gzip, deflate
Sec-WebSocket-Version: 13
Origin: http://example.com
Sec-WebSocket-Protocol: dummy, xsrf-7646db48d09813bbe5038c1aa2967e0a9712f81a24b156731f88bde5d3c4d8a5
Sec-WebSocket-Extensions: permessage-deflate
Sec-WebSocket-Key: 3sSlW9J6GN6d4+bhFr1IIQ==
Connection: keep-alive, Upgrade
Pragma: no-cache
Cache-Control: no-cache
Upgrade: websocket
The response headers looks like this:
HTTP/1.1 101 Switching Protocols
Connection: upgrade
Date: Sat, 06 Jun 2020 15:18:08 GMT
Sec-Websocket-Accept: x29WLUMyl5OmRfhZOncdLE65lOU=
Server: nginx
Upgrade: WebSocket
Both errors indicate to me, that the response is missing a correct Sec-WebSocket-Protocol
header. But I don't know how to fix that. Initially I thought it might have something to do with TLS, that's why I commented out the secure entrypoint and redirect. But it still exists.
I've previously had no issues with a nginx config like this one:
server {
# Host/port on which to expose Data Science Studio to users
listen 80;
server_name dss.example.com;
location / {
# Base url of the Data Science Studio installation
proxy_pass http://DSS_HOST:DSS_PORT/;
proxy_redirect off;
# Allow long queries
proxy_read_timeout 3600;
proxy_send_timeout 600;
# Allow large uploads
client_max_body_size 0;
# Allow protocol upgrade to websocket
proxy_http_version 1.1;
proxy_set_header Host $http_host;
proxy_set_header Upgrade $http_upgrade;
proxy_set_header Connection "upgrade";
}
}
Does anyone have an idea how to solve this?