OpenMCF logoOpenMCF

Loading...

Kubernetes Namespace

Deploys a Kubernetes namespace with optional resource quotas, LimitRanges, network policies, service mesh sidecar injection, and Pod Security Standards enforcement. Configuration is abstracted into T-shirt-sized resource profiles and declarative network isolation rules, so each namespace is created with resource limits and network isolation configured from the start.

What Gets Created

When you deploy a KubernetesNamespace resource, OpenMCF provisions:

  • Namespace — a Kubernetes Namespace with merged labels (user-specified plus standard management labels) and annotations (user-specified plus service-mesh annotations when enabled)
  • ResourceQuota — enforces CPU, memory, and object-count limits for the namespace, created only when a resourceProfile preset or custom quota is configured
  • LimitRange — sets default CPU and memory requests/limits for containers that do not declare their own, created only when custom defaultLimits are provided
  • Ingress NetworkPolicy — a default-deny ingress policy that allows traffic only from pods within the namespace and from explicitly listed namespaces, created only when networkConfig.isolateIngress is true
  • Egress NetworkPolicy — a default-deny egress policy that allows DNS traffic to kube-system, traffic within the namespace, and traffic to explicitly listed CIDR blocks, created only when networkConfig.restrictEgress is true

Prerequisites

  • Kubernetes credentials configured via environment variables or OpenMCF provider config
  • A running Kubernetes cluster reachable from the deployment environment
  • A CNI plugin that supports NetworkPolicy (e.g., Calico, Cilium) if using ingress isolation or egress restriction
  • A service mesh control plane (Istio, Linkerd, or Consul Connect) already installed on the cluster if enabling service mesh injection

Quick Start

Create a file namespace.yaml:

apiVersion: kubernetes.openmcf.org/v1
kind: KubernetesNamespace
metadata:
  name: my-namespace
  labels:
    openmcf.org/provisioner: pulumi
    pulumi.openmcf.org/organization: my-org
    pulumi.openmcf.org/project: my-project
    pulumi.openmcf.org/stack.name: dev.KubernetesNamespace.my-namespace
spec:
  name: my-namespace

Deploy:

openmcf apply -f namespace.yaml

This creates a bare namespace named my-namespace with standard OpenMCF management labels. No quotas, network policies, or service mesh injection are applied.

Configuration Reference

Required Fields

FieldTypeDescriptionValidation
spec.namestringThe Kubernetes namespace name. Used as metadata.name on the created Namespace.1–63 characters, valid DNS label (lowercase alphanumeric and hyphens, no leading/trailing hyphens)

Optional Fields

FieldTypeDefaultDescription
spec.targetCluster.clusterKindenum—Kubernetes cluster kind. Valid values: AwsEksCluster, GcpGkeCluster, AzureAksCluster, DigitalOceanKubernetesCluster, CivoKubernetesCluster.
spec.targetCluster.clusterNamestring—Name of the target Kubernetes cluster in the same environment.
spec.labelsmap<string, string>{}Additional labels merged onto the Namespace. Standard management labels (managed-by, resource, resource-kind) are always added.
spec.annotationsmap<string, string>{}Additional annotations merged onto the Namespace. Service-mesh injection annotations are added automatically when serviceMeshConfig is enabled.
spec.resourceProfile.presetenum—T-shirt-sized resource profile. One of small, medium, large, xlarge. Mutually exclusive with resourceProfile.custom. See table below.
spec.resourceProfile.custom.cpu.requestsstring—Total CPU requests quota (e.g., "4", "4000m").
spec.resourceProfile.custom.cpu.limitsstring—Total CPU limits quota (e.g., "8", "8000m").
spec.resourceProfile.custom.memory.requestsstring—Total memory requests quota (e.g., "8Gi").
spec.resourceProfile.custom.memory.limitsstring—Total memory limits quota (e.g., "16Gi").
spec.resourceProfile.custom.objectCounts.podsint32—Maximum number of pods. Must be >= 1.
spec.resourceProfile.custom.objectCounts.servicesint32—Maximum number of services. Must be >= 1.
spec.resourceProfile.custom.objectCounts.configmapsint32—Maximum number of ConfigMaps. Must be >= 1.
spec.resourceProfile.custom.objectCounts.secretsint32—Maximum number of Secrets. Must be >= 1.
spec.resourceProfile.custom.objectCounts.persistentVolumeClaimsint32—Maximum number of PVCs. Must be >= 0.
spec.resourceProfile.custom.objectCounts.loadBalancersint32—Maximum number of LoadBalancer services. Must be >= 0.
spec.resourceProfile.custom.defaultLimits.defaultCpuRequeststring—Default CPU request injected into containers without explicit values (e.g., "100m"). Triggers LimitRange creation.
spec.resourceProfile.custom.defaultLimits.defaultCpuLimitstring—Default CPU limit (e.g., "1000m").
spec.resourceProfile.custom.defaultLimits.defaultMemoryRequeststring—Default memory request (e.g., "128Mi").
spec.resourceProfile.custom.defaultLimits.defaultMemoryLimitstring—Default memory limit (e.g., "512Mi").
spec.networkConfig.isolateIngressboolfalseWhen true, creates a NetworkPolicy that denies all ingress except from the same namespace and from allowedIngressNamespaces.
spec.networkConfig.restrictEgressboolfalseWhen true, creates a NetworkPolicy that denies all egress except DNS to kube-system, same-namespace traffic, and allowedEgressCidrs.
spec.networkConfig.allowedIngressNamespacesstring[][]Namespace names permitted to send ingress traffic to this namespace. Only effective when isolateIngress is true.
spec.networkConfig.allowedEgressCidrsstring[][]CIDR blocks that pods may reach (e.g., "10.0.0.0/8"). Only effective when restrictEgress is true.
spec.networkConfig.allowedEgressDomainsstring[][]DNS domains that pods may reach (e.g., "api.stripe.com"). Requires a CNI with DNS-based policy support (Calico or Cilium).
spec.serviceMeshConfig.enabledboolfalseWhen true, adds mesh-specific sidecar injection annotations to the namespace. Requires meshType to be set.
spec.serviceMeshConfig.meshTypeenum—Service mesh type. One of istio, linkerd, consul. Required when serviceMeshConfig.enabled is true.
spec.serviceMeshConfig.revisionTagstring—Istio revision tag (e.g., "prod-stable", "1-19-5"). Istio-specific; sets istio.io/rev instead of the global istio-injection annotation. Max 63 characters.
spec.podSecurityStandardenumunspecifiedPod Security Standards enforcement level. One of privileged, baseline, restricted. Sets the pod-security.kubernetes.io/enforce label on the namespace.

Built-in resource profile sizes:

PresetCPU Req/LimitMemory Req/LimitPodsServicesConfigMapsSecretsPVCsLBs
small2 / 44Gi / 8Gi2010505052
medium4 / 88Gi / 16Gi5020100100103
large8 / 1616Gi / 32Gi10040200200205
xlarge16 / 3232Gi / 64Gi200804004004010

Examples

Basic Namespace with a Resource Profile

A development namespace with the small resource profile to set guardrails on resource consumption:

apiVersion: kubernetes.openmcf.org/v1
kind: KubernetesNamespace
metadata:
  name: dev-team-alpha
  labels:
    openmcf.org/provisioner: pulumi
    pulumi.openmcf.org/organization: my-org
    pulumi.openmcf.org/project: my-project
    pulumi.openmcf.org/stack.name: dev.KubernetesNamespace.dev-team-alpha
spec:
  name: dev-team-alpha
  labels:
    team: alpha
    cost-center: engineering
  resourceProfile:
    preset: small

Network-Isolated Namespace with Pod Security

A staging namespace that locks down both ingress and egress, allows traffic from a shared monitoring namespace, permits outbound access to an internal subnet, and enforces the baseline Pod Security Standard:

apiVersion: kubernetes.openmcf.org/v1
kind: KubernetesNamespace
metadata:
  name: staging-backend
  labels:
    openmcf.org/provisioner: pulumi
    pulumi.openmcf.org/organization: my-org
    pulumi.openmcf.org/project: my-project
    pulumi.openmcf.org/stack.name: staging.KubernetesNamespace.staging-backend
spec:
  name: staging-backend
  labels:
    team: backend
    environment: staging
  resourceProfile:
    preset: medium
  networkConfig:
    isolateIngress: true
    restrictEgress: true
    allowedIngressNamespaces:
      - monitoring
      - istio-system
    allowedEgressCidrs:
      - "10.0.0.0/8"
  podSecurityStandard: baseline

Full-Featured Production Namespace with Service Mesh and Custom Quotas

A production namespace with Istio sidecar injection pinned to a specific revision, custom resource quotas and default container limits, full network isolation, and the restricted Pod Security Standard:

apiVersion: kubernetes.openmcf.org/v1
kind: KubernetesNamespace
metadata:
  name: prod-payments
  labels:
    openmcf.org/provisioner: pulumi
    pulumi.openmcf.org/organization: my-org
    pulumi.openmcf.org/project: my-project
    pulumi.openmcf.org/stack.name: prod.KubernetesNamespace.prod-payments
spec:
  name: prod-payments
  labels:
    team: payments
    compliance: pci-dss
  annotations:
    janitor/ttl: "never"
  targetCluster:
    clusterKind: GcpGkeCluster
    clusterName: prod-us-central1
  resourceProfile:
    custom:
      cpu:
        requests: "12"
        limits: "24"
      memory:
        requests: "24Gi"
        limits: "48Gi"
      objectCounts:
        pods: 150
        services: 30
        configmaps: 200
        secrets: 200
        persistentVolumeClaims: 50
        loadBalancers: 5
      defaultLimits:
        defaultCpuRequest: "100m"
        defaultCpuLimit: "2000m"
        defaultMemoryRequest: "128Mi"
        defaultMemoryLimit: "1Gi"
  networkConfig:
    isolateIngress: true
    restrictEgress: true
    allowedIngressNamespaces:
      - istio-system
      - monitoring
      - logging
    allowedEgressCidrs:
      - "10.0.0.0/8"
      - "172.16.0.0/12"
  serviceMeshConfig:
    enabled: true
    meshType: istio
    revisionTag: prod-stable
  podSecurityStandard: restricted

Stack Outputs

After deployment, the following outputs are available in status.outputs:

OutputTypeDescription
namespacestringName of the created Kubernetes namespace
namespaceIdstringFully qualified namespace identifier (same as namespace)
resourceQuotasAppliedstring"true" if ResourceQuota objects were created
limitRangesAppliedstring"true" if LimitRange objects were created
networkPoliciesAppliedstring"true" if NetworkPolicy objects were created
serviceMeshEnabledstring"true" if the namespace is configured for automatic sidecar injection
serviceMeshTypestringConfigured mesh type (istio, linkerd, consul, or empty)
podSecurityStandardstringApplied Pod Security Standard level (privileged, baseline, restricted, or empty)
labelsJsonstringJSON representation of all labels applied to the namespace
annotationsJsonstringJSON representation of all annotations applied to the namespace

Related Components

  • KubernetesDeployment — deploys containerized workloads into namespaces managed by this component
  • KubernetesPostgres — deploys PostgreSQL into a namespace, often co-deployed alongside application namespaces
  • KubernetesRedis — deploys Redis into a namespace for caching and pub/sub workloads

Next article

Kubernetes NATS

Kubernetes NATS Deploys a NATS messaging cluster on Kubernetes using the official NATS Helm chart, with optional JetStream persistence, authentication (bearer-token or basic-auth), TLS encryption, external ingress via LoadBalancer, and declarative stream/consumer management through the NACK JetStream controller. What Gets Created When you deploy a KubernetesNats resource, OpenMCF provisions: Namespace — created only when createNamespace is true Helm Release (NATS) — deploys a NATS server...
Read next article
Presets
3 ready-to-deploy configurationsView presets →