@@ -8,7 +8,7 @@ weight: 30
8
8
9
9
<!-- overview -->
10
10
11
- {{< feature-state for_k8s_version="v1.4" state="beta " >}}
11
+ {{< feature-state feature_gate_name="AppArmor " >}}
12
12
13
13
14
14
[ AppArmor] ( https://apparmor.net/ ) is a Linux kernel security module that supplements the standard Linux user and group based
@@ -54,7 +54,7 @@ Nodes before proceeding:
54
54
Y
55
55
```
56
56
57
- The Kubelet verifies that AppArmor is enabled on the host before admitting a pod with AppArmor
57
+ The kubelet verifies that AppArmor is enabled on the host before admitting a pod with AppArmor
58
58
explicitly configured.
59
59
60
60
3 . Container runtime supports AppArmor -- All common Kubernetes-supported container
@@ -64,7 +64,7 @@ Nodes before proceeding:
64
64
65
65
4 . Profile is loaded -- AppArmor is applied to a Pod by specifying an AppArmor profile that each
66
66
container should be run with. If any of the specified profiles are not loaded in the
67
- kernel, the Kubelet will reject the Pod. You can view which profiles are loaded on a
67
+ kernel, the kubelet will reject the Pod. You can view which profiles are loaded on a
68
68
node by checking the ` /sys/kernel/security/apparmor/profiles ` file. For example:
69
69
70
70
``` shell
@@ -85,25 +85,26 @@ Nodes before proceeding:
85
85
## Securing a Pod
86
86
87
87
{{< note >}}
88
- AppArmor is currently in beta, so options are specified as annotations. Once support graduates to
89
- general availability, the annotations will be replaced with first-class fields .
88
+ Prior to Kubernetes v1.30, AppArmor was specified through annotations. Use the documentation version
89
+ selector to view the documentation with this deprecated API .
90
90
{{< /note >}}
91
91
92
- AppArmor profiles are specified * per-container * . To specify the AppArmor profile to run a Pod
93
- container with, add an annotation to the Pod's metadata:
92
+ AppArmor profiles can be specified at the pod level or container level. The container AppArmor
93
+ profile takes precedence over the pod profile.
94
94
95
95
``` yaml
96
- container.apparmor.security.beta.kubernetes.io/<container_name> : <profile_ref>
96
+ securityContext :
97
+ appArmorProfile :
98
+ type : <profile_type>
97
99
` ` `
98
100
99
- Where ` <container_name>` is the name of the container to apply the profile to, and `<profile_ref>`
100
- specifies the profile to apply. The `<profile_ref>` can be one of :
101
+ Where ` <profile_type>` is one of:
101
102
102
- * `runtime/default ` to apply the runtime's default profile
103
- * `localhost/<profile_name> ` to apply the profile loaded on the host with the name `<profile_name>`
104
- * `unconfined ` to indicate that no profiles will be loaded
103
+ * `RuntimeDefault ` to use the runtime's default profile
104
+ * `Localhost ` to use a profile loaded on the host (see below)
105
+ * `Unconfined ` to run without AppArmor
105
106
106
- See the [API Reference](#api-reference) for the full details on the annotation and profile name formats .
107
+ See the [API Reference](#api-reference) for the full details on the AppArmor profile API .
107
108
108
109
To verify that the profile was applied, you can check that the container's root process is
109
110
running with the correct profile by examining its proc attr :
@@ -115,14 +116,14 @@ kubectl exec <pod_name> -- cat /proc/1/attr/current
115
116
The output should look something like this :
116
117
117
118
` ` `
118
- k8s- apparmor-example-deny-write (enforce)
119
+ cri-containerd. apparmor.d (enforce)
119
120
` ` `
120
121
121
122
# # Example
122
123
123
124
*This example assumes you have already set up a cluster with AppArmor support.*
124
125
125
- First, load the profile you want to use onto your Nodes. This profile denies all file writes :
126
+ First, load the profile you want to use onto your Nodes. This profile blocks all file write operations :
126
127
127
128
` ` `
128
129
#include <tunables/global>
@@ -197,9 +198,11 @@ apiVersion: v1
197
198
kind: Pod
198
199
metadata:
199
200
name: hello-apparmor-2
200
- annotations:
201
- container.apparmor.security.beta.kubernetes.io/hello: localhost/k8s-apparmor-example-allow-write
202
201
spec:
202
+ securityContext:
203
+ appArmorProfile:
204
+ type: Localhost
205
+ localhostProfile: k8s-apparmor-example-allow-write
203
206
containers:
204
207
- name: hello
205
208
image: busybox:1.28
@@ -243,7 +246,7 @@ An Event provides the error message with the reason, the specific wording is run
243
246
244
247
### Setting up Nodes with profiles
245
248
246
- Kubernetes does not currently provide any built-in mechanisms for loading AppArmor profiles onto
249
+ Kubernetes {{< skew currentVersion >}} does not provide any built-in mechanisms for loading AppArmor profiles onto
247
250
Nodes. Profiles can be loaded through custom infrastructure or tools like the
248
251
[ Kubernetes Security Profiles Operator] ( https://github.com/kubernetes-sigs/security-profiles-operator ) .
249
252
@@ -270,29 +273,31 @@ logs or through `journalctl`. More information is provided in
270
273
[ AppArmor failures] ( https://gitlab.com/apparmor/apparmor/wikis/AppArmor_Failures ) .
271
274
272
275
273
- ## API Reference
276
+ ## Specifying AppArmor confinement
277
+
278
+ {{< caution >}}
279
+ Prior to Kubernetes v1.30, AppArmor was specified through annotations. Use the documentation version
280
+ selector to view the documentation with this deprecated API.
281
+ {{< /caution >}}
274
282
275
- ### Pod Annotation
283
+ ### AppArmor profile within security context {#appArmorProfile}
276
284
277
- Specifying the profile a container will run with:
285
+ You can specify the ` appArmorProfile ` on either a container's ` securityContext ` or on a Pod's
286
+ ` securityContext ` . If the profile is set at the pod level, it will be used as the default profile
287
+ for all containers in the pod (including init, sidecar, and ephemeral containers). If both a pod & container
288
+ AppArmor profile are set, the container's profile will be used.
278
289
279
- - ** key** : ` container.apparmor.security.beta.kubernetes.io/<container_name> `
280
- Where ` <container_name> ` matches the name of a container in the Pod.
281
- A separate profile can be specified for each container in the Pod.
282
- - ** value** : a profile reference, described below
290
+ An AppArmor profile has 2 fields:
283
291
284
- ### Profile Reference
292
+ ` type ` _ (required)_ - indicates which kind of AppArmor profile will be applied. Valid options are:
293
+ - ` Localhost ` - a profile pre-loaded on the node (specified by ` localhostProfile ` ).
294
+ - ` RuntimeDefault ` - the container runtime's default profile.
295
+ - ` Unconfined ` - no AppArmor enforcement.
285
296
286
- - ` runtime/default ` : Refers to the default runtime profile.
287
- - Equivalent to not specifying a profile, except it still requires AppArmor to be enabled.
288
- - In practice, many container runtimes use the same OCI default profile, defined here:
289
- https://github.com/containers/common/blob/main/pkg/apparmor/apparmor_linux_template.go
290
- - ` localhost/<profile_name> ` : Refers to a profile loaded on the node (localhost) by name.
291
- - The possible profile names are detailed in the
292
- [ core policy reference] ( https://gitlab.com/apparmor/apparmor/wikis/AppArmor_Core_Policy_Reference#profile-names-and-attachment-specifications ) .
293
- - ` unconfined ` : This effectively disables AppArmor on the container.
297
+ ` localhostProfile ` - The name of a profile loaded on the node that should be used.
298
+ The profile must be preconfigured on the node to work.
299
+ This option must be provided if and only if the ` type ` is ` Localhost ` .
294
300
295
- Any other profile reference format is invalid.
296
301
297
302
## {{% heading "whatsnext" %}}
298
303
0 commit comments