From d163a92ec6ff6653e2cf870aceac7b35e81f80b0 Mon Sep 17 00:00:00 2001 From: Will Anderson Date: Thu, 26 Mar 2026 11:13:25 -0500 Subject: [PATCH] fix: replace registry Ingress+Buffering with IngressRoute for streaming The Buffering middleware was causing 413 on large Docker layer pushes by spooling entire request bodies to disk before forwarding. Docker's chunked blob upload protocol (PATCH/PUT with Content-Range) requires streaming, not buffering. Replace with IngressRoute CRDs + Certificate resources for direct streaming passthrough. responseForwarding.flushInterval=100ms ensures prompt chunk delivery to the registry backend. --- servers/legion/k8s/registry/ingress.yaml | 106 +++++++++++------------ 1 file changed, 52 insertions(+), 54 deletions(-) diff --git a/servers/legion/k8s/registry/ingress.yaml b/servers/legion/k8s/registry/ingress.yaml index 2082031..feb4ea1 100644 --- a/servers/legion/k8s/registry/ingress.yaml +++ b/servers/legion/k8s/registry/ingress.yaml @@ -1,71 +1,69 @@ --- -# Middleware: allow unlimited body size for Docker image layer uploads -apiVersion: traefik.io/v1alpha1 -kind: Middleware +# Certificate for Docker registry (cert-manager — required for IngressRoute) +apiVersion: cert-manager.io/v1 +kind: Certificate metadata: - name: registry-chunked + name: registry-tls namespace: registry spec: - buffering: - maxRequestBodyBytes: 0 - maxResponseBodyBytes: 0 - memRequestBodyBytes: 0 - retryExpression: "" + secretName: registry-tls + issuerRef: + name: letsencrypt-prod + kind: ClusterIssuer + dnsNames: + - registry.neuralplatform.ai --- -# Docker registry ingress with chunked upload middleware -apiVersion: networking.k8s.io/v1 -kind: Ingress +# Docker registry — IngressRoute with no buffering middleware. +# Traefik streams blob data directly to the registry backend. +# The Buffering middleware was causing 413s on large layer pushes by +# spooling the entire body to disk before forwarding. +apiVersion: traefik.io/v1alpha1 +kind: IngressRoute metadata: name: registry namespace: registry - annotations: - traefik.ingress.kubernetes.io/router.entrypoints: websecure - cert-manager.io/cluster-issuer: letsencrypt-prod - traefik.ingress.kubernetes.io/router.middlewares: registry-chunked@kubernetescrd - nginx.ingress.kubernetes.io/proxy-body-size: "0" - nginx.ingress.kubernetes.io/proxy-read-timeout: "600" - nginx.ingress.kubernetes.io/proxy-send-timeout: "600" spec: - ingressClassName: traefik + entryPoints: + - websecure + routes: + - match: Host(`registry.neuralplatform.ai`) + kind: Rule + services: + - name: registry + port: 5000 + responseForwarding: + flushInterval: "100ms" tls: - - hosts: - - registry.neuralplatform.ai - secretName: registry-tls - rules: - - host: registry.neuralplatform.ai - http: - paths: - - path: / - pathType: Prefix - backend: - service: - name: registry - port: - number: 5000 + secretName: registry-tls +--- +# Certificate for Docker registry UI +apiVersion: cert-manager.io/v1 +kind: Certificate +metadata: + name: docker-ui-tls + namespace: registry +spec: + secretName: docker-ui-tls + issuerRef: + name: letsencrypt-prod + kind: ClusterIssuer + dnsNames: + - docker.neuralplatform.ai --- # Docker registry UI -apiVersion: networking.k8s.io/v1 -kind: Ingress +apiVersion: traefik.io/v1alpha1 +kind: IngressRoute metadata: name: registry-ui namespace: registry - annotations: - traefik.ingress.kubernetes.io/router.entrypoints: websecure - cert-manager.io/cluster-issuer: letsencrypt-prod spec: - ingressClassName: traefik + entryPoints: + - websecure + routes: + - match: Host(`docker.neuralplatform.ai`) + kind: Rule + services: + - name: registry-ui + port: 80 tls: - - hosts: - - docker.neuralplatform.ai - secretName: docker-ui-tls - rules: - - host: docker.neuralplatform.ai - http: - paths: - - path: / - pathType: Prefix - backend: - service: - name: registry-ui - port: - number: 80 + secretName: docker-ui-tls