Niels Uitterdijk
Niels Uitterdijk

Reputation: 770

CSRF cookie not set - possibly blocked by kubernetes ingress

I use Axios in React and Django Rest Framework with dj-rest-auth. After migrating from GCP to Azure and removing the unmaintained django-rest-auth, I got some new CSRF issues. Initially I removed django-rest-auth and created my own LoginView from Django.contrib.auth.views. Noticed that this also gave the CSRF error in development. So I added dj-rest-auth, which solved my issue locally. Pushed to the AKS, but there the cookie still does not appear. I'm suspecting my ingress to be the problem, which is able to set INGRESSCOOKIE for both my backend and frontend, but no CSRF.

I know there's a million tickets about this topic, my Django settings are fine, the set-cookie resopnse header is set. Also use the right axios settings to make sure that if the cookie is there, it's used for requests. The problem is really with the fact that the set-cookie is not coming through, as it is being created in Django.

I use an Nginx controller with TLS on a static IP with and have my ingress defined as follows:

apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:
  name: basic-ingress
  annotations:
    kubernetes.io/ingress.class: nginx
    cert-manager.io/cluster-issuer: letsencrypt-prod
    nginx.ingress.kubernetes.io/rewrite-target: /
    kubernetes.io/ingress.allow-http: "true"
spec:
  tls:
  - hosts:
    - XXXXX
    secretName: tls-secret
  rules:
  - host: XXXXXXXX
    http:
      paths:
      - path: /
        pathType: Prefix
        backend:
          service:
            name: frontend
            port:
              number: 80
      - path: /api/
        pathType: Prefix
        backend:
          service:
            name: backend
            port:
              number: 8080

Upvotes: 1

Views: 2214

Answers (1)

Niels Uitterdijk
Niels Uitterdijk

Reputation: 770

The problems was indeed at the ingress, not so much with the settings, but with the routing. The routing used above, rewrites the targets to / for all requests. My backend actually has a page there, which is CSRF protected. It went to that page instead of the login page. Changing the ingress to below yielded better results.


apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:
  name: basic-ingress
  annotations:
    kubernetes.io/ingress.class: nginx
    cert-manager.io/cluster-issuer: letsencrypt-prod
    nginx.ingress.kubernetes.io/rewrite-target: /$1
    kubernetes.io/ingress.allow-http: "true"
    nginx.ingress.kubernetes.io/ssl-redirect: "true"
spec:
  tls:
  - hosts:
    - XXXXXXXXXX
    secretName: tls-secret
  rules:
  - host: XXXXXX
    http:
      paths:
      - path: /?(.*)
        pathType: Prefix
        backend:
          service:
            name: frontend
            port:
              number: 80
      - path: /api/?(.*)
        pathType: Prefix
        backend:
          service:
            name: backend
            port:
              number: 8080

Upvotes: 1

Related Questions