<p>I am trying to host my own Nextcloud server using Kubernetes.</p>
<p>I want my Nextcloud server to be accessed from <code>http://localhost:32738/nextcloud</code> but every time I access that URL, it gets redirected to <code>http://localhost:32738/login</code> and gives me <code>404 Not Found</code>.</p>
<p>If I replace the path with:</p>
<pre><code>path: /
</code></pre>
<p>then, it works without problems on <code>http://localhost:32738/login</code> but as I said, it is not the solution I am looking for. The login page should be accessed from <code>http://localhost:32738/nextcloud/login</code>.</p>
<p>Going to <code>http://127.0.0.1:32738/nextcloud/</code> does work for the initial setup but after that it becomes inaccessible as it always redirects to:</p>
<pre><code>http://127.0.0.1:32738/apps/dashboard/
</code></pre>
<p>and not to:</p>
<pre><code>http://127.0.0.1:32738/nextcloud/apps/dashboard/
</code></pre>
<p>This is my yaml:</p>
<pre><code>#Nextcloud-Dep
apiVersion: apps/v1
kind: Deployment
metadata:
  name: nextcloud-server
  labels:
    app: nextcloud
spec:
  replicas: 1
  selector:
    matchLabels:
      pod-label: nextcloud-server-pod
  template:
    metadata:
      labels:
        pod-label: nextcloud-server-pod
    spec:
      containers:
      - name: nextcloud
        image: nextcloud:22.2.0-apache
        env:
        - name: POSTGRES_DB
          valueFrom:
            secretKeyRef:
              name: nextcloud
              key: db-name
        - name: POSTGRES_USER
          valueFrom:
            secretKeyRef:
              name: nextcloud
              key: db-username
        - name: POSTGRES_PASSWORD
          valueFrom:
            secretKeyRef:
              name: nextcloud
              key: db-password
        - name: POSTGRES_HOST
          value: nextcloud-database:5432
        volumeMounts:
        - name: server-storage
          mountPath: /var/www/html
          subPath: server-data
      volumes:
      - name: server-storage
        persistentVolumeClaim:
          claimName: nextcloud
---
#Nextcloud-Serv
apiVersion: v1
kind: Service
metadata:
  name: nextcloud-server
  labels:
    app: nextcloud
spec:
  selector:
    pod-label: nextcloud-server-pod
  ports:
  - port: 80
    protocol: TCP
    name: nextcloud-server
---
#Database-Dep
apiVersion: apps/v1
kind: Deployment
metadata:
  name: nextcloud-database
  labels:
    app: nextcloud
spec:
  replicas: 1
  selector:
    matchLabels:
      pod-label: nextcloud-database-pod
  template:
    metadata:
      labels:
        pod-label: nextcloud-database-pod
    spec:
      containers:
      - name: postgresql
        image: postgres:13.4
        env:
        - name: POSTGRES_DATABASE
          valueFrom:
            secretKeyRef:
              name: nextcloud
              key: db-name
        - name: POSTGRES_USER
          valueFrom:
            secretKeyRef:
              name: nextcloud
              key: db-username
        - name: POSTGRES_PASSWORD
          valueFrom:
            secretKeyRef:
              name: nextcloud
              key: db-password
        - name: POSTGRES_ROOT_PASSWORD
          valueFrom:
            secretKeyRef:
              name: nextcloud
              key: db-rootpassword
        - name: PGDATA
          value: /var/lib/postgresql/data/
        volumeMounts:
        - name: database-storage
          mountPath: /var/lib/postgresql/data/
          subPath: data
      volumes:
      - name: database-storage
        persistentVolumeClaim:
          claimName: nextcloud
---
#Database-Serv
apiVersion: v1
kind: Service
metadata:
  name: nextcloud-database
  labels:
    app: nextcloud
spec:
  selector:
    pod-label: nextcloud-database-pod
  ports:
  - port: 5432
    protocol: TCP
    name: nextcloud-database
---
#PV
apiVersion: v1
kind: PersistentVolume
metadata:
  name: nextcloud-pv
  labels:
    type: local
spec:
  capacity:
    storage: 8Gi
  accessModes:
    - ReadWriteOnce
  hostPath:
    path: &quot;/tmp&quot;
---
#PVC
apiVersion: v1
kind: PersistentVolumeClaim
metadata:
  name: nextcloud
spec:
  accessModes:
    - ReadWriteOnce
  resources:
    requests:
      storage: 8Gi
---
#Ingress
apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:
  name: nextcloud-ingress
  annotations:
    kubernetes.io/ingress.class: nginx
    nginx.ingress.kubernetes.io/use-regex: &quot;true&quot;
    nginx.ingress.kubernetes.io/rewrite-target: /$1
spec:
  rules:
  - http:
      paths:
      - backend:
          service:
            name: nextcloud-server
            port:
              number: 80
        pathType: Prefix
        path: /nextcloud(/.*)
---
#Secret
apiVersion: v1
kind: Secret
metadata:
  name: nextcloud
  labels:
    app: nextcloud
immutable: true
stringData:
  db-name: nextcloud
  db-username: nextcloud
  db-password: changeme
  db-rootpassword: longpassword
  username: admin
  password: changeme
</code></pre>
<p>ingress-nginx was installed with:</p>
<pre><code>helm install nginx ingress-nginx/ingress-nginx
</code></pre>
<p>Please tell me if you want me to supply more information.</p>

Paul Schuldesz
<p>In your case there is a difference between the exposed URL in the backend service and the specified path in the Ingress rule. That's why you get an error.</p>
<p>To avoid that you can use rewrite rule.</p>
<p>Using that one your ingress paths will be rewritten to value you provide.
This annotation <code>ingress.kubernetes.io/rewrite-target: /login</code> will rewrite the URL <code>/nextcloud/login</code> to <code>/login</code> before sending the request to the backend service.</p>
<p>But:</p>
<blockquote>
<p>Starting in Version 0.22.0, ingress definitions using the annotation nginx.ingress.kubernetes.io/rewrite-target are not backwards compatible with previous versions.</p>
</blockquote>
<p>On <a href="https://kubernetes.github.io/ingress-nginx/examples/rewrite/" rel="nofollow noreferrer">this documentation</a> you can find following example:</p>
<pre><code>$ echo '
apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:
  annotations:
    nginx.ingress.kubernetes.io/rewrite-target: /$2
  name: rewrite
  namespace: default
spec:
  rules:
  - host: rewrite.bar.com
    http:
      paths:
      - backend:
          serviceName: http-svc
          servicePort: 80
        path: /something(/|$)(.*)
' | kubectl create -f -
</code></pre>
<blockquote>
<p>In this ingress definition, any characters captured by <code>(.*)</code> will be assigned to the placeholder <code>$2</code>, which is then used as a parameter in the <code>rewrite-target</code> annotation.</p>
</blockquote>
<p>So in your URL you could see wanted <code>/nextcloud/login</code>, but rewriting will couse changing path to <code>/login</code> in the Ingress rule and finding your backend. I would suggest use one of following option:</p>
<pre><code>path: /nextcloud(/.*)
</code></pre>
<pre><code>nginx.ingress.kubernetes.io/rewrite-target: /$1
</code></pre>
<p>or</p>
<pre><code>path: /nextcloud/login
</code></pre>
<pre><code>nginx.ingress.kubernetes.io/rewrite-target: /login
</code></pre>
<p>See also <a href="https://docs.pivotal.io/pks/1-7/nsxt-ingress-rewrite-url.html" rel="nofollow noreferrer">this article</a>.</p>
