Recopilación de logs de Kubernetes
Esta página trata sobre la recopilación de logs a partir de los archivos de log de Kubernetes.
Cuando tus aplicaciones en contenedores escriben sus logs a la salida y al error (stdout
/stderr
) estándar, el tiempo de ejecución del contenedor y Kubernetes gestionan automáticamente los logs. El patrón por defecto consiste en que Kubernetes almacene estos flujos (streams) de logs como archivos en el host, en la carpeta /var/log/pods
y las subcarpetas de cada pod y contenedor.
El Datadog Agent puede recopilar estos archivos de logs Kubernetes de estos contenedores siguiendo las instrucciones que se indican a continuación. Esta opción se adapta bien a la naturaleza efímera de los pods que crea Kubernetes y es más eficiente en cuanto a recursos que la recopilación de logs desde el socket Docker. Datadog recomienda este método para la recopilación de logs en Kubernetes.
Alternativamente, el Datadog Agent también puede recopilar logs mediante solicitudes repetidas a la API Docker a través del socket Docker. Sin embargo, esto requiere que Docker sea el tiempo de ejecución del contenedor de tu clúster Kubernetes. Esto también consume más recursos que el uso de archivos de logs. Para saber cómo recopilar logs utilizando el socket Docker, consulta Recopilación de logs con el socket Docker. Si tus aplicaciones en contenedores escriben en archivos de logs almacenados en un contenedor, esto puede complicar la recopilación de logs. Consulta la recopilación de logs a partir de un archivo.
Configuración
Recopilación de logs
Antes de empezar a recopilar logs de aplicación, asegúrate de que estás ejecutando el Datadog Agent en tu clúster Kubernetes.
Para configurar la recopilación de logs manualmente con un DaemonSet, consulta Recopilación de logs con DaemonSet. De lo contrario, sigue las siguientes instrucciones:
Actualiza tu manifiesto datadog-agent.yaml
con:
apiVersion: datadoghq.com/v2alpha1
kind: DatadogAgent
metadata:
name: datadog
spec:
global:
credentials:
apiKey: <DATADOG_API_KEY>
features:
logCollection:
enabled: true
containerCollectAll: true
A continuación, aplica la nueva configuración:
kubectl apply -n $DD_NAMESPACE -f datadog-agent.yaml
Consulta el ejemplo de manifiesto con la recopilación de logs, métricas y APM activada para ver un ejemplo adicional. Puedes configurar features.logCollection.containerCollectAll
como true
para recopilar logs de todos los contenedores detectados por defecto. Cuando se configura como false
(por defecto), es necesario especificar configuraciones de log de Autodiscovery para habilitar la recopilación de logs.
Para habilitar la recopilación de logs con Helm, actualiza tu archivo datadog-values.yaml con la siguiente configuración para la recopilación de logs. Luego, actualiza tu Datadog Helm chart:
datadog:
logs:
enabled: true
containerCollectAll: true
Puedes configurar datadog.logs.containerCollectAll
como true
para recopilar logs de todos los contenedores detectados por defecto. Cuando se configura como false
(por defecto), es necesario definir configuraciones de logs Autodiscovery para habilitar la recopilación de logs. Para obtener más información, consulta Detección de logs - Filtrado.
Sin privilegios
(Opcional) Para ejecutar una instalación sin privilegios, añade lo siguiente al recurso personalizado DatadogAgent:
apiVersion: datadoghq.com/v2alpha1
kind: DatadogAgent
metadata:
name: datadog
spec:
global:
credentials:
apiKey: <DATADOG_API_KEY>
features:
logCollection:
enabled: true
containerCollectAll: true
override:
nodeAgent:
securityContext:
runAsUser: <USER_ID>
supplementalGroups:
- <DOCKER_GROUP_ID>
- Sustituye
<USER_ID>
por el UID para ejecutar el Agent - Sustituye
<DOCKER_GROUP_ID>
por el ID del grupo al que pertenece el socket de Docker o containerd.
(Opcional) Para ejecutar una instalación sin privilegios, añade lo siguiente en el archivo values.yaml
:
datadog:
securityContext:
runAsUser: <USER_ID>
supplementalGroups:
- <DOCKER_GROUP_ID>
- Sustituye
<USER_ID>
por el UID para ejecutar el Agent. - Sustituye
<DOCKER_GROUP_ID>
por el ID del grupo al que pertenece el socket de Docker o containerd.
Advertencia para instalaciones sin privilegios
Cuando se ejecuta una instalación sin privilegios, el Agent necesita poder leer archivos de logs en /var/log/pods
.
Si estás utilizando el tiempo de ejecución contenedorizado, los archivos de logs en /var/log/pods
son legibles por los miembros del grupo raíz
. Con las instrucciones anteriores, el Agent se ejecuta con el grupo raíz
. No es necesario realizar ninguna acción.
Si estás utilizando el tiempo de ejecución Docker, los archivos de logs en /var/log/pods
son enlaces simbólicos a /var/lib/docker/containers
, que sólo puede recorrer el usuario raíz
. Consecuentemente, con el tiempo de ejecución Docker, no es posible para un Agent no raíz
leer logs en /var/log/pods
. El socket Docker debe estar montado en el contenedor del Agent, para que pueda obtener logs de pod a través del Docker daemon.
Para recopilar logs de /var/log/pods
cuando el socket Docker está montado, define la variable de entorno DD_LOGS_CONFIG_K8S_CONTAINER_USE_FILE
(o logs_config.k8s_container_use_file
en datadog.yaml
) como true
. Esto fuerza al Agent a utilizar el modo de recopilación de archivos.
Detección de logs
El Datadog Agent en Kubernetes es desplegado por un DaemonSet (gestionado por el Datadog Operator o Helm). Este DaemonSet programa una réplica de pod del Agent en cada nodo del clúster. Cada pod del Agent es entonces responsable de informar de logs de los otros pods y contenedores en su nodo respectivo. Cuando la función “Contenedor recopilar todo” está activada, el Agent informa de los logs de cada contenedor detectado con un conjunto predeterminado de etiquetas (tags).
Filtrado
Cuando “Contenedor recopilar todo” está activado, puedes configurar de qué contenedores quieres recopilar logs. Esto puede ser útil para evitar la recopilación de logs del Datadog Agent, si así lo prefieres. Puedes hacerlo pasando configuraciones al Datadog Agent para controlar lo que recopila o pasando configuraciones al pod Kubernetes para excluir ciertos logs más explícitamente.
Cuando “Contenedor recopilar todo” está desactivado (por defecto) esto no es necesario, ya que se habilitan las configuraciones de logs mediante anotaciones o archivos de configuración de Autodiscovery.
Para obtener más información, consulta Gestión de la detección de contenedores.
Etiquetado
El Datadog Agent etiqueta logs de contenedores Kubernetes con etiquetas Kubernetes predeterminadas, así como con cualquier etiqueta personalizada extraída. Cuando “Contenedor recopilar todo” está activado, el Agent informa de logs de un contenedor con una etiqueta source
y service
que coincida con el nombre de imagen corto del contenedor. Por ejemplo, los logs de un contenedor que utiliza la imagen de contenedor gcr.io/owner/example-image:latest
tendría example-image
como valor de etiqueta source
, service
y short_image
.
La etiqueta (tag) service
también puede definirse mediante la etiqueta (label) del pod de Etiquetado unificado de servicios tags.datadoghq.com/service: "<SERVICE>"
. Para obtener más información sobre los atributos source
y service
, consulta los atributos reservados.
La etiqueta (tag) source
puede ser importante para tus logs, ya que los pipelines de logs predefinidos se filtran con esta etiqueta (tag). Sin embargo, estos pipelines se pueden personalizar completamente, si así lo prefieres. Para personalizar aún más las etiquetas (tags) de tus logs, consulta los pasos en la sección Logs de integración más abajo.
Logs de integración
Autodiscovery te permite utilizar plantillas para configurar la recopilación de logs (y otras capacidades) en contenedores. Esta opción puede utilizarse para habilitar la recopilación de logs, personalizar el etiquetado y añadir reglas de recopilación avanzadas. Para configurar la recopilación de logs para una integración con Autodiscovery puedes:
- Especifica una configuración de log como anotaciones Autodiscovery en un pod concreto, para configurar las reglas de un contenedor concreto (recomendado).
- Especifica una configuración de log como archivo de configuración, para configurar las reglas de cada contenedor coincidente por imagen.
Como mínimo, estas configuraciones de logs requieren una etiqueta (tag) source
y service
. Es posible que quieras hacer coincidir la etiqueta (tag) source
con uno de los pipelines de logs predefinidos de Datadog para ayudarte a enriquecer automáticamente tus logs. También puedes encontrar una biblioteca de pipelines en Datadog.
Anotaciones de Autodiscovery
Con Autodiscovery, el Agent busca automáticamente plantillas de integración en todas las anotaciones de pod.
Para aplicar una configuración específica a un contenedor concreto, añade la anotación ad.datadoghq.com/<CONTAINER_NAME>.logs
a tu pod con la configuración de log con formato JSON.
Nota: Las anotaciones Autodiscovery identifican los contenedores por su nombre, no por su imagen. Intenta hacer coincidir el <CONTAINER_NAME>
con el .spec.containers[i].name
, no con la .spec.containers[i].image
.
Si defines tus pods Kubernetes directamente (con kind:Pod
), añade las anotaciones de cada pod en su sección de metadatos
, como se muestra en la siguiente sección.
Si defines tus pods Kubernetes indirectamente (con controladores de replicación, ReplicaSets o despliegues), añade anotaciones de pod a la plantilla de pod en .spec.template.metadata
.
Configurar un solo contenedor
Para configurar la recopilación de logs de un contenedor concreto dentro de tu pod, añade las siguientes anotaciones a tu pod:
apiVersion: v1
kind: Pod
# (...)
metadata:
name: '<POD_NAME>'
annotations:
ad.datadoghq.com/<CONTAINER_NAME>.logs: '[<LOG_CONFIG>]'
# (...)
spec:
containers:
- name: '<CONTAINER_NAME>'
# (...)
Ejemplo de anotaciones de logs Autodiscovery
La siguiente anotación de pod define la plantilla de integración para un ejemplo de contenedor. Se define dentro de las anotaciones de la plantilla de pod, en lugar de en el propio despliegue. Esta configuración de log configura todos los logs del contenedor app
con las etiquetas (tags) source:java
y service:example-app
, y la etiqueta (tag) adicional foo:bar
.
apiVersion: apps/v1
kind: Deployment
metadata:
name: example
labels:
app: example-app
spec:
selector:
matchLabels:
app: example-app
template:
metadata:
labels:
app: example-app
annotations:
ad.datadoghq.com/app.logs: '[{"source":"java", "service":"example-app", "tags":["foo:bar"]}]'
spec:
containers:
- name: app
image: owner/example-image:latest
Configurar dos contenedores diferentes
Para aplicar dos plantillas de integración diferentes a dos contenedores distintos dentro de tu pod, <CONTAINER_NAME_1>
y <CONTAINER_NAME_2>
, añade las siguientes anotaciones a tu pod:
apiVersion: v1
kind: Pod
# (...)
metadata:
name: '<POD_NAME>'
annotations:
ad.datadoghq.com/<CONTAINER_NAME_1>.logs: '[<LOG_CONFIG_1>]'
# (...)
ad.datadoghq.com/<CONTAINER_NAME_2>.logs: '[<LOG_CONFIG_2>]'
spec:
containers:
- name: '<CONTAINER_NAME_1>'
# (...)
- name: '<CONTAINER_NAME_2>'
# (...)
Archivos de configuración de Autodiscovery
Puedes proporcionar archivos de configuración al Datadog Agent para que ejecute una integración especificada cuando detecte un contenedor que utiliza el identificador de imagen coincidente. Esto permite crear una configuración de log genérica que se aplica a un conjunto de imágenes de contenedor.
Puede personalizar la colección Logs por integración con un override en el override.nodeAgent.extraConfd.configDataMap
. Este método crea el ConfigMap y monta el archivo Configuración deseado en el Agent Contenedor .
apiVersion: datadoghq.com/v2alpha1
kind: DatadogAgent
metadata:
name: datadog
spec:
#(...)
override:
nodeAgent:
extraConfd:
configDataMap:
<INTEGRATION_NAME>.yaml: |-
ad_identifiers:
- <CONTAINER_IMAGE>
logs:
- source: example-source
service: example-service
La <CONTAINER_IMAGE>
debe coincidir con el nombre corto de la imagen del contenedor al que quieres que se aplique. Para ver un ejemplo adicional, consulta el ejemplo de manifiesto con la asignación ConfigMap.
Puede personalizar la colección Logs por integración dentro de datadog.confd
. Este método crea el ConfigMap y monta el archivo Configuración deseado en el Agent Contenedor .
datadog:
#(...)
confd:
<INTEGRATION_NAME>.yaml: |-
ad_identifiers:
- <CONTAINER_IMAGE>
logs:
- source: example-source
service: example-service
La <CONTAINER_IMAGE>
debe coincidir con el nombre corto de la imagen del contenedor al que quieres que se aplique.
Los siguientes comandos etcd crean una plantilla Redis integración con un parámetro password
personalizado y etiquetas (tags) Logs con los atributos source
y service
correctos:
etcdctl mkdir /datadog/check_configs/redis
etcdctl set /datadog/check_configs/redis/logs '[{"source": "redis", "service": "redis", "tags": ["env:prod"]}]'
Fíjate que cada uno de los tres valores es una lista. Autodiscovery agrupa los elementos de la lista en configuraciones de integraciones basadas en índices de lista compartidos. En este caso, define la primera (y única) configuración de checks a partir de check_names[0]
, init_configs[0]
y instances[0]
.
A diferencia de los archivos de configuración automática, los almacenes de clave-valor pueden utilizar el nombre corto O largo de la imagen como identificadores de contenedor, por ejemplo, redis
O redis:latest
.
Autodiscovery puede utilizar Consul, Etcd y Zookeeper como fuentes de plantillas de integración.
Para utilizar un almacén de clave-valor, configúralo en el archivo de configuración datadog.yaml
del Agent y monta este archivo dentro del contenedor del Agent. Otra opción es pasar el almacén de clave-valor como variables de entorno al contenedor del Agent.
En datadog.yaml
En el archivo datadog.yaml
, configura la dirección <KEY_VALUE_STORE_IP>
y el<KEY_VALUE_STORE_PORT>
de tu base de datos clave-valor:
config_providers:
- name: etcd
polling: true
template_dir: /datadog/check_configs
template_url: '<KV_STORE_IP>:<KV_STORE_PORT>'
username:
password:
- name: consul
polling: true
template_dir: datadog/check_configs
template_url: '<KV_STORE_IP>:<KV_STORE_PORT>'
ca_file:
ca_path:
cert_file:
key_file:
username:
password:
token:
- name: zookeeper
polling: true
template_dir: /datadog/check_configs
template_url: '<KV_STORE_IP>:<KV_STORE_PORT>'
username:
password:
Luego, reinicia el Agent, para aplicar el cambio de configuración.
En variables de entorno
Si la base de datos clave-valor se ha activado como fuente de plantillas, el Agent busca plantillas con la clave /datadog/check_configs
. Autodiscovery espera una jerarquía clave-valor como la siguiente:
/datadog/
check_configs/
<CONTAINER_IMAGE>/
- logs: ["<LOGS_CONFIG>"]
...
Nota: Para aplicar una configuración específica a un contenedor, cuando Autodiscovery utiliza los almacenes clave-valor, identifica los contenedores por imagen, intentando que <CONTAINER_IMAGE>
coincida con .spec.containers[0].image
.
Recopilación avanzada de logs
Utiliza etiquetas de logs (labels) de Autodiscovery para aplicar la lógica de procesamiento de la recopilación avanzada de logs, por ejemplo:
A partir de un archivo de log de contenedor local
Datadog recomienda que utilices los flujos (streams) de salida stdout
y stderr
para aplicaciones en contenedores, de modo que puedas configurar más automáticamente la recopilación de logs.
Sin embargo, el Agent también puede recopilar directamente logs de un archivo basándose en una anotación. Para recopilar estos logs, utiliza ad.datadoghq.com/<CONTAINER_IMAGE>.logs
con una configuración type: file
y path
. Los logs recopilados de archivos con es´ta anotación se etiquetan automáticamente con el mismo conjunto de etiquetas (tags) que los logs procedentes del propio contenedor. Datadog recomienda que utilices los flujos de salida stdout
y stderr
para aplicaciones en contenedores, de modo que puedas configurar automáticamente la recopilación de logs. Para obtener más información, consulta las configuraciones recomendadas.
Estas rutas de archivo son relativas al contenedor del Agent. Por lo tanto, el directorio que contiene el archivo de log debe montarse tanto en la aplicación como en el contenedor del Agent para que éste pueda tener la visibilidad adecuada.
Por ejemplo, puedes hacerlo con un volumen hostPath
compartido. El pod a continuación está emitiendo logs en el archivo /var/log/example/app.log
. Esto se hace en el directorio /var/log/example
, donde un volumen y volumeMount lo han establecido como hostPath
.
apiVersion: v1
kind: Pod
metadata:
name: logger
annotations:
ad.datadoghq.com/busybox.logs: |
[{
"type": "file",
"path": "/var/log/example/app.log",
"source": "example-source",
"service": "example-service"
}]
spec:
containers:
- name: busybox
image: busybox
command: [ "/bin/sh", "-c", "--" ]
args: [ "while true; do sleep 1; echo `date` example file log >> /var/log/example/app.log; done;" ]
volumeMounts:
- name: applogs
mountPath: /var/log/example
volumes:
- name: applogs
hostPath:
path: /var/log/example
El volumen equivalente y la ruta volumeMount deben establecerse en el contenedor del Agent para que pueda leer el mismo archivo de log.
containers:
- name: agent
# (...)
volumeMounts:
- mountPath: /var/log/example
name: applogs
# (...)
volumes:
- name: applogs
hostPath:
path: /var/log/example
# (...)
Configuraciones recomendadas
Esta estrategia puede funcionar para un pod concreto, pero puede resultar engorrosa cuando varias aplicaciones utilizan esta estrategia. También puedes tener problemas si varias réplicas utilizan la misma ruta de logs. Cuando sea posible, Datadog recomienda aprovechar la variable de plantilla Autodiscovery %%kube_pod_name%%
. Por ejemplo, puedes configurar tu path
para que haga referencia a esta variable: "path": "/var/log/example/%%kube_pod_name%%/app.log"
. A continuación, tu pod de aplicación también debe escribir sus archivos de logs en función de esta nueva ruta. Puedes utilizar la API descendente para ayudar a tu aplicación a determinar su nombre de pod.
Cuando se utiliza este tipo de anotación con un contenedor, los logs stdout
y stderr
no se recopilan automáticamente desde el contenedor. Si se necesita la recopilación tanto del contenedor como de un archivo, debe habilitarse explícitamente en la anotación. Por ejemplo:
ad.datadoghq.com/<CONTAINER_IMAGE>.logs: |
[
{"type":"file","path":"/var/log/example/app.log","source":"file","service":"example-service"},
{"source":"container","service":"example-service"}
]
Cuando se utiliza este tipo de combinación, source
y service
no tienen un valor por defecto para logs recopilados de un archivo y deben establecerse explícitamente en la anotación.
Solucionar problemas
Contenedores de corta duración
Por defecto, Agent busca nuevos contenedores cada 5 segundos.
Para Agent v6.12+, los logs de contenedor de corta duración (detenidos o bloqueados) se recopilan automáticamente cuando se utiliza el método de recopilación de logs de archivos K8s (a través de /var/log/pods
). Esto también incluye la recopilación de logs de contenedor init.
Al enviar logs a Datadog desde contenedores o pods recién creados, es posible que el etiquetador interno del Datadog Agent aún no disponga de las etiquetas (tags) de contenedor/pod relacionadas. Como resultado, pueden faltar etiquetas (tags) en estos logs.
Para solucionar este problema, puede utilizar la variable de entorno DD_LOGS_CONFIG_TAGGER_WARMUP_DURATION
para configurar una duración (en segundos) para que el Datadog Agent espere antes de empezar a enviar logs desde contenedores y pods recién creados. El valor por defecto es 0
.
spec:
override:
nodeAgent:
env:
- name: DD_LOGS_CONFIG_TAGGER_WARMUP_DURATION
value: "5"
datadog:
env:
- name: DD_LOGS_CONFIG_TAGGER_WARMUP_DURATION
value: "5"
Las etiquetas (tags) a nivel de host son las que aparecen en la lista de infraestructuras de un host determinado y proceden de un proveedor de nube o del Datadog Agent. Las etiquetas (tags) a nivel de host más frecuentes incluyen kube_cluster_name
, region
, instance-type
y autoscaling-group
.
Cuando se envían logs a Datadog desde un nodo o host recién creado, pueden pasar algunos minutos hasta que se hereden las etiquetas (tags) de nivel de host. Como resultado, en estos logs pueden faltar las etiquetas (tags) de nivel de host.
Para solucionar este problema, puedes utilizar la variable de entorno DD_LOGS_CONFIG_EXPECTED_TAGS_DURATION
para configurar una duración (en minutos). Durante este tiempo, el Datadog Agent adjunta manualmente las etiquetas (tags) de nivel de host que conoce a cada log enviado. Después de este tiempo, el Agent vuelve a confiar en las etiquetas (tags) heredadas durante la ingesta.
spec:
override:
nodeAgent:
env:
- name: DD_LOGS_CONFIG_EXPECTED_TAGS_DURATION
value: "10m"
datadog:
env:
- name: DD_LOGS_CONFIG_EXPECTED_TAGS_DURATION
value: "10m"
Referencias adicionales
Más enlaces, artículos y documentación útiles: