Websockets on AKS using GraphQL Not Connecting

6/17/2019

I currently have an AKS cluster setup running a GraphQL server and normal nginx ingress. We're attempting to onboard GraphQL Subscriptions, which utilize Websockets. The URL that GraphQL uses for websockets is the same url that is used for GraphQL queries. We've tried adding proxy configuration to enable websocket ingress, but the connection is never established. Running the GraphQL server without Kubernetes is successful, so we think there is something kubernetes-specific going on here...has anyone had any success doing this? Relevant ingress config below

apiVersion: extensions/v1beta1
kind: Ingress
metadata:
  name: web-ingress
  namespace: web
  annotations:
    kubernetes.io/ingress.class: nginx
    certmanager.k8s.io/cluster-issuer: letsencrypt
    nginx.ingress.kubernetes.io/use-regex: "true"
    nginx.ingress.kubernetes.io/affinity: cookie
    nginx.ingress.kubernetes.io/proxy-send-timeout: "3600"
    nginx.ingress.kubernetes.io/proxy-read-timeout: "3600"
    nginx.ingress.kubernetes.io/proxy-connect-timeout: "30"
    nginx.ingress.kubernetes.io/configuration-snippet: |
        proxy_http_version 1.1;
        proxy_set_header Upgrade $http_upgrade;
        proxy_set_header Connection "upgrade";
spec:
  tls:
  - hosts:
    - my.host
    - my-api.host
    secretName: tls-secret
  rules:
  - host: my.host
    http:
      paths:
      - path: /graphql
        backend:
          serviceName: webapi
          servicePort: 80
      - path: /(.*)
        backend:
          serviceName: website
          servicePort: 80
  - host: my-api.host
    http:
      paths:
      - backend:
          serviceName: webapi
          servicePort: 80
        path: /(.*)
-- Jonathan Miller
azure-aks
graphql
kubernetes
kubernetes-ingress
websocket

1 Answer

12/28/2019

You might want to start from a bit less complex config like this:

apiVersion: extensions/v1beta1
kind: Ingress
metadata:
  name: web-ingress
  namespace: web
  annotations:
    kubernetes.io/ingress.class: nginx
    certmanager.k8s.io/cluster-issuer: letsencrypt
    ingress.kubernetes.io/ssl-redirect: "true"
    kubernetes.io/tls-acme: "true"
spec:
  tls:
  - hosts:
    - my.host
    secretName: tls-secret
  rules:
  - host: my.host
    http:
      paths:
      - path: /
        backend:
          serviceName: website
          servicePort: 80
      - path: /graphql
        backend:
          serviceName: webapi
          servicePort: 80

I switched the config to one endpoint instead of two. Removed some config since NGINX handles websockets out of the box. I removed regexp. I added the tls-acme annotation. And also ssl-redirect. In summary I just made it a bit less complex. Get this up and running first and then start applying advanced config stuff like the timeouts you did.

Happy to hear any feedback on this!

-- Merijn
Source: StackOverflow