Ignorando Recursos No Deseados en APM

Los servicios a menudo manejan puntos de conexión cuyo tráfico puede que no desees trazar (por ejemplo, las verificaciones de salud). Esta guía explica los siguientes enfoques para excluir ese tráfico:

  • Muestreo: Utiliza cuando deseas que las solicitudes permanezcan visibles en las métricas de traza, pero reducir el volumen de ingesta de traza.
  • Filtrado en el Agente de Datadog: Utiliza para excluir solicitudes por completo (incluyendo de las métricas de traza) en todos los servicios que reportan al Agente.
  • Configuración del rastreador: Utiliza cuando la lógica de filtrado debe aplicarse por servicio o depende del contexto específico de la aplicación (por ejemplo, atributos de solicitud o estado de ejecución).

Si necesitas asistencia para decidir cuál opción es la más relevante para tu caso de uso, contacta a soporte de Datadog.

Muestreo

Si deseas que el tramo esté incluido en las métricas de traza pero no quieres que sea ingerido, utiliza reglas de muestreo. Para más información sobre muestreo, consulta Controles de Ingesta.

Usando reglas de muestreo

El enfoque recomendado es utilizar reglas de muestreo, que te permiten muestrear trazas basadas en nombres de recursos, nombres de servicios, etiquetas y nombres de operaciones:

DD_TRACE_SAMPLING_RULES='[{"resource": "GET healthcheck", "sample_rate": 0.0}]'

O muestrear basado en etiquetas de URL HTTP:

DD_TRACE_SAMPLING_RULES='[{"tags": {"http.url": "http://.*/healthcheck$"}, "sample_rate": 0.0}]'
Las decisiones de muestreo se determinan utilizando el primer tramo en una traza. Si el tramo que contiene la etiqueta que deseas filtrar no es un Un tramo es un tramo raíz de la traza cuando es el primer tramo de una traza. El tramo raíz es el método de entrada de la solicitud rastreada. Su inicio marca el comienzo de la traza.Glossary, esta regla no se aplica.

Filtrado en el Agente de Datadog

Si no deseas que el tramo se ingeste o se refleje en las métricas de traza, utiliza el filtrado en el Agente de Datadog.

El componente Trace Agent dentro del Agente de Datadog tiene dos métodos para evitar que ciertas trazas sean enviadas: filtrado por etiquetas de tramo o filtrado por recursos. Si las trazas son descartadas debido a estas configuraciones, las métricas de traza excluyen estas solicitudes.

Configurar el Trace Agent para ignorar ciertas trazas o recursos se aplica a todos los servicios que envían trazas a este Agente de Datadog. Si tienes requisitos específicos de la aplicación, utiliza la configuración del rastreador en su lugar.

Si ninguna de las opciones en esta guía cumple con tus requisitos, considera agregar una etiqueta de tramo personalizada en tu aplicación y usarla para descartar trazas en el Agente.

Ignorando trazas basadas en etiquetas de tramo

A partir de Datadog Agent 6.27.0/7.27.0, la opción filter tags descarta trazas con tramos raíz que coinciden con las etiquetas de tramo especificadas. Esta opción se aplica a todos los servicios que envían trazas a este Datadog Agent. Las trazas que son descartadas debido a las etiquetas de filtro no se incluyen en las métricas de traza.

Los tramos individuales dentro de una traza no pueden ser descartados selectivamente; si el tramo raíz coincide con los criterios de filtro, la traza completa es descartada.

Comportamiento de coincidencia:

La opción de filtrar etiquetas requiere una coincidencia exacta de cadena. Para filtrado basado en regex, consulte Ignorando basado en recursos.

Cuando especificas múltiples etiquetas, el filtro utiliza lógica OR: las trazas son descartadas si el tramo raíz coincide con cualquiera de las etiquetas. Para coincidir múltiples condiciones simultáneamente, agrega una etiqueta personalizada que represente esos criterios combinados.

Configuración:

Puedes especificar etiquetas de tramo para requerir o rechazar utilizando una lista de claves y valores separados por espacios en las variables de entorno:

DD_APM_FILTER_TAGS_REQUIRE
Recoge solo trazas que tienen tramos raíz con una coincidencia exacta para las etiquetas y valores de tramo especificados. Si no coincide con esta regla, la traza se descarta. Por ejemplo, DD_APM_FILTER_TAGS_REQUIRE="key1:value1 key2:value2". En Datadog Agent 7.49+, se pueden proporcionar expresiones regulares con DD_APM_FILTER_TAGS_REGEX_REQUIRE.
DD_APM_FILTER_TAGS_REJECT
Rechaza trazas que tienen tramos raíz con una coincidencia exacta para las etiquetas y valores de tramo especificados. Si coincide con esta regla, la traza se descarta. Por ejemplo, DD_APM_FILTER_TAGS_REJECT="key1:value1 key2:value2". En Datadog Agent 7.49+, se pueden proporcionar expresiones regulares con DD_APM_FILTER_TAGS_REGEX_REJECT.

Datadog Operator

datadog-agent.yaml

apiVersion: datadoghq.com/v2alpha1
kind: DatadogAgent
metadata:
  name: datadog
spec:
  override:
    nodeAgent:
      containers:
        trace-agent:
          env:
            - name: DD_APM_FILTER_TAGS_REJECT
              value: tag_key1:tag_val2 tag_key2:tag_val2

After making your changes, apply the new configuration by using the following command:

kubectl apply -n $DD_NAMESPACE -f datadog-agent.yaml

Helm

datadog-values.yaml

agents:
  containers:
    traceAgent:
      env:
        - name: DD_APM_FILTER_TAGS_REJECT
          value: tag_key1:tag_val2 tag_key2:tag_val2

After making your changes, upgrade your Datadog Helm chart using the following command:

helm upgrade -f datadog-values.yaml <RELEASE NAME> datadog/datadog

También puedes establecer estos valores en el archivo de configuración del Agent utilizando una lista separada por comas:

datadog.yaml

apm_config:
  filter_tags:
    require: ["db:sql", "db.instance:mysql"]
    reject: ["outcome:success", "key2:value2"]

Por ejemplo, para ignorar las verificaciones de salud donde la http.url coincide con este punto de conexión:

datadog.yaml

apm_config:
  filter_tags:
    reject: ["http.url:http://localhost:5050/healthcheck"]

Etiquetas de tramo disponibles

En el backend, Datadog crea las siguientes etiquetas de tramo en los tramos después de la ingestión.

Nota: Estas etiquetas no se pueden usar para descartar trazas a nivel del Datadog Agent. El agente solo filtra en función de las etiquetas disponibles antes de la ingestión.

NombreDescripción
http.path_groupLa ruta completa de URL desde la etiqueta http.url.
http.url_details.hostLa porción del nombre del servidor de la etiqueta http.url
http.url_details.pathEl objetivo completo de la solicitud tal como se pasa en una línea de solicitud HTTP o equivalente.
http.url_details.schemeEl esquema de la solicitud de la etiqueta http.url.
http.url_details.queryStringLa porción de la cadena de consulta de la etiqueta http.url.
http.url_details.portEl puerto HTTP de la etiqueta http.url.
http.useragent_details.os.familyLa familia del sistema operativo reportada por el User-Agent.
http.useragent_details.browser.familyLa familia del navegador reportada por el User-Agent.
http.useragent_details.device.familyLa familia del dispositivo reportada por el User-Agent.
A partir del 1 de octubre de 2022, el backend de Datadog aplica un remapeo para aplicar la semántica de las etiquetas de tramo a través de los rastreadores en todos los tramos ingeridos. Si deseas descartar trazas basadas en etiquetas de tramo raíz a nivel del Agente de Datadog, utiliza etiquetas en la columna Remap from.
Comunicaciones de red
NombreRemap from
network.host.iptcp.local.address - Node.js
network.destination.ipout.host - Todos los lenguajes
network.destination.portgrpc.port - Python
tcp.remote.port - Node.js
out.port - Todos los lenguajes
Solicitudes HTTP
NombreRemap from
http.routeaspnet_core.route - .NET
aspnet.route - .NET
laravel.route - PHP
symfony.route - PHP
http.useragentuser_agent - Java, C++
http.url_details.queryStringhttp.query.string - Python
Base de datos
NombreRemap from
db.systemdb.type - Java, Python, Node.js, Go
active_record.db.vendor - Ruby
sequel.db.vendor - Ruby
db.instancemongodb.db - Python
sql.db - Python
db.name - Todos los lenguajes
db.statementcassandra.query - Go
consul.command - Python
memcached.query - Python
mongodb.query - Python, .NET, Go
redis.command - Python
redis.raw_command - Python
sql.query - Python, PHP, Node.js, Java
db.row_countcassandra.row_count - Python
db.rowcount - Python, PHP
mongodb.rows - Python
sql.rows - Python
db.cassandra.clustercassandra.cluster - Python, Go
db.cassandra.consistency_levelcassandra.consistency_level - Python, Go
db.cassandra.tablecassandra.keyspace - Python, Go
db.redis.database_indexdb.redis.dbIndex - Java
out.redis_db - Python, Ruby
db.mongodb.collectionmongodb.collection - Python, .NET, Ruby, PHP
db.cosmosdb.containercosmosdb.container - .NET
Cola de Mensajes
NombreRemapear desde
messaging.destinationamqp.destination - Node.js
amqp.queue - .NET
msmq.queue.path - .NET
aws.queue.name - .NET
messaging.urlaws.queue.url - .NET, Java
messaging.message_idserver_id - Go
messaging.message_payload_sizemessage.size - .NET, Java
messaging.operationamqp.command - .NET
msmq.command - .NET
messaging.rabbitmq.routing_keyamqp.routing_key - Java
amqp.routingKey - Node.js
messaging.rabbitmq.delivery_modemessaging.rabbitmq.exchange - .NET
messaging.msmq.message.transactionalmsmq.message.transactional - .NET
messaging.msmq.queue.transactionalmsmq.queue.transactional - .NET
messaging.kafka.consumer_groupkafka.group - Java
messaging.kafka.tombstonekafka.tombstone - .NET
tombstone - Java
messaging.kafka.partitionkafka.partition - .NET
partition - Node.js, Go, Java
messaging.kafka.offsetkafka.offset - .NET
messaging.msmq.message.transactionalmsmq.message.transactional - .NET
Llamadas a procedimientos remotos
NombreRemapear desde
rpc.servicegrpc.method.service - Python, .NET
rpc.methodgrpc.method.name - Python, .NET, Go
rpc.grpc.packagegrpc.method.package - Python, .NET, Go
rpc.grpc.status_codegrpc.code - Go
status.code - Python, .NET, Node.js
grpc.status.code - Python, .NET, Node.js
rpc.grpc.kindgrpc.method.kind - Python, Node.js, Go, .NET
rpc.grpc.pathrpc.grpc.path - Python, Node.js, Go, .NET
rpc.grpc.request.metadata.*grpc.request.metadata.* - Python, Node.js
rpc.grpc.request.metadata - Go
rpc.grpc.response.metadata.*grpc.response.metadata.* - Python, Node.js
Errores
NombreRemapear desde
error.messageerror.msg - Todos los lenguajes

Ignorando trazas basadas en recursos

La opción ignorar recursos permite excluir recursos si el tramo raíz global de la traza coincide con ciertos criterios. Consulte Excluir recursos de ser recolectados. Esta opción se aplica a todos los servicios que envían trazas a este Agente de Datadog en particular. Las trazas que se descartan debido a recursos ignorados no se incluyen en las métricas de traza.

Puede especificar recursos a ignorar ya sea en el archivo de configuración del Agente, datadog.yaml, o con la variable de entorno DD_APM_IGNORE_RESOURCES. Consulte los ejemplos a continuación.

Usando datadog.yaml:

datadog.yaml

apm_config:
## @param ignore_resources - list of strings - optional
## A list of regular expressions can be provided to exclude certain traces based on their resource name.
## All entries must be surrounded by double quotes and separated by commas.

  ignore_resources: ["(GET|POST) /healthcheck","API::NotesController#index"]

Usando DD_APM_IGNORE_RESOURCES:

DD_APM_IGNORE_RESOURCES="(GET|POST) /healthcheck,API::NotesController#index"

Notas:

  • Al usar el formato de variable de entorno (DD_APM_IGNORE_RESOURCES), los valores deben proporcionarse como una lista de cadenas separadas por comas.
  • La sintaxis regex que acepta el Agente de Trazas es evaluada por regexp de Go.
  • Dependiendo de su estrategia de implementación, es posible que deba ajustar la regex escapando caracteres especiales.
  • Si utiliza contenedores dedicados con Kubernetes, asegúrese de que la variable de entorno para la opción de recurso ignorado se esté aplicando al contenedor trace-agent.

Ejemplo

Considere una traza que contiene llamadas a /api/healthcheck de las que no desea trazas:

Gráfico de llamas de un recurso que desea que el SDK ignore

Tome nota del nombre del recurso del span raíz global.

  • Nombre de la operación: rack.request
  • Nombre del recurso: Api::HealthchecksController#index
  • Http.url: /api/healthcheck

Para usar correctamente la opción de recurso ignorado, la regla regex escrita debe coincidir con el nombre del recurso, Api::HealthchecksController#index. Existen algunas opciones de regex, pero para filtrar rastros de este recurso tal como está, un regex potencial a utilizar es Api::HealthchecksController#index$.

Dependiendo de cómo lo implementes, la sintaxis se ve un poco diferente:

datadog.yaml

apm_config:
  ignore_resources: Api::HealthchecksController#index$

Para múltiples valores:

apm_config:
  ignore_resources: ["value1","Api::HealthchecksController#index$"]

En la lista de variables de entorno del contenedor del Agente de Datadog, agrega DD_APM_IGNORE_RESOURCES con un patrón como el ejemplo a continuación. Docker Compose tiene su propia sustitución de variables a considerar cuando usas caracteres especiales como $.

    environment:
      // other Datadog Agent environment variables
      - DD_APM_IGNORE_RESOURCES=Api::HealthchecksController#index$$

Para múltiples valores:

    environment:
      // other Datadog Agent environment variables
      - DD_APM_IGNORE_RESOURCES="value1","Api::HealthchecksController#index$$"

En tu comando de docker run para iniciar el Agente de Datadog, agrega DD_APM_IGNORE_RESOURCES:

docker run -d --name datadog-agent \
              --cgroupns host \
              --pid host \
              -v /var/run/docker.sock:/var/run/docker.sock:ro \
              -v /proc/:/host/proc/:ro \
              -v /sys/fs/cgroup/:/host/sys/fs/cgroup:ro \
              -e DD_API_KEY=<> \
              -e DD_APM_IGNORE_RESOURCES="Api::HealthchecksController#index$" \
              -e DD_APM_ENABLED=true \
              -e DD_APM_NON_LOCAL_TRAFFIC=true \
              registry.datadoghq.com/agent:latest

Para múltiples valores:

              -e DD_APM_IGNORE_RESOURCES=["value1","Api::HealthchecksController#index$"] \

En el contenedor dedicado del trace-agent, agrega la variable de entorno DD_APM_IGNORE_RESOURCES:

    - name: trace-agent
        image: "registry.datadoghq.com/agent:latest"
        imagePullPolicy: IfNotPresent
        command: ["trace-agent", "-config=/etc/datadog-agent/datadog.yaml"]
        resources: {}
        ports:
        - containerPort: 8126
          hostPort: 8126
          name: traceport
          protocol: TCP
        env:
        - name: DD_API_KEY
          valueFrom:
            secretKeyRef:
              name: "datadog-secret"
              key: api-key
        - name: DD_KUBERNETES_KUBELET_HOST
          valueFrom:
            fieldRef:
              fieldPath: status.hostIP
        - name: KUBERNETES
          value: "yes"
        - name: DOCKER_HOST
          value: unix:///host/var/run/docker.sock
        - name: DD_LOG_LEVEL
          value: "INFO"
        - name: DD_APM_ENABLED
          value: "true"
        - name: DD_APM_NON_LOCAL_TRAFFIC
          value: "true"
        - name: DD_APM_RECEIVER_PORT
          value: "8126"
        - name: DD_KUBELET_TLS_VERIFY
          value: "false"
        - name: DD_APM_IGNORE_RESOURCES
          value: "Api::HealthchecksController#index$"

Para múltiples valores:

        - name: DD_APM_IGNORE_RESOURCES
          value: '"value1","Api::HealthchecksController#index$"'

En la sección traceAgent del archivo values.yaml, agrega DD_APM_IGNORE_RESOURCES en la sección env, luego inicia helm como de costumbre.

values.yaml

    traceAgent:
      # agents.containers.traceAgent.env -- Additional environment variables for the trace-agent container
      env:
        - name: DD_APM_IGNORE_RESOURCES
          value: Api::HealthchecksController#index$

Para múltiples valores:

        - name: DD_APM_IGNORE_RESOURCES
          value: value1, Api::HealthchecksController#index$

Alternativamente, puedes establecer agents.containers.traceAgent.env en el comando helm install:

helm install dd-agent -f values.yaml \
  --set datadog.apiKeyExistingSecret="datadog-secret" \
  --set agents.containers.traceAgent.env[0].name=DD_APM_IGNORE_RESOURCES, \
    agents.containers.traceAgent.env[0].value="Api::HealthchecksController#index$" \
  datadog/datadog

Si usas Amazon ECS (como en EC2), en la definición de tu contenedor del Agente de Datadog, agrega la variable de entorno DD_APM_IGNORE_RESOURCES con los valores de tal manera que el JSON evalúe a algo como esto:

    "environment": [
	// other environment variables for the Datadog Agent
        {
          "name": "DD_APM_IGNORE_RESOURCES",
          "value": "Api::HealthchecksController#index$"
        }
     ]
Filtrar trazas de esta manera elimina estas solicitudes de métricas de traza. Para información sobre cómo reducir la ingestión sin afectar las métricas de traza, consulta controles de ingestión.

Configuración del trazador

Algunos trazadores para algunos lenguajes pueden descartar trazas antes de que sean enviadas al Agente de Datadog. Usa esta opción si tienes requisitos específicos de la aplicación.

1. Si la solicitud está asociada con una traza distribuida, la traza resultante puede tener imprecisión de muestreo si se eliminan partes de ella debido a estas reglas de filtrado.
2. Filtrar las trazas de esta manera elimina estas solicitudes de métricas de traza. Para obtener información sobre cómo reducir la ingesta sin afectar las métricas de traza, consulte controles de ingesta.

El rastreador de Ruby tiene una canalización de post-procesamiento que elimina las trazas que cumplen con ciertos criterios. Más información y ejemplos se pueden encontrar en Post-procesamiento de trazas.

Por ejemplo, si el nombre del recurso es Api::HealthchecksController#index, use la clase Datadog::Tracing::Pipeline::SpanFilter para eliminar las trazas que contienen el nombre del recurso. Este filtro también se puede usar para filtrar otros metadatos disponibles para el objeto de tramo.

Datadog::Tracing.before_flush(
   Datadog::Tracing::Pipeline::SpanFilter.new { |span| span.resource =~ /Api::HealthchecksController#index/ }
)

El rastreador de Python proporciona una opción para filtrar trazas no deseadas:

Usando filtros personalizados

Para casos de uso avanzados, puede crear filtros personalizados:

from ddtrace.trace import tracer
from ddtrace.trace import TraceFilter
import re

class CustomFilter(TraceFilter):
    def __init__(self, pattern):
        self.pattern = re.compile(pattern)

    def process_trace(self, trace):
        for span in trace:
            if span.get_tag('http.url') and self.pattern.match(span.get_tag('http.url')):
                return None  # Drop the trace
        return trace  # Keep the trace

# Configure the SDK with your custom filter
tracer.configure(trace_processors=[CustomFilter(r'http://.*/healthcheck$')])

Configure una lista de bloqueo en el plugin Http. Tenga en cuenta en qué coincide la lista de bloqueo según la documentación de la API. Por ejemplo, las solicitudes Http entrantes coinciden con las rutas de URL, así que si la etiqueta de tramo de la traza es http.url y es http://<domain>/healthcheck, escriba una regla que coincida con la healthcheck URL:

const tracer = require('dd-trace').init();
tracer.use('http', {
  // incoming http requests match on the path
  server: {
    blocklist: ['/healthcheck']
  },
  // outgoing http requests match on a full URL
  client: {
    blocklist: ['https://telemetry.example.org/api/v1/record']
  }
})

//import http
La configuración del SDK para la integración debe venir antes de que se importe ese módulo instrumentado.

El rastreador de Java tiene una opción para un TraceInterceptor personalizado para filtrar ciertos tramos. Consulte Extensión de trazadores.

Por ejemplo, si su nombre de recurso es GET /healthcheck, escriba un interceptor de traza que elimine las trazas que contengan este nombre de recurso. Ajuste la lógica para satisfacer su caso de uso.

public class GreetingController {
   static {
       // In a class static block to avoid initializing multiple times.
       GlobalTracer.get().addTraceInterceptor(new TraceInterceptor() {
           @Override
           public Collection<? extends MutableSpan> onTraceComplete(Collection<? extends MutableSpan> trace) {
               for (MutableSpan span : trace) {
                   if ("GET /healthcheck".contentEquals(span.getResourceName())) {
                       return Collections.emptyList();
                   }
               }
               return trace;
           }
           @Override
           public int priority() {
               return 200;  // Some unique number
           }
       });
   }
}