Skip to content

Cluster Policies

Kupe checks workloads and rejects settings that break a required policy. This page is the reference: what’s blocked, what defaults get applied on your behalf, and the exact fix for each common rejection.

Policy Mode What it means for you
No privileged or host-level access Enforce Privileged containers, host networking, host PID/IPC, and hostPath volumes are rejected
Non-root containers Enforce runAsNonRoot: true and allowPrivilegeEscalation: false are required
Drop all capabilities Enforce capabilities.drop: ["ALL"] is required; only NET_BIND_SERVICE may be added back
Resource requests required Enforce CPU and memory requests are required; defaults are applied if you omit them
Default service account token mount Automatic The default ServiceAccount does not mount a token unless you opt in
No NodePort / LoadBalancer services Enforce Use ClusterIP plus an HTTPRoute for external access
No Service externalIPs Enforce Setting spec.externalIPs on a Service is rejected; it lets a node intercept traffic destined to those addresses
HTTPRoute hostname validation Enforce Public route hostnames must stay within your tenant’s allowed domain space
Read-only root filesystem Audit readOnlyRootFilesystem: true is recommended but not yet required
Seccomp profile Audit seccompProfile.type: RuntimeDefault or Localhost is recommended but not yet required
Image registry policy Audit Registry usage is logged for review; deploys are not blocked

Omitted requests default to 100m CPU and 128Mi memory. Omitted limits match requests. Set both explicitly when your application needs more headroom:

resources:
requests: { cpu: 100m, memory: 128Mi }
limits: { cpu: 400m, memory: 512Mi }

Deploy applications in your own namespaces. Leave kube-system and Kupe-managed components unchanged. Use the default StorageClass for volumes and omit priorityClassName unless your workload requires a supported value.

Set capabilities.drop: ["ALL"] on every container. Only NET_BIND_SERVICE may be added back without an exception. Contact support if a workload needs another capability. All other workload rules still apply.

When a policy blocks your deployment, the error message Kupe returns includes the exact YAML to add. This section collects the most common ones for reference.

“Tenant containers must set runAsNonRoot: true”

Section titled ““Tenant containers must set runAsNonRoot: true””

Add a securityContext block to your pod spec:

apiVersion: apps/v1
kind: Deployment
metadata:
name: my-app
spec:
template:
spec:
securityContext:
runAsNonRoot: true
runAsUser: 65532 # nobody
runAsGroup: 65532
seccompProfile:
type: RuntimeDefault
containers:
- name: app
image: ghcr.io/your-org/app:v1.0.0
securityContext:
runAsNonRoot: true
allowPrivilegeEscalation: false
readOnlyRootFilesystem: true
capabilities:
drop: ["ALL"]

If your image only runs as root, the fastest fix is usually to switch to a non-root base image (Chainguard, Red Hat UBI, distroless, or Bitnami’s nonroot variants). Most official images on Docker Hub (postgres, redis, nginx, mysql, mariadb) support non-root without modification.

“Containers must drop ALL capabilities”

Section titled ““Containers must drop ALL capabilities””

Two options:

Option 1: drop everything.

containers:
- name: app
securityContext:
capabilities:
drop: ["ALL"]

Option 2: drop all and add NET_BIND_SERVICE back, the only allowed add-back.

containers:
- name: app
securityContext:
capabilities:
drop: ["ALL"]
add: ["NET_BIND_SERVICE"]

Anything beyond NET_BIND_SERVICE requires a platform-issued policy exception. See Capability exemptions above.

“CPU and memory requests are required”

Section titled ““CPU and memory requests are required””

You rarely need to set these yourself; Kupe applies sensible defaults for any container that omits them. If you’re hitting this error anyway, fill in the missing request field:

containers:
- name: app
resources:
requests:
cpu: 100m
memory: 128Mi
# limits are optional; omitted limits default to match requests.

“NodePort and LoadBalancer services are not allowed”

Section titled ““NodePort and LoadBalancer services are not allowed””

Change your Service to ClusterIP and create an HTTPRoute for external access:

apiVersion: v1
kind: Service
metadata:
name: my-app
spec:
type: ClusterIP # ← was NodePort or LoadBalancer
selector:
app: my-app
ports:
- port: 80
targetPort: 8080

Then follow the standard route pattern in HTTP Routes to publish the service.

“Services must not set spec.externalIPs”

Section titled ““Services must not set spec.externalIPs””

Remove externalIPs from your Service spec:

apiVersion: v1
kind: Service
metadata:
name: my-app
spec:
type: ClusterIP
# externalIPs: ["1.2.3.4"] # ← remove this
selector:
app: my-app
ports:
- port: 80
targetPort: 8080

For external access, use a type: ClusterIP Service plus an HTTPRoute through the Gateway API, the same pattern as the NodePort/LoadBalancer fix above.

If you see a registry policy warning or error

Section titled “If you see a registry policy warning or error”

On the standard Kupe tenant policy set, the registry policy is currently in audit mode. Registry usage is logged, but deploys are not blocked. If your cluster is using a stricter custom policy and a deploy is blocked, contact support. See Image Registry Allowlist for the current approved list and how to request additions.

Enforced policies reject a deployment. Audit policies report findings but allow it to run. Read-only filesystems, seccomp profiles, and registry selection are currently audited. Kupe will give notice before changing these requirements.