Key Takeaways
- ✓AppArmor and SELinux add a Mandatory Access Control layer to containers
- ✓Profiles confine compromised processes by limiting file and network access
- ✓Combine AppArmor/SELinux with Pod Security Standards for defense in depth
AppArmor Kubernetes and SELinux constitute the two pillars of container security at the system level. These Mandatory Access Control (MAC) technologies restrict process actions beyond classic Unix permissions. A compromised container finds itself confined to a strict perimeter, limiting the impact of an exploit.
TL;DR: Deploy AppArmor profiles for each sensitive workload. Use SELinux on RHEL/CentOS distributions. Combine these mechanisms with Pod Security Standards for defense in depth.
Professionals who want to master these skills follow the LFS460 Kubernetes Security Fundamentals training.
What is AppArmor and why use it with Kubernetes?
AppArmor is a Linux security module that controls program capabilities via text profiles. Each profile defines accessible files, authorized capabilities, and permitted network operations.
Kubernetes natively supports AppArmor since version 1.4. This integration allows applying profiles to each container individually.
According to the CNCF Annual Survey 2025, 82% of organizations run Kubernetes in production. Each container without a security profile represents a potential attack vector.
| AppArmor Mode | Behavior | Usage |
|---|---|---|
| enforce | Blocks and logs | Production |
| complain | Logs without blocking | Development |
| disabled | No restrictions | Not recommended |
Key takeaway: AppArmor confines containerized processes. A restrictive profile prevents access to sensitive system files even if the container is compromised.
How to configure AppArmor Kubernetes for your pods?
Applying an AppArmor kubernetes profile is done via annotations on the pod or container.
Verify AppArmor availability
# Check AppArmor module on nodes
kubectl get nodes -o jsonpath='{range .items[*]}{.metadata.name}{"\t"}{.status.nodeInfo.containerRuntimeVersion}{"\n"}{end}'
# On a node, check loaded profiles
cat /sys/module/apparmor/parameters/enabled
aa-status
Create a custom AppArmor profile
# /etc/apparmor.d/k8s-restricted
#include <tunables/global>
profile k8s-restricted flags=(attach_disconnected,mediate_deleted) {
#include <abstractions/base>
# Deny access to sensitive mounts
deny /proc/** w,
deny /sys/** w,
deny /etc/passwd w,
deny /etc/shadow rw,
# Allow read access to /app
/app/** r,
/app/bin/* ix,
# Minimal capabilities
capability net_bind_service,
}
Load the profile on each node:
sudo apparmor_parser -r /etc/apparmor.d/k8s-restricted
To deepen Kubernetes cluster administration, check our complete guide.
Apply the profile to a pod
apiVersion: v1
kind: Pod
metadata:
name: secured-app
annotations:
container.apparmor.security.beta.kubernetes.io/app: localhost/k8s-restricted
spec:
containers:
- name: app
image: myapp:v1.0
securityContext:
allowPrivilegeEscalation: false
runAsNonRoot: true
Key takeaway: Deploy AppArmor profiles on all nodes before referencing them in pods. Use a DaemonSet to automate deployment.
How to use SELinux Kubernetes on RHEL distributions?
SELinux kubernetes offers an alternative to AppArmor on Red Hat, CentOS, and Fedora distributions. This MAC module uses security labels to control access.
Verify SELinux on nodes
# SELinux status
getenforce
sestatus
# Labels of containerized processes
ps -eZ | grep container
seLinuxOptions configuration in securityContext
apiVersion: v1
kind: Pod
metadata:
name: selinux-app
spec:
securityContext:
seLinuxOptions:
level: "s0:c123,c456"
containers:
- name: app
image: myapp:v1.0
securityContext:
seLinuxOptions:
type: "container_t"
level: "s0:c123,c456"
Common SELinux types for containers
| Type | Description | Restrictions |
|---|---|---|
| container_t | Default type | Limited filesystem access |
| container_runtime_t | Runtime (containerd) | Elevated privileges |
| spc_t | Super Privileged Container | No restrictions |
Warning: spc_t disables SELinux for the container. Reserve it for exceptional cases like node-level monitoring agents.
For a complete Kubernetes training, explore our paths including system security.
When to choose AppArmor Kubernetes versus SELinux?
The choice between AppArmor and SELinux depends on your Linux distribution and existing skills.
Technical comparison
| Criterion | AppArmor | SELinux |
|---|---|---|
| Distributions | Ubuntu, Debian, SUSE | RHEL, CentOS, Fedora |
| Syntax | Simple text profiles | Complex policies |
| Granularity | Path-based | Label-based |
| Learning curve | Moderate | High |
| Kubernetes support | Native (annotations) | Native (seLinuxOptions) |
Recommendations by use case
Use AppArmor if:
- Your nodes run on Ubuntu/Debian
- You're starting with MAC
- You want readable profiles
Use SELinux if:
- Your nodes run on RHEL/CentOS
- You have existing SELinux expertise
- You need strict multi-tenant isolation
Key takeaway: AppArmor and SELinux are mutually exclusive on the same node. Choose based on your distribution and maintain consistency across the cluster.
Check Kubernetes security for a global view of protection mechanisms.
How to integrate AppArmor Kubernetes with Pod Security Standards?
Pod Security Standards (PSS) define three security levels (Privileged, Baseline, Restricted). They complement AppArmor without replacing it.
Pod Security Admission configuration
apiVersion: v1
kind: Namespace
metadata:
name: production
labels:
pod-security.kubernetes.io/enforce: restricted
pod-security.kubernetes.io/audit: restricted
pod-security.kubernetes.io/warn: restricted
Combine PSS and AppArmor
apiVersion: v1
kind: Pod
metadata:
name: hardened-app
annotations:
container.apparmor.security.beta.kubernetes.io/app: localhost/k8s-restricted
spec:
securityContext:
runAsNonRoot: true
seccompProfile:
type: RuntimeDefault
containers:
- name: app
image: myapp:v1.0
securityContext:
allowPrivilegeEscalation: false
capabilities:
drop:
- ALL
readOnlyRootFilesystem: true
According to Spectro Cloud State of Kubernetes 2025, 82% of Kubernetes workloads are overprovisioned. A strict securityContext also reduces the attack surface.
How to audit and debug AppArmor profiles?
Complain mode allows developing profiles without blocking applications.
Enable complain mode
# Switch a profile to complain mode
aa-complain /etc/apparmor.d/k8s-restricted
# Analyze audit logs
journalctl -k | grep apparmor
dmesg | grep -i apparmor
Automatically generate a profile
# Install tools
apt install apparmor-utils
# Start learning
aa-genprof /app/bin/myapp
# Analyze and refine the generated profile
aa-logprof
Test a profile before deployment
# Validate syntax
apparmor_parser -p /etc/apparmor.d/k8s-restricted
# Load in enforce mode
apparmor_parser -r /etc/apparmor.d/k8s-restricted
# Check status
aa-status | grep k8s-restricted
To master Kubernetes troubleshooting, include MAC log analysis in your workflow.
Key takeaway: Develop your profiles in complain mode, analyze logs, then switch to enforce for production.
What are AppArmor Kubernetes best practices in production?
Standardize and automate profile deployment to ensure consistency across all nodes.
Deployment via DaemonSet
apiVersion: apps/v1
kind: DaemonSet
metadata:
name: apparmor-loader
namespace: kube-system
spec:
selector:
matchLabels:
app: apparmor-loader
template:
metadata:
labels:
app: apparmor-loader
spec:
containers:
- name: loader
image: apparmor-profiles:v1.0
command: ["sh", "-c", "cp /profiles/* /host/etc/apparmor.d/ && apparmor_parser -r /host/etc/apparmor.d/k8s-*"]
volumeMounts:
- name: apparmor-d
mountPath: /host/etc/apparmor.d
securityContext:
privileged: true
volumes:
- name: apparmor-d
hostPath:
path: /etc/apparmor.d
Admission controller validation
Use an admission webhook to reject pods without AppArmor profiles:
apiVersion: admissionregistration.k8s.io/v1
kind: ValidatingWebhookConfiguration
metadata:
name: apparmor-validator
webhooks:
- name: validate.apparmor.k8s.io
rules:
- apiGroups: [""]
apiVersions: ["v1"]
operations: ["CREATE"]
resources: ["pods"]
According to the CNCF Project Journey Report, 71% of Fortune 100 companies run Kubernetes in production. Security profile standardization becomes critical at this scale.
Check Kubernetes production best practices to complete your strategy.
AppArmor and SELinux Security Checklist
Validate each point for secured workloads:
- [ ] AppArmor/SELinux enabled on all nodes
- [ ] Custom profiles for each critical application
- [ ] Enforce mode in production (not complain)
- [ ] DaemonSet for automatic profile deployment
- [ ] Validation via admission controller
- [ ] Pod Security Standards configured (Restricted)
- [ ] MAC violation monitoring
- [ ] Profile and exception documentation
Key takeaway: AppArmor and SELinux form the last line of defense. Even if all other protections fail, these profiles limit an attacker's actions.
Take Action: Train on Kubernetes Workloads Security
The LFS460 Kubernetes Security Fundamentals training covers AppArmor, SELinux, Pod Security Standards, and CKS certification preparation. In 4 days, master container system security.
Next steps:
- Discover the Kubernetes CKA CKAD CKS certifications
- Explore the LFS458 Kubernetes Administration training
- Check the session calendar
Contact our advisors to develop your custom Kubernetes security path.