Detection rules › Elastic
Azure AKS Ephemeral Container Added to Pod
Detects an identity injecting an ephemeral (debug) container into a running AKS (Azure Kubernetes Service) pod via the pods/ephemeralcontainers subresource, excluding known AKS control-plane and platform identities. Ephemeral containers share the target pod's namespaces and give stealthy interactive access to its processes and mounted secrets without creating a new pod. Coverage includes workload service accounts (system:serviceaccount:*), so a compromised in-cluster token used to attach a debug container is not excluded.
Known false positives
- Operators and support tooling use ephemeral containers (kubectl debug) for legitimate troubleshooting. Baseline expected users and exclude verified break-glass or platform identities after review.
MITRE ATT&CK coverage
| Tactic | Techniques |
|---|---|
| Execution |
Telemetry coverage
Rules detecting the same action
These rules filter on the same operation.
- Direct Interactive Kubernetes API Request by Unusual Utilities (Elastic)
- EphemeralContainers Created (Falco)
- GCP K8s Pod Attached To Node Host Network (Panther)
- GCP K8S Pod Create Or Modify Host Path Volume Mount (Panther)
- GCP K8s Pod Using Host PID Namespace (Panther)
- GKE Anonymous Pod Create/Update/Patch (Elastic)
- GKE Ephemeral Container Added to Pod (Elastic)
- GKE Pod Created with a Sensitive hostPath Volume (Elastic)
Rule body
[metadata]
creation_date = "2026/07/09"
integration = ["azure"]
maturity = "production"
updated_date = "2026/07/09"
[rule]
author = ["Elastic"]
description = """
Detects an identity injecting an ephemeral (debug) container into a running AKS (Azure Kubernetes Service) pod via the
pods/ephemeralcontainers subresource, excluding known AKS control-plane and platform identities. Ephemeral containers
share the target pod's namespaces and give stealthy interactive access to its processes and mounted secrets without
creating a new pod. Coverage includes workload service accounts (system:serviceaccount:*), so a compromised in-cluster
token used to attach a debug container is not excluded.
"""
false_positives = [
"""
Operators and support tooling use ephemeral containers (kubectl debug) for legitimate troubleshooting. Baseline
expected users and exclude verified break-glass or platform identities after review.
""",
]
from = "now-9m"
index = ["logs-azure.platformlogs-*"]
language = "kuery"
license = "Elastic License v2"
name = "Azure AKS Ephemeral Container Added to Pod"
note = """## Triage and analysis
### Investigating Azure AKS Ephemeral Container Added to Pod
AKS kube-audit events are carried under the flattened `azure.platformlogs.properties.log.*` subtree and share the ARM
operation `event.action: Microsoft.ContainerService/managedClusters/diagnosticLogs/Read`. An ephemeral container is
attached to a running pod (via `kubectl debug`) and shares that pod's process and network namespaces. Adversaries use it
as a stealthier alternative to `exec` to read mounted secrets and interact with the workload.
### Possible investigation steps
- Identify the acting identity in `azure.platformlogs.properties.log.user.username` (and its groups in
`azure.platformlogs.properties.log.user.groups`) and whether it should debug pods. A username of `masterclient` with
the `system:masters` group is the AKS local cluster-admin certificate (`az aks get-credentials --admin`); on clusters
with local accounts disabled it should not appear at all, so its presence is itself notable. Entra-integrated admins
appear as their UPN/objectId instead.
- Inspect the injected container in the `azure.platformlogs.properties.log.requestObject.spec.ephemeralContainers.*`
fields: the `image`, `command`, and `targetContainerName` show what was run and against which container, and
`securityContext.capabilities.add` (e.g. `SYS_PTRACE`, `SYS_ADMIN`) or a privileged context indicates offensive
debugging.
- Review `azure.platformlogs.properties.log.userAgent` to distinguish an interactive `kubectl debug` from automation or
custom tooling, and `azure.platformlogs.properties.log.responseStatus.code` to tell a successful injection (200) from
a denied attempt (403) by an identity lacking RBAC.
- Identify the target pod in `azure.platformlogs.properties.log.objectRef.name` /
`azure.platformlogs.properties.log.objectRef.namespace`.
- Evaluate the source in `azure.platformlogs.properties.log.sourceIPs` and pivot on it for related exec sessions, secret
reads, or RBAC changes.
### False positive analysis
- Operators and support tooling use ephemeral containers for legitimate troubleshooting; baseline expected users and
exclude verified break-glass or platform identities.
### Response and remediation
- If unauthorized, remove the ephemeral container (delete or replace the pod), revoke the acting identity's tokens, and
review the RBAC that permitted the injection.
- Inspect the target pod for accessed secrets or tampering and rotate any exposed credentials.
- Collect kube-audit and identity artifacts per incident response procedures.
"""
references = [
"https://kubernetes.io/docs/tasks/debug/debug-application/debug-running-pod/#ephemeral-container",
"https://microsoft.github.io/Threat-Matrix-for-Kubernetes/",
"https://unit42.paloaltonetworks.com/hildegard-malware-teamtnt/",
]
risk_score = 47
rule_id = "d4209683-ee18-439f-b816-1bbe6ee6bbc8"
setup = """The Azure Fleet integration collecting AKS diagnostic logs forwarded through Event Hub into the `azure.platformlogs`
data stream is required for this rule. Enable either the `kube-audit` or the `kube-audit-admin` log category (Microsoft
recommends `kube-audit-admin` alone to reduce volume, as it only drops read-only get/list events). Mutating
ephemeral-container writes are recorded in both categories with the same `auditID`, so clusters that enable both
categories may generate two alerts per injection.
"""
severity = "medium"
tags = [
"Domain: Cloud",
"Domain: Kubernetes",
"Data Source: Azure",
"Data Source: Azure Platform Logs",
"Data Source: Kubernetes",
"Use Case: Threat Detection",
"Tactic: Execution",
"Resources: Investigation Guide",
]
timestamp_override = "event.ingested"
type = "query"
query = '''
data_stream.dataset:azure.platformlogs and
event.action:"Microsoft.ContainerService/managedClusters/diagnosticLogs/Read" and
azure.platformlogs.category:("kube-audit" or "kube-audit-admin") and
azure.platformlogs.properties.log.stage:"ResponseComplete" and
azure.platformlogs.properties.log.objectRef.resource:"pods" and
azure.platformlogs.properties.log.objectRef.subresource:"ephemeralcontainers" and
azure.platformlogs.properties.log.verb:("update" or "patch") and
not azure.platformlogs.properties.log.user.username:(
system\:node\:* or "aksService" or "hcpService" or "readinessChecker" or
system\:serviceaccount\:kube-system\:*
)
'''
[[rule.threat]]
framework = "MITRE ATT&CK"
[[rule.threat.technique]]
id = "T1610"
name = "Deploy Container"
reference = "https://attack.mitre.org/techniques/T1610/"
[rule.threat.tactic]
id = "TA0002"
name = "Execution"
reference = "https://attack.mitre.org/tactics/TA0002/"
[rule.investigation_fields]
field_names = [
"@timestamp",
"event.action",
"azure.platformlogs.category",
"azure.platformlogs.properties.log.verb",
"azure.platformlogs.properties.log.user.username",
"azure.platformlogs.properties.log.user.groups",
"azure.platformlogs.properties.log.userAgent",
"azure.platformlogs.properties.log.sourceIPs",
"azure.platformlogs.properties.log.objectRef.namespace",
"azure.platformlogs.properties.log.objectRef.name",
"azure.platformlogs.properties.log.objectRef.subresource",
"azure.platformlogs.properties.log.requestObject.spec.ephemeralContainers.name",
"azure.platformlogs.properties.log.requestObject.spec.ephemeralContainers.image",
"azure.platformlogs.properties.log.requestObject.spec.ephemeralContainers.command",
"azure.platformlogs.properties.log.requestObject.spec.ephemeralContainers.targetContainerName",
"azure.platformlogs.properties.log.requestObject.spec.ephemeralContainers.securityContext.capabilities.add",
"azure.platformlogs.properties.log.responseStatus.code",
]
Stages and Predicates
Stage 1: query
data_stream.dataset:azure.platformlogs and
event.action:"Microsoft.ContainerService/managedClusters/diagnosticLogs/Read" and
azure.platformlogs.category:("kube-audit" or "kube-audit-admin") and
azure.platformlogs.properties.log.stage:"ResponseComplete" and
azure.platformlogs.properties.log.objectRef.resource:"pods" and
azure.platformlogs.properties.log.objectRef.subresource:"ephemeralcontainers" and
azure.platformlogs.properties.log.verb:("update" or "patch") and
not azure.platformlogs.properties.log.user.username:(
system\:node\:* or "aksService" or "hcpService" or "readinessChecker" or
system\:serviceaccount\:kube-system\:*
)
Exclusions
The rule actively suppresses these predicates.
Indicators
These rows show field, operator, and value matches.
| Field | Kind | Values | Search |
|---|---|---|---|
azure.platformlogs.category | in |
| field:"azure.platformlogs.category" kind:in |
azure.platformlogs.properties.log.objectRef.resource | eq |
| field:"azure.platformlogs.properties.log.objectRef.resource" kind:eq value:"pods" |
azure.platformlogs.properties.log.objectRef.subresource | eq |
| field:"azure.platformlogs.properties.log.objectRef.subresource" kind:eq value:"ephemeralcontainers" |
azure.platformlogs.properties.log.stage | eq |
| field:"azure.platformlogs.properties.log.stage" kind:eq value:"ResponseComplete" |
azure.platformlogs.properties.log.verb | in |
| field:"azure.platformlogs.properties.log.verb" kind:in |
data_stream.dataset | eq |
| field:"data_stream.dataset" kind:eq value:"azure.platformlogs" |
event.action | eq |
| field:"EventType" kind:eq value:"Microsoft.ContainerService/managedClusters/diagnosticLogs/Read" |