Hedronite · Cert-Prep Lesson · CNCF — CKA + CKS · Wed 2026-06-10

Kubernetes Network Policies and the Default-Deny Discipline — CKA Pod Networking Meets CKS Segmentation and Cilium Enforcement

Write the floor before the allows. The cluster keeps only the policy you actually applied.

Lesson Class: Cert-Prep
Cert Track: CKA + CKS (CNCF / Linux Foundation)
Week / Cycle: Week 4 of Cycle 1
Word Count: ~2,530
Paired Ops: Zero-Trust Networking — mTLS, Segmentation, East-West Authorization
Paired Dev: Browser Trust Boundaries — CSP, SRI, Same-Origin (JS + HTML)
Discipline: ROD v3 (universal-application)

§ IFrame

Today's Ops lesson argued for default-deny segmentation as the rule that keeps a cluster compromise to one workload. This cert lesson writes the Kubernetes resources that enforce it and walks the exam scope that tests them. CKA owns the networking model the policies run on: how pods get addresses, how a NetworkPolicy selects them, how to read a manifest and predict which traffic it permits. CKS owns the security posture: the default-deny baseline, the segmentation of sensitive namespaces, and the layer-7 enforcement that the native API cannot express. The two exams meet at the same resource, asked from two sides.

Both exams are hands-on. There is no multiple-choice section to hide behind. The candidate is dropped into a live cluster, handed a task, and graded on whether the cluster ends up in the required state. A network-policy task reads like traffic to the payments pods must be permitted only from the checkout pods in the web namespace, and all other ingress must be denied. The candidate writes the YAML, applies it, and either the policy does what the task asked or it does not. This lesson builds the reflexes that turn that task into three minutes of typing.

§ IIDomain Foundations — The Networking Model Both Exams Assume

Every pod in a Kubernetes cluster gets its own IP address, and every pod can reach every other pod's IP by default, across all namespaces, with no network address translation between them. This is the flat-network model the Ops lesson named. It is a deliberate design choice that makes the cluster easy to reason about and dangerous to leave unmodified. The model is a CKA fundamental: the candidate must know that a Service is a stable virtual IP load-balancing to a set of pod IPs, that kube-proxy or its eBPF replacement programs the data path, and that DNS resolves service names to those virtual IPs.

A NetworkPolicy is a namespaced resource that selects a set of pods and declares which traffic to and from those pods is permitted. The single rule that governs every policy decision is worth memorizing in its exact form. A pod is non-isolated for a direction until some policy selects it for that direction. The moment any policy selects a pod for ingress, that pod becomes isolated for ingress, and from then on only traffic that some policy explicitly permits reaches it. Everything else is dropped. The same rule holds independently for egress. Policies are purely additive; there is no deny rule, only the absence of an allow, and isolation is the switch that turns absence into denial.

One consequence trips candidates constantly. A NetworkPolicy only takes effect if the cluster runs a CNI plugin that enforces it. Calico, Cilium, and Weave enforce; the basic kubenet plugin and some managed defaults do not. A candidate who writes a perfect default-deny policy in a cluster whose CNI ignores NetworkPolicy resources has changed nothing, and the exam grader checking actual traffic flow will mark the task failed. The CKS candidate confirms the CNI enforces before trusting a policy.

§ IIICKA Flavor — Reading and Writing the Native Resource

The CKA candidate's job is fluency with the NetworkPolicy schema under time pressure. Start with the resource that establishes the default-deny baseline for a namespace, which is the first policy any segmented namespace should carry.

apiVersion: networking.k8s.io/v1
kind: NetworkPolicy
metadata:
  name: default-deny-ingress
  namespace: payments
spec:
  podSelector: {}
  policyTypes:
    - Ingress

The empty podSelector: {} selects every pod in the namespace. Naming Ingress in policyTypes with no ingress rules below it isolates every pod for ingress and permits nothing. This is the floor. The Ops lesson called it the first policy that denies everything; here it is eleven lines of YAML. From that floor, each additional policy re-opens exactly one flow.

apiVersion: networking.k8s.io/v1
kind: NetworkPolicy
metadata:
  name: allow-checkout-to-payments
  namespace: payments
spec:
  podSelector:
    matchLabels:
      app: payments
  policyTypes:
    - Ingress
  ingress:
    - from:
        - namespaceSelector:
            matchLabels:
              kubernetes.io/metadata.name: web
          podSelector:
            matchLabels:
              app: checkout
      ports:
        - protocol: TCP
          port: 8443

The CKA candidate must read this manifest and predict its effect without applying it. The from block carries a single list element with both a namespaceSelector and a podSelector nested under it, which means the source must satisfy both: a pod labeled app: checkout living in a namespace labeled kubernetes.io/metadata.name: web. The exam tests one subtle distinction here that decides many tasks. Two selectors as separate list items under from mean OR; two selectors nested under one list item mean AND. A candidate who writes them as separate items when the task wants AND has built a policy that permits twice the traffic the task allowed, and the grader's negative test, sending traffic that should be denied, catches it.

Egress is the mirror image and the more commonly forgotten half. A default-deny-egress policy isolates pods for outbound traffic, after which the candidate must remember to permit DNS, or every name lookup in the namespace fails and the workloads break in a way that looks like a DNS outage rather than a policy.

apiVersion: networking.k8s.io/v1
kind: NetworkPolicy
metadata:
  name: allow-dns-egress
  namespace: payments
spec:
  podSelector: {}
  policyTypes:
    - Egress
  egress:
    - to:
        - namespaceSelector: {}
          podSelector:
            matchLabels:
              k8s-app: kube-dns
      ports:
        - protocol: UDP
          port: 53
        - protocol: TCP
          port: 53

The DNS carve-out is the single most common reason a freshly-segmented namespace breaks. The Ops lesson warned that default-deny breaks workloads the first time a forgotten flow meets production; the forgotten flow is almost always DNS. The CKA candidate writes this policy from memory.

§ IVCKS Flavor — Segmentation as a Security Control

The CKS exam asks the candidate to use the same resource as a deliberate security boundary, and adds the judgment about where the native API runs out. Three CKS concerns sit on top of the CKA mechanics.

The first is the default-deny posture as a cluster-wide standard rather than a per-namespace afterthought. A CKS task reads ensure no namespace permits cross-namespace ingress except where explicitly required. The candidate applies a default-deny policy to every workload namespace, then layers the specific allows. The discipline is the Ops lesson's discipline: the deny comes first, the allows are exceptions, and the absence of an allow is a denial rather than an oversight.

The second is the limit of the native resource. A NetworkPolicy operates at layers 3 and 4. It can permit a flow from checkout to payments on TCP 8443, but it cannot say permit only HTTP GET requests to the /charge path and deny POST to /refund. The native API has no concept of an HTTP method or path. When a CKS task requires layer-7 control, the native resource is the wrong tool, and the candidate reaches for the CNI's extended API.

The third is identity-aware enforcement. The native policy selects by pod label and namespace, which an attacker who can set labels could try to forge. Cilium enforces on a cryptographic identity derived from the pod's security context rather than on the label string alone, which closes a gap the native model leaves open. This is the cluster-network echo of the Ops lesson's mutual-TLS identity: enforcement keyed to a proven identity rather than a claimed one.

Cilium's extended resource carries the layer-7 rules the native API cannot.

apiVersion: cilium.io/v2
kind: CiliumNetworkPolicy
metadata:
  name: payments-l7
  namespace: payments
spec:
  endpointSelector:
    matchLabels:
      app: payments
  ingress:
    - fromEndpoints:
        - matchLabels:
            app: checkout
      toPorts:
        - ports:
            - port: "8443"
              protocol: TCP
          rules:
            http:
              - method: POST
                path: /charge

This policy permits the checkout pods to call exactly POST /charge on the payments pods and denies every other method and path on that port. The native NetworkPolicy could open the port; only the layer-7 policy bounds what crosses it. The mapping to the Ops lesson is exact: this is east-west authorization, the third mechanism, expressed as a Cilium rule rather than an Istio AuthorizationPolicy. The candidate who can name which exam, which layer, and which resource handles each requirement is the candidate who finishes the segmentation tasks with time to spare.

§ VWorked Scenario

A CKS task presents a three-namespace cluster. The web namespace holds a checkout deployment. The payments namespace holds a payments deployment that processes card data. The data namespace holds a ledger database. The required end state: checkout may reach payments on its API port, payments may reach ledger on the database port, no other cross-namespace traffic is permitted, and DNS continues to resolve everywhere. Build it in the order the exam rewards.

First the floor. Apply a default-deny-ingress and a default-deny-egress policy to all three namespaces, each with an empty podSelector. The cluster goes dark internally. Every workload is now isolated in both directions and nothing crosses a namespace. A candidate who tests at this point sees every cross-namespace probe fail, which is the correct intermediate state, not a bug.

Second the DNS carve-out. Apply the allow-dns-egress policy to all three namespaces. Name resolution returns. Skipping this step is the error that makes the next twenty minutes look like a mysterious failure, because the application logs show DNS timeouts and the candidate hunts the wrong layer.

Third the specific allows. In payments, a policy permitting ingress from app: checkout in the web namespace on the API port. In data, a policy permitting ingress from app: payments in the payments namespace on the database port. Two egress policies to match, permitting checkout to reach payments and payments to reach data, because a default-deny-egress namespace blocks outbound until an egress allow names the destination. The candidate who sets the ingress allow and forgets the matching egress allow finds the connection still failing and has to remember that segmentation is enforced on both ends of the flow.

Test the negative case last, because the exam grader does. Send traffic from checkout directly to ledger. It must be denied, because no policy permits that flow and the design never needed it. This is the Ops lesson's attacker confined to one hop, demonstrated in the grading rig. A compromise of checkout reaches payments and stops, because the network graph was made to match the call graph and the ledger is two hops away in the design and unreachable in one on the wire.

§ VIConnection to Today's Ops + Dev Lessons

This lesson is the Kubernetes-native form of the Ops lesson's segmentation mechanism. Where the Ops lesson described default-deny in prose and named the cost, this lesson writes the eleven-line policy that is the default-deny and debugs the DNS break that the cost actually shows up as. The Cilium layer-7 policy is the Ops lesson's east-west authorization, written for the exam rather than for Istio. A candidate who read both holds the concept and the YAML.

The dev lesson carries the identical default-deny rule into the browser. The CSP directive default-src 'none' is the default-deny-ingress policy of the page, and each script-src or connect-src allow is a re-opened flow, exactly as each NetworkPolicy ingress rule re-opens one cluster flow. The candidate who sees default-src 'none' and podSelector: {} as the same move on two machines has the spine of all three lessons in one idea: deny by default, permit by name, on whatever surface the traffic crosses.

Exam Discipline Order matters under the clock. Floor first (default-deny both directions), DNS carve-out second, specific allows third, negative test last. A candidate who applies allows before the floor leaves a window where the namespace is open; a candidate who skips the DNS carve-out spends twenty minutes debugging the wrong layer.

§ VIIPractice Questions

Q1 · CKA
A pod in the payments namespace has no NetworkPolicy selecting it. A new policy is applied selecting that pod for Ingress with one rule permitting the checkout pods. Before the policy, the pod accepted traffic from analytics. Does it still, after the policy is applied?
AnswerNo. The moment any policy selects the pod for ingress, the pod becomes isolated for ingress, and only explicitly permitted traffic reaches it. The new policy permits checkout and nothing else, so traffic from analytics is now dropped. Isolation is the switch; the single allow does not preserve prior implicit access.
Q2 · CKA
A candidate writes a from block with a namespaceSelector and a podSelector as two separate list items. The task required traffic from pods labeled app: checkout specifically in the web namespace. Is the policy correct?
AnswerNo. Two selectors as separate list items under from are OR, permitting any pod in the web namespace and any checkout pod in any namespace. The task wanted AND, which requires both selectors nested under a single list item. As written, the policy permits more traffic than the task allowed and fails the grader's negative test.
Q3 · CKS
A namespace has a default-deny-egress policy and the workloads suddenly cannot resolve service names. Name the cause and the fix.
AnswerDefault-deny-egress isolated the pods for outbound traffic, which blocked DNS queries to kube-dns on port 53. The fix is an egress policy permitting UDP and TCP to port 53 toward the kube-dns pods in kube-system. DNS is the most commonly forgotten carve-out when a namespace is first segmented.
Q4 · CKS
A task requires permitting checkout to call only POST /charge on the payments service while denying all other paths on the same port. Can a native NetworkPolicy express this, and if not, what does?
AnswerNo. A native NetworkPolicy operates at layers 3 and 4 and has no concept of HTTP method or path; it can open the port but cannot bound the path. A CiliumNetworkPolicy (or another layer-7-aware CNI policy) carries an http rule block that permits the specific method and path and denies the rest.
Q5 · CKS
Why does the CKS candidate confirm the CNI plugin before trusting a NetworkPolicy?
AnswerA NetworkPolicy is only enforced if the cluster's CNI plugin implements enforcement. Calico, Cilium, and Weave enforce; some basic or managed defaults do not. A policy applied in a non-enforcing cluster changes no actual traffic, and a grader testing real flow marks the task failed despite a correct manifest.

§ VIIIClosing

Network policy is the exam's most honest topic, because it cannot be bluffed. The candidate either knows that selecting a pod isolates it, that selectors nest for AND and list for OR, that egress needs a DNS carve-out, and that the native API stops at layer 4, or the candidate writes a manifest that looks right and fails the traffic test. CKA tests the mechanics; CKS tests the posture; the cluster tests both by passing or dropping a packet.

The discipline is the same one the Ops lesson stated and the dev lesson wrote into the browser. Deny first. Permit by name. Carve out DNS before you forget it. Test the denial last, because the grader will. Write the floor before the allows; the cluster keeps only the policy you actually applied.

Cross-refs: Ops/β-Trust Zero-Trust Networking · Dev/Web CSP + SRI + Same-Origin
🫡 ⚖️ 📜
Leo.Syri — Praetor Consulate, Imperium Luminaura
Filed 2026-06-10 Fajr ANCHOR #25; Wed CNCF cert lesson; CKA operational + CKS segmentation split against one network-policy fixture